ACL Manager

Supervised least privilege for messy live databases — AI proposes, humans confirm, chaos does not get amplified.

Why it exists

Most Odoo installations are a permission mess. Groups stay open because removing one feels dangerous — overnight a clerk can no longer pick an analytic account, a journal, or a product on a customer form. Fear beats hygiene, so almost everyone drifts toward “almost Settings”.

AI intensifies that problem. Users rarely see how oversized their access already is; an assistant that acts with those same privileges turns leftover ACL into an automated attack surface. Without least privilege, a chat assistant inherits oversized access and can read where the user never consciously looked — payroll, journals, or another team's documents — simply because the groups were left open “just in case”. At the same time, AI is part of the solution — if it does not “fix chaos by hand”, but works inside a supervised least-privilege frame: closed roles, a human Confirm on every sensitive change, and a deterministic align path instead of free-form group surgery.

In the AI era, ACL cannot stay “leave it open just in case”. It has to become supervised management of minimum privilege — with AI accelerating diagnosis and proposals, not amplifying disorder.

Compared to OCA user roles

Inspired by the OCA idea, not a fork of it. Same goal — package res.groups into roles — with a playbook that fits messy live databases and an AI-era ERP:

Under Apache-2.0, no hard dependency on OCA. Uninstalling this module leaves native Odoo groups on users as they were — it is a facilitator, not a parallel permission system.

What it is

Agentic access-control manager for the Patanegra Soft Suite (seed agent pns_acl_manager). It packages native Odoo res.groups into functional roles, adds selection grants (pick records without master UI), ships a safe migrate-then-align playbook for live databases, keeps ACL checkpoints so you can undo a bad align or migrate, and can Suggest names for Seal proposals from the same screen (no Chatboo skills). See Compared to OCA user roles above for how that differs from a hard sync-on-install model.

ACL checkpoints

Production airbag: before every align and every migrate, the module stores a versioned restore point (acl.checkpoint, schema v2) with the full role catalog (incl. Seal origin/candidates), assignment lines, selection grants, model guards and native group sets for the users in scope. Restore archives roles that did not exist in the snapshot. You can also create one manually from ACL Manager → Checkpoints.

Model guards & role Access panel

Menus hide screens, not data. Native Odoo lets Purchase / Sales users read every journal item even when Accounting menus are hidden — so an AI chat (or an export) can dump the whole ledger. A model guard (acl.guard) closes the model at the ORM level for everyone except the roles you pick.

Features

  • ACL roles — packages of groups assigned to users
  • Dated assignments — Valid from / Valid to (holidays, temporary cover), plus a quick +30/60/90-day duration shortcut; daily cron re-applies groups
  • Role-level validity window — a whole role can itself expire (Valid from / Valid to on the role), not just individual assignments
  • Expiring soon — ACL Manager → Expiring soon lists every dated assignment with 7/30-day and "already expired" filters; a daily cron also schedules a To-do activity for Settings admins before a role or assignment lapses
  • Default role for new users — flag a role "Assign to new users automatically" and every internal user created afterwards gets it on creation; a role-form button backfills users that already existed
  • Create role from user — Action on Users
  • Create role from groups — Action on Groups
  • Align user permissions to roles — deterministic wizard on the user form; drops snapshot lines and rewrites native groups to Grant-ON roles only, in one DB transaction
  • Remove permissions outside their roles — one header button on each role: rewrites every assigned user to exactly what their roles grant, no row selection; a red Misaligned counter on the role shows how many users hold leftovers (Odoo's implied technical groups always count as aligned)
  • Add users & give role permissions… — on each role: filter internal users by groups, pick a list, assign in one step; by default it also removes their permissions outside their roles right after
  • Access tab on each role — groups + selection grants + blocked models in one place; Block this role from a model… closes Purchase/Sales ORM leaks without making the role keep access
  • Model guards — lock a sensitive model at the ORM; global menu Protect a model… chooses who keeps access
  • ACL checkpoints — auto restore points before align/migrate; manual capture + UI restore with preview (see section above)
  • Discover + Migrate — snapshot current membership with Grant role groups to users OFF
  • Selection grants — Many2one pickers without master menus/forms; optional domain + field whitelist
  • Grant role groups to users flag — enforce via roles only when you are ready
  • Roles ↔ Groups ↔ Users navigation — every user, group and role form cross-links to the others with real, clickable lists (not read-only modals)
  • ACL Manager → Users / Groups — dedicated lists with ACL role/group counters, also reusable filtered to one role's members
  • Suggest names — ACL Seal catalog button calls the module agent (pns_acl_manager) to rename automatic proposals; no Chatboo skill
  • Chatboo / MCP knowledge — context pack + trusted align actions; still no ACL Chatboo skills

Production playbook

  1. Open ACL Manager → Discover roles and run discovery.
  2. Migrate from current state — creates missing discovery roles only (origin=migrate); never overwrites Manual/Seed packages. Refresh migrate snapshots rewrites only migrate-owned roles. Grant stays OFF. An automatic checkpoint is taken first.
  3. Review / align each role under ACL Manager → Roles.
  4. Enable Grant role groups to users only when ready to enforce via roles.
  5. On each role: Remove permissions outside their roles — one click rewrites every assigned user (the red Misaligned counter tells you when it is needed). Or, per user / selection: Align user permissions to roles — drops snapshot lines and rewrites native groups to the union of enabled Grant-ON roles only. Deterministic and atomic — from the UI button, or proposed by Chatboo/MCP as the acl.align / acl.bulk_align trusted action (never imitated with raw Safe Plan CRUD steps). An automatic checkpoint is taken before each align (one shared blob for bulk).
  6. If something goes wrong: ACL Manager → Checkpoints → open a restore point → Restore… → Confirm. Restore is human UI only (not Safe Plan).

ACL Manager is Settings-only (base.group_system). Settings (system) users and portal/share users are never rewritten by grant or align. Auto-checkpoints keep the last 30 non-manual entries; manual checkpoints are kept.

Selection grants

Per role + model: auto-managed selector res.groups, read-only ir.model.access, optional ir.rule from domain override. Selector-only users: master menus hidden, forms blocked, field whitelist on read. Full app ACL on the model still wins over selector-only limits.

AI posture

Capture and migrate stay in the ACL Manager UI only. Chatboo may help with ad-hoc additive proposes (create a role, add a group, assign a user via propose_safe_operations + Confirm) and it can now also propose align / least-privilege enforce — but ONLY as a trusted action (op="action", action_code: "acl.align" / "acl.bulk_align"), a closed, pre-vetted call into the EXACT same _acl_align_plan() / _acl_align_apply() the UI wizard and bulk action use. It must never imitate an align with raw create/write/unlink steps, rewrite native groups directly, mass-delete assignment lines, or resurrect retired skills. The trusted action still requires Settings access and human Confirm on the toast — the wizard/button on the user form remains available as an alternative.

Models

ModelPurpose
acl.rolePermission package (groups + grant flag)
acl.role.lineUser assignment with optional date window
acl.grantSelection without master UI
acl.guardDeny sensitive model at ORM (except chosen roles)
acl.discovery.wizardScan / migrate helpers
acl.user.align.wizardDeterministic single-user align preview + apply
acl.checkpointVersioned ACL restore point (roles, lines, grants, user groups)

Apache License 2.0 — © 2026 PATANEGRA Soft