Skip to content

PRD: Phân cấp Resource, Action & Domain

ModuleQuyền hạn (CORE-02)PRD IDPRD-HIER-001
StatusDraftOwnerPhat Nguyen
Date2026-06-04Versionv0.1
Packages@nx/core · @nx/identityURDHIER · DECL

TL;DR

Mô hình hoá permission thành cây resource × bậc thang action × cây domain để một grant thô duy nhất - Sale:manage trên một organizer - thay thế hàng trăm dòng phẳng theo từng method, bao mọi subject, operation và merchant bên dưới. Với chủ sở hữu nền tảng và kỹ sư, điều này biến những role cồng kềnh, dễ vỡ thành vài grant dễ đọc và rút việc khai báo permission cho một controller xuống chỉ một lời gọi helper.

1. Context & Problem

Engine scoped-RBAC (ignis CASBIN_RBAC_DOMAIN_SCOPED_MODEL) cung cấp ba trục kế thừa mà KICKO chưa khai thác: trục action (g5, manage ⊃ read), trục resource (g4 + objectMatch dạng dotted, Order ⊃ Order.refund, Order ⊃ OrderItem), và trục domain (g3, Organizer ⊃ Merchant).

Hiện tại permission đang ở dạng phẳng: ~950 code Subject.method, mỗi cái cấp riêng lẻ. OWNER mang ~950 dòng grant; "HQ thấy tất cả" liên merchant được giả lập bằng cách ghi một membership join_domain cho từng merchant. Không có super-action manage/write và không có cơ chế khai báo thuận tiện - mỗi package tự viết tay createPermission. Hệ quả là role trở nên cồng kềnh, dễ vỡ, tải chậm và khó suy luận. Mô hình hoá permission thành cây × bậc thang × cây-domain cho phép một role gộp lại còn vài grant thô trong khi role chi tiết vẫn chính xác, và biến việc khai báo permission thành một lời gọi helper.

2. Goals & Non-Goals

Mục tiêu

  • Gộp grant của role - OWNER trở thành (Sale, manage) thay vì mọi dòng SaleOrder.*.
  • Một bậc thang action ba bậc: manage ⊃ {write, read, execute}, write ⊃ {create, update, delete}.
  • Một phân cấp resource không đổi tên code - subject giữ nguyên code; nhóm theo module cộng với lồng liên-thực-thể qua g4, và lồng operation tự do qua objectMatch dạng dotted.
  • Một phân cấp domain Merchant ⊂ Organizer qua g3 - role HQ/quản lý vươn tới mọi merchant của một organizer qua một grant theo scope organizer, loại bỏ việc backfill membership cho từng merchant.
  • Một bộ công cụ khai báo tối giản boilerplate (defineResource / crudPermissions / ma trận role→grant / seeder cạnh cấu trúc idempotent), xây trong nx-seller trước.

Ngoài phạm vi

  • Đưa bộ công cụ vào IGNIS - hoãn sang đợt sau (nx-seller trước, chuyển sau).
  • Permission glob/regex tuỳ ý (sales.*) - độ thô đến từ phân cấp, không phải glob.
  • Thay đổi tập role hay ngữ nghĩa priority - một mối quan tâm riêng.
  • Permission theo thời gian/ca và log audit permission.

3. Success Metrics

MetricMục tiêu / tín hiệu
Nén grantSố dòng grant mỗi role giảm từ ~950 xuống vài chục
DX khai báoThêm controller mới chỉ cần một lời gọi khai báo (không liệt kê CRUD)
Idempotency của seedmigrate:dev chạy lại không thay đổi gì; code đã gỡ được reconcile away
Tương đương phân quyềnLaunchpad + mọi route được bảo vệ giữ nguyên kết quả cho phép/từ chối (đã kiểm thử hồi quy)
Tầm với HQRole HQ/quản lý vươn tới mọi merchant của organizer mà không cần dòng membership cho từng merchant

4. Personas & Use Cases

PersonaMục tiêu trong tính năng này
Chủ sở hữu / admin nền tảngGán role thô, dễ đọc (Sale:manage) thay vì sửa hàng trăm dòng grant
Owner (HQ)Vươn tới mọi merchant của organizer qua một grant theo scope organizer
Kỹ sưKhai báo permission + resource node + base action của một controller trong một lời gọi helper
OperatorTin rằng việc seed lại là idempotent và code cũ được reconcile away

Core scenarios: khai báo resource và operation của một controller trong một lời gọi → seed bậc thang action, roll-up resource và cạnh domain một cách idempotent → gán role dưới dạng ma trận thô nhỏ gọn → một request giải độ phủ qua bậc thang action, cây resource và cây domain mà không cần liệt kê phẳng nào.

