"""Unit tests — Spec 027 RBAC matrix.""" from __future__ import annotations import importlib.util import sys import unittest from pathlib import Path API_ROOT = Path(__file__).resolve().parents[1] def _load(name: str, rel_path: str): path = API_ROOT / rel_path spec = importlib.util.spec_from_file_location(name, path) if spec is None or spec.loader is None: raise ImportError(path) mod = importlib.util.module_from_spec(spec) sys.modules[name] = mod spec.loader.exec_module(mod) return mod permissions = _load("permissions_027", "app/permissions.py") registry = _load("registry_027", "app/modules/registry.py") ASSIGNABLE_ROLES = permissions.ASSIGNABLE_ROLES HUMAN_ROLES = permissions.HUMAN_ROLES can_create_foss_order = permissions.can_create_foss_order can_manage_billing = permissions.can_manage_billing can_read_billing = permissions.can_read_billing can_read_crm_leads = permissions.can_read_crm_leads can_validate_billing = permissions.can_validate_billing is_assignable_role = permissions.is_assignable_role ROLE_MODULE_DEFAULTS = registry.ROLE_MODULE_DEFAULTS role_module_defaults = registry.role_module_defaults class TestSpec027Permissions(unittest.TestCase): def test_human_role_count(self): self.assertGreaterEqual(len(HUMAN_ROLES), 13) def test_assignable_excludes_super_admin(self): self.assertNotIn("super_admin", ASSIGNABLE_ROLES) self.assertIn("sales_admin", ASSIGNABLE_ROLES) self.assertIn("sales_support", ASSIGNABLE_ROLES) def test_sales_admin_billing_validate(self): self.assertTrue(can_validate_billing("sales_admin")) self.assertTrue(can_manage_billing("sales_admin")) self.assertTrue(can_read_billing("sales_admin")) def test_sales_support_no_billing_validate(self): self.assertFalse(can_validate_billing("sales_support")) self.assertFalse(can_manage_billing("sales_support")) self.assertTrue(can_read_billing("sales_support")) def test_finance_billing(self): self.assertTrue(can_validate_billing("finance")) self.assertTrue(can_create_foss_order("finance")) def test_sales_roles_crm(self): self.assertTrue(can_read_crm_leads("sales_admin")) self.assertTrue(can_read_crm_leads("sales_support")) self.assertTrue(can_read_crm_leads("marketing")) def test_registration_roles(self): for role in ( "ops_lead", "technician", "noc", "sales_admin", "sales_support", "finance", "marketing", "seo", "developer", "devops", "security_analyst", "content_editor", "agentic_operator", ): self.assertTrue(is_assignable_role(role), role) def test_role_module_defaults(self): sales_admin_mods = role_module_defaults("sales_admin") self.assertIsNotNone(sales_admin_mods) assert sales_admin_mods is not None self.assertIn("billing-recurrence", sales_admin_mods) self.assertNotIn("billing-recurrence", role_module_defaults("sales_support") or set()) def test_ops_roles_no_module_filter(self): self.assertIsNone(role_module_defaults("ops_lead")) self.assertIsNone(role_module_defaults("technician")) def test_all_defaults_registered(self): for role, mods in ROLE_MODULE_DEFAULTS.items(): self.assertIn("core", mods, role) if __name__ == "__main__": unittest.main()