Skip to content

History / PHP Enums and RBAC

Revisions

  • PHP-Enums-and-RBAC: describe the code that exists, not the code that used to Ed's catch, and a fair one — the page was comparing enums against a string-keyed design that no longer exists. It quoted four functions that have been deleted (rbacCapabilities, rbacAllCapabilityKeys, rbacCapabilityExists, rbacCapabilityLabel), invented a capability that was never shipped (tickets.manage_settings), and presented all of it under "what we built last week". A wiki page should describe the actual code. Rewritten against the codebase as it stands: Cap:: constants, and a registry DERIVED from each module's settings manifest. Every symbol and every number on the page verified against the source — 76 capabilities, 76 constants, and the guard's parameter really is still `string`. The rewrite also forced an honest walk-back the old page never made. Its central claim was that enums would collapse four hand-maintained lists (constants, registry, tab layout, setting-key map) onto one type. THOSE LISTS WERE ALREADY COLLAPSED — without enums — by deriving the registry from the manifest. So the headline benefit is banked, and the metadata arguably lives somewhere better: next to the tab it belongs to, rather than on the type. What genuinely remains is one narrow thing: a guard whose signature could refuse a string outright. requireCapabilityJson(string $capability) still accepts one; the constant makes the right thing easy and a typo loud, but it cannot make the wrong thing impossible. That is a real gap, and it is now the ONLY one — which is exactly why the floor stayed at 7.4. Also corrected two claims on the floor page that had aged with it: it still called the enum "the only correctness argument on offer" (it isn't — the constants answered that), and its phase-2 plan still listed the deleted helpers among the things the swap would remove.

    @edmozley edmozley committed Jul 14, 2026
  • Wiki: split the PHP floor page, refresh Roles & Permissions, restructure the sidebar The PHP floor page had grown to 861 lines and was three documents in a trench coat: a decision, a language tour, and a deep argument about permission keys. Split into three, each standing alone: Raising-the-PHP-Floor (307) the DECISION — where we are, who breaks, the verdict, and the constants-to-enums bridge PHP-8-Language-Features (261) the 101 tour of 8.0/8.1 with before/after from real code, including the features that WOULDN'T help us, said plainly PHP-Enums-and-RBAC (353) the one feature the argument turns on — and the reason a capability is a Cap:: constant and never a string. Worth reading even if the floor never moves, because it explains the permission system. Section numbers and cross-references rewritten by meaning rather than by find-and-replace, since the sections changed pages. Roles & Permissions was stale: written before the manifest became the single declaration and before the endpoint audit existed. Now says that capabilities are derived from one file per module (and why the four-list version was the bug), and carries a table of what D005 has actually found — the shared settings endpoint, six Intune endpoints, all 49 RFP Builder endpoints, unauthenticated audit-log forgery, and an LMS learner reaching the authoring settings. Every one found by hand, by accident, which is the point. Sidebar: the security pages are now grouped by the three layers they belong to (module access → capabilities → administrator), rather than a flat list, and all nine RBAC/PHP pages are linked. The two new PHP pages nest under the floor page.

    @edmozley edmozley committed Jul 13, 2026