List Users
One page of users, decorated with realm roles and tenant groups.
The window used to be hard-coded to the first 20 with no offset, so a realm with more users than that simply could not be browsed — and nothing said so, which is what made a truncated list look like the whole one.
Whether more rows exist is reported in the X-Has-More header, and it is derived by asking Keycloak for one row beyond the page and throwing it away. That is deliberate, and replaces a /users/count route that lied: Keycloak's user SEARCH excludes service accounts while its user COUNT includes them, so on this realm the list returned 8 and the count said 14. The screen claimed 14 users, six of which it could never show, and offered a next page that resolved to nothing. Over-fetching asks the same endpoint both questions, so the two cannot disagree — no service-account naming convention to encode, and nothing to keep in sync when Keycloak changes.
The defaults reproduce the pre-paging behaviour: console-web resolves an email through this route and so does the sso-admin MCP, and neither passes a window. The body is still a bare array for the same reason — the extra fact rides in a header so no caller has to change.
Filters and a total. enabled, role and group narrow the list, and total=true asks for an exact X-Total-Count. Both need the whole set: a role or group filter is an intersection (Keycloak cannot search by either) and a count is only honest when it is the length of the set the page is cut from. So those requests enumerate the search once (up to ENUMERATION_CAP) and slice it; the total is never Keycloak's COUNT, which is the lie above. A request that only wants a total on a realm past the cap falls back to the window with no total (cut from the rows the enumeration already holds when it can be, from a second search when it cannot); a role/group filter there is refused, because filtering one page of a bigger set would show a short list that reads as complete. Everything else keeps the cheap windowed path exactly as it was.
X-Filters-Applied. When at least one of role, group, enabled was requested, a 200 carries the names of the filters it honoured, comma-separated in the fixed order role,group,enabled (role,enabled, or just enabled); with none requested the header is absent. It is sent on the enumerated path and the plain window alike. Absence from an older API means "not confirmed": that API ignores the parameters, and a missing X-Total-Count cannot tell the caller so, because a status filter past the cap legitimately has no total.
Request
- Base URLhttps://api.b2metric.com (the document declares no server; this is the origin it was published from)
- Authnone declared
Query parameters
Headers
Response
Successful Response
Changes
No recorded changes to this operation across all 1 revision of this API.