5. User Stories

  • Là một admin, tôi muốn cấp (Sale, manage) cho OWNER, để role bao mọi sale subject và operation mà không phải liệt kê từng cái.
  • Là một HQ owner, tôi muốn một grant theo scope organizer vươn tới mọi merchant của organizer, để không còn phụ thuộc vào dòng membership cho từng merchant.
  • Là một kỹ sư, tôi muốn khai báo resource node, operation và base action của một controller trong một lời gọi helper, để thêm route không đồng nghĩa với viết tay permission CRUD.
  • Là một operator, tôi muốn việc seed reconcile các code đã gỡ một cách idempotent, để permission và grant cũ không bao giờ tích tụ.
  • Là một người thiết kế role, tôi muốn một action rộng hơn (manage/write) đáp ứng mọi request hẹp hơn, để tôi cấp theo ý định thay vì từng động từ CRUD.

6. Functional Requirements

#Yêu cầuURD ref
FR-1Một grant CÓ THỂ nhắm tới resource ở bất kỳ cấp nào - module, subject hay operation - và bao mọi hậu duệURD-HIER-001
FR-2Resource operation lồng dưới subject của nó theo code dạng dotted (SaleOrder.refund ⊂ SaleOrder) không cần cấu hình thêmURD-HIER-002
FR-3Một subject CÓ THỂ roll up lên một module để một grant cấp module bao mọi subject trong đóURD-HIER-003
FR-4Một thực thể con CÓ THỂ lồng dưới cha xuyên cách đặt tên (SaleOrderItem ⊂ SaleOrder) qua g4URD-HIER-004
FR-5Action tạo thành bậc thang - manage ⊃ {write, read, execute}, write ⊃ {create, update, delete} - rộng hơn đáp ứng hẹp hơnURD-HIER-005
FR-6Một route yêu cầu một base action (read/create/update/delete/execute); một grant CÓ THỂ dùng bất kỳ bậc nào kể cả manage/writeURD-HIER-006
FR-7Một grant theo scope organizer áp dụng cho mọi merchant bên dưới; một grant theo scope merchant chỉ áp dụng tại đóURD-HIER-007
FR-8Một role HQ / quản lý vươn tới mọi merchant của organizer qua một grant theo scope organizer - không cần dòng membership cho từng merchantURD-HIER-008
FR-9Một grant CÓ THỂ ghim vào SYSTEM_WIDE (mọi nơi) hoặc ANY_MEMBER (mọi merchant đã tham gia)URD-HIER-009
FR-10Permission, bậc thang action và các cạnh phân cấp resource/domain được khai báo trong code và seed một cách idempotentURD-DECL-001
FR-11Khai báo operation + resource node + base action của một controller chỉ tốn một lời gọi helperURD-DECL-002
FR-12Gán role→grant được khai báo dưới dạng ma trận nhỏ gọn (OWNER → Sale:manage), không liệt kê theo từng operationURD-DECL-003
FR-13Việc seed reconcile các code đã gỡ một cách idempotent - không tích tụ permission/grant cũURD-DECL-004
FR-14Bộ công cụ được xây trong nx-seller trước, với lộ trình rõ ràng để chuyển vào IGNIS sauURD-DECL-005

Toàn văn yêu cầu và tiêu chí chấp nhận nằm trong URD Quyền hạn. PRD này tham chiếu chúng thay vì lặp lại.

7. Non-Functional Requirements

Khía cạnhYêu cầu
Tương đương phân quyềnGiải độ phủ qua objectMatch/g4 (resource), g5 (action), g3 (domain) giữ nguyên kết quả cho phép/từ chối so với mô hình phẳng
Idempotency của seedCác cạnh cấu trúc (g3/g4/g5) và permission code seed một cách idempotent; chạy lại là no-op; code đã gỡ được reconcile away
Tenancy & authzMột grant giải trong một domain merchant đang hoạt động cho mỗi request (x-merchant-id); scope organizer mở rộng qua g3, không qua dòng cho từng merchant
Hiệu năng / quy môSố dòng grant mỗi role gộp từ ~950 xuống vài chục, thu nhỏ tải policy và chi phí enforcement mỗi request
Khả năng bảo trìMột helper khai báo cho mỗi controller; không còn createPermission viết tay theo từng package
i18nTên/mô tả permission hiển thị cho người dùng vẫn song ngữ ({ en, vi })

8. UX & Flows

Đợt này là hạ tầng phân quyền - không có màn hình người dùng cuối. Nó thể hiện qua UI quản trị permission/role hiện có (trang Permission Matrix và các view role-grant), nơi các grant thô giờ hiển thị thành vài dòng thay vì ~950. Xem bản đồ Phân cấp Permission.

9. Data & Domain

