Roles and permissions
Admin, Roles (/admin/roles), gated by the role.manage permission.
A role is a named set of permissions. Users hold one or more roles, and their effective permissions are the union.
A role holding * is a superuser within its tenant. Not across tenants: there is
no permission anywhere that crosses a tenant boundary.
Using the screen
Section titled “Using the screen”Roles are listed down the side, each with how many people hold it. Select one to see its grants grouped by area (Tickets, Repairs & charges, Devices, Identity, Administration and so on), each with a readable name beside the exact permission key. Editing a role uses the same areas; saving shows the grants for review first, because saving replaces the role’s whole permission set.
A role’s permissions also decide the seat type of everyone who holds it. Granting a role that raises someone’s seat says so in the role step on the Users page, and never blocks the grant.
Build roles first
Section titled “Build roles first”Create the roles, then create the users. Doing it the other way means editing every account when you realise the role was wrong.
Roles that match a school desk
Section titled “Roles that match a school desk”A shape that works for most schools:
| Role | Holds | For |
|---|---|---|
| Administrator | * |
You, and one other person |
| Technician | View and update everything operational; issue and return loans; create, update and close repairs and tickets; view costs | Your day-to-day staff |
| Senior technician | Technician, plus device.manage, directory.manage, charge.approve, report.manage |
Whoever is trusted with MDM commands and money |
| Front desk | loan.view, loan.issue, loan.return, repair.view, repair.create, client.view, stock.manage |
A counter that hands things out but does not fix them |
| Read only | The .view permissions |
A head of department who wants visibility |
| Agentforce pilot | client.view, assistant.agentforce.use |
Selected staff authorised for the Salesforce execution identity’s data; requires the upcoming advisory connector pilot |
| Operations coordinator | operations.view, operations.manage |
Projects, maintenance, events, purchasing and shared resources |
| Operations approver | operations.view, operations.approve |
Staff assigned to approve spending or change plans |
| Ticket approver | ticket.view, approvals.view, approvals.decide |
Staff assigned to approve requests within their department and campus |
The front desk role is the one worth building even in a small school. It is what lets you put a student helper or a casual on the counter during the first week of term without giving them the directory or the audit log.
The full permission list
Section titled “The full permission list”The complete, current set of permission keys — grouped by area, with what each
one allows — lives on one page so it cannot drift out of sync with itself: the
permissions reference. That page is generated
against packages/core/src/permissions.ts and checked for parity with it, so
it is the page to build roles from.
Two splits are worth knowing about before you build a role:
ticket.internal is split out on purpose. An internal note is where somebody
writes “third time this term, escalate” or “her mother rang, do not put this in
writing”. Separating it means a school can hand a casual the queue without
handing them that.
charge.raise and charge.approve are split across two people on purpose. A
technician who can propose a charge must not be able to make it real, and the
person who decides a family pays is the same person who can decide they do not,
so waiving sits with approval rather than with raising. See
damage charges.
Permissions apply everywhere
Section titled “Permissions apply everywhere”The same checks run on every surface:
- The web console.
- The public REST API, scoped to the API key.
- The MCP server, where a key without a permission does not
even see the corresponding tool in
tools/list. - The assistant, which can only do what the signed-in user’s role allows.
There is no ambient administrator and no back door for an integration. An API key is a set of scopes, and it cannot exceed them.
Two to be careful with
Section titled “Two to be careful with”device.wipe.approve makes a wipe happen. That command destroys a
student’s data and cannot be undone — it is split from device.wipe.request
so the person who asks for a wipe is not, by default, the person who can also
make it happen.
Live identity actions use separate permissions, including
identity.password.reset, identity.mfa.reset and
identity.mailbox.delegate. Re-enabling an account requires both
identity.account.manage and identity.account.enable; granting Full Access
also requires identity.mailbox.fullaccess. These operations can change who
controls an account. Grant them selectively and record the reason and related
ticket. directory.manage covers the older directory workflow and does not
replace these live-action permissions.
Auditing
Section titled “Auditing”Permission-gated actions are written to the audit log with who did it, when, and what changed. Reviewing that log once a term shows which permissions are in use, which is often narrower than what people asked for.
The 0.12.0-rc.3 candidate records covered directory actions and guarded live identity operations, with demo results labelled as such. Confirm the installed version and deployment status. Audit coverage is not complete for every operation; see coverage limits. A linked ticket preserves the reason for an action in addition to its audit record.