A valid request URL is required to generate request examples{
"id": "3c90c3cc-0d44-4b50-8888-8dd25736052a",
"key": "teacher",
"name": "Professor",
"is_system": true,
"permissions": [
"$team.manage",
"grades:write"
],
"current_version": 123,
"member_count": 123
}{
"error": {
"code": "forbidden",
"message": "your role does not allow this action"
}
}{
"error": {
"code": "forbidden",
"message": "your role does not allow this action"
}
}{
"error": {
"code": "forbidden",
"message": "your role does not allow this action"
}
}{
"error": {
"code": "forbidden",
"message": "your role does not allow this action"
}
}{
"error": {
"code": "owner_must_manage_the_team",
"message": "that version does not grant $team.manage, and the owner role cannot give it up"
}
}Restore a customer role version
Requires customers:write. Put an earlier permission set back.
Nothing new is written: the role’s head moves and the version that was live stays on the shelf, so restoring is itself reversible. That is the difference between a rollback and a fourth version that happens to be a copy of the second.
The version must belong to this role — one from another role answers 404 rather than pointing a role at a set that was never its. And it carries the same refusal an edit does: a version that does not grant $team.manage cannot become the owner role’s live set.
A valid request URL is required to generate request examples{
"id": "3c90c3cc-0d44-4b50-8888-8dd25736052a",
"key": "teacher",
"name": "Professor",
"is_system": true,
"permissions": [
"$team.manage",
"grades:write"
],
"current_version": 123,
"member_count": 123
}{
"error": {
"code": "forbidden",
"message": "your role does not allow this action"
}
}{
"error": {
"code": "forbidden",
"message": "your role does not allow this action"
}
}{
"error": {
"code": "forbidden",
"message": "your role does not allow this action"
}
}{
"error": {
"code": "forbidden",
"message": "your role does not allow this action"
}
}{
"error": {
"code": "owner_must_manage_the_team",
"message": "that version does not grant $team.manage, and the owner role cannot give it up"
}
}Authorizations
A staff session token, uk_st_…. Minted by sign-up, sign-in or the two-factor exchange. Only a 401 means it is spent; not_a_member (403) is about the organization named in X-Organization-Id and leaves the token good for the others.
Headers
The organization the caller is acting on — the org_… code that appears in the panel URL. It identifies; the membership JOIN is what authorizes, so a forged code reads nothing: the answer is not_a_member (403), which does not mean the session is over. Absent, the session's default organization answers, or — if that membership was revoked while the session was open — any other one the caller still holds.
Path Parameters
The role.
The version to make live.
Query Parameters
Which environment to act in. A view parameter, valid only on the staff surface — a machine credential never chooses its environment, it is resolved from the key.
live, test Response
The role, now granting what that version granted.
A role inside a customer, in one environment. permissions mixes the two vocabularies: $… entries are the capabilities UserKit evaluates, everything else is yours and reaches your backend through the contact's JWT.
The stored literal. Immutable.
"teacher"
"Professor"
owner and member, seeded into every environment. Not deletable; name and permissions still editable.
["$team.manage", "grades:write"]
Which version of the permission set is live. An edit bumps it; a restore moves it back.
Memberships holding this role. A role with any cannot be deleted.