Thực thểVai trò
Permission (resource code)Danh mục module + subject + operation tuỳ chỉnh - không phải ~950 dòng method
Bậc thang action (g5)Các cạnh kế thừa manage/write/read/execute/create/update/delete
Cạnh resource (g4 + objectMatch dotted)Roll-up module⊃subject và lồng liên-thực-thể / operation
Cạnh domain (g3)Organizer ⊃ Merchant để grant theo scope organizer vươn tới mọi merchant
Grant (policy)(Role|User, resourceCode, action, domain, effect)
Ma trận role→grantGán thô theo kiểu khai báo (OWNER → Sale:manage)

Chỉ ở mức khái niệm - toàn bộ schema và Casbin model nằm trong tài liệu developer RBACCasbin Authorization.

10. Dependencies & Assumptions

Phụ thuộc vào

  • Engine scoped-RBAC (ignis CASBIN_RBAC_DOMAIN_SCOPED_MODEL) - cung cấp các trục g3/g4/g5objectMatch.
  • Vai trò cố định & tùy chỉnh (URD-ROLE · URD-CROLE) - role là chủ thể của grant.
  • Danh mục permission & grant/revoke (URD-PERM · URD-GRANT) - danh mục mà phân cấp này định hình lại.
  • Effective permissions & scope (URD-EFF) - việc giải vẫn nằm trong domain merchant đang hoạt động.
  • @nx/core (Casbin model + adapter + enforcer) và @nx/identity (role, permission, grant).

Giả định

  • Code subject ổn định - phân cấp mang tính bổ sung (không đổi tên code).
  • Quan hệ organizer→merchant sẵn có để seed các cạnh g3.
  • Một bộ kiểm thử hồi quy bao launchpad và mọi route được bảo vệ cho tương đương cho phép/từ chối.

11. Risks & Open Questions

Rủi ro / câu hỏiGiảm thiểu / trạng thái
Việc giải độ phủ lệch khỏi mô hình phẳngKiểm thử hồi quy launchpad + mọi route được bảo vệ cho kết quả cho phép/từ chối giống hệt
Danh sách seed nhóm-module g4 chính xác (subject nào roll up vào module nào)Mở - sẽ liệt kê trong plan
execute cho operation tuỳ chỉnh cấp theo từng operation hay chỉ gộp vào manageMở - quyết định trước khi seed bậc thang action
Di chuyển membership owner theo từng merchant hiện có → grant theo scope organizerMở - định nghĩa hình dạng data migration
Seed lại có thể làm rớt code đang dùngViệc reconcile là idempotent và do code điều khiển; chạy lại là no-op

12. Release Plan & Launch Criteria

Khía cạnhKế hoạch
PhaseP3 - xem danh mục feature URD (HIER + DECL)
RolloutTheo giai đoạn: (1) toolkit + bậc thang action (g5) + gộp grant OWNER/EMPLOYEE/CASHIER về dòng thô trong nx-seller; (2) cây domain (g3) + loại bỏ backfill membership theo merchant + grant quản lý theo scope organizer; (3) chuyển toolkit sang IGNIS (PRD riêng)
MigrationData migration: membership owner theo từng merchant hiện có → grant theo scope organizer; seed cạnh cấu trúc chạy qua migrate:dev
Launch criteriaSố dòng grant mỗi role gộp xuống vài chục; migrate:dev idempotent; launchpad + mọi route được bảo vệ giữ nguyên kết quả cho phép/từ chối
MonitoringSố dòng grant mỗi role, kiểm tra idempotency của seed, bộ kiểm thử hồi quy cho phép/từ chối phân quyền

13. FAQ

Việc này có cần đổi tên code subject không? Không. Phân cấp mang tính bổ sung - subject giữ nguyên code; việc nhóm và lồng diễn ra qua các cạnh g4objectMatch dạng dotted.

Sale:manage khác glob như sales.* ở chỗ nào? Độ thô đến từ cây resource cộng với action manage, không phải regex glob. Không có permission wildcard.

Giờ một HQ owner vươn tới mọi merchant bằng cách nào? Qua một grant theo scope organizer được giải qua g3 - việc backfill membership join_domain cho từng merchant được loại bỏ.

Một action rộng hơn có bao các action hẹp hơn không? Có. manage ⊃ {write, read, execute}write ⊃ {create, update, delete}, nên một grant manage đáp ứng mọi request hẹp hơn.

Bộ công cụ có vào IGNIS không? Không trong đợt này - nó được xây trong nx-seller trước, với lộ trình rõ ràng để chuyển vào IGNIS ở một PRD sau.

Điều gì xảy ra với một permission code bị gỡ khỏi khai báo? Việc seed reconcile nó away một cách idempotent, cùng với các grant của nó - không tích tụ dòng cũ.

References

Proprietary and Confidential. Unauthorized copying, distribution, or use of this software is strictly prohibited.