(this holder) may (act) on (that resource).
The fourth row is the one that earns the design. A grant whose resource is
another person makes “ask about someone else” an ordinary entitlement,
checked by the same code as everything else — instead of a relationship table
with its own rules that has to be audited separately.
Resources are a tree
You name the kinds. A syllabus is a programme with weeks beneath it and days beneath those; a CRM is accounts; a school is departments and cohorts.inherit set covers the whole subtree, so enrolling somebody in a
programme reaches every week and day inside it without enumerating them. A node
optionally carries a body of knowledge; a week that carries none simply costs
nothing.
Cycles are refused when the tree is rebuilt, not tolerated. A loop in a
parent chain does not return a wrong answer — it hangs the request that walks
it.
Roles include, they do not rank
A role reaches the grants of the roles itincludes:
tutor is reachable by head_teacher. A grant made to
head_teacher is not reachable by tutor.
A numeric level was the obvious alternative and is worse: it is a second
ordering that can disagree with the first, and “may a head of year read a
bursar’s ledger?” is not a question about magnitude. A lattice says exactly
what it means, and it expresses a CRM’s
manager ⊃ rep with the same
construct as a school’s four levels.Scoping a role to one subtree
Onetutor role serves every tutor. Narrow the assignment, not the role:
Deny always wins
A grant can be an allow or a deny, and deny is subtracted last. That lets you exclude one person from one week without unpicking the role that everybody else depends on.How a request is resolved
- The roles the principal holds, unexpired.
- Everything those roles reach through
includes. - Every grant held directly or by one of those roles.
- Subtrees expanded for inheriting grants.
- Role-scoped assignments intersected with their scope.
- Deny subtracted.
- What remains becomes the knowledge and the people this request may reach.
What retrieval does with it
No end user
Nothing changes. The dashboard and the public widget behave exactly as they
did before permissions existed.
An end user
Search is narrowed to what a grant names, in SQL, before ranking.
Knowledge that belongs to no group
A workspace’s profile, its FAQs and its hand-typed cards belong to no group, and by default they answer for everyone. That is right for an assistant talking to the public and wrong for a learner. So it is a per-workspace policy:It fails closed
An entitlement lookup that cannot be resolved yields an empty scope, not an open one. A request that the platform knows belongs to an end user but cannot identify reaches nothing.This is the opposite of how workspace scoping behaves, and the difference is
intentional. A background job with no workspace pinned is trusted code and
reads across the platform. An end user is by definition untrusted, and the
cost of guessing wrong is showing one person another person’s records.

