feat(commercial) : declare commercial.clients permissions + sync RBAC mirrors

Ajoute CommercialModule::permissions() (5 codes commercial.clients.* :
view, manage, accounting.view, accounting.manage, archive) — alignes sur
les is_granted deja references par ERP-55 (Client ApiResource, ClientProcessor,
ClientReadGroupContextBuilder).

Synchronise les 3 sources RBAC (regle ABSOLUE n8) : item sidebar
"Repertoire clients" (commercial.clients.view), persona user-full dans
personas.ts et SeedE2ECommand.php, cle i18n sidebar.commercial.clients.

Les roles metier Bureau/Compta/Commerciale/Usine sont seedes par ERP-74 :
les 5 permissions sont mappees ici sur le seul persona technique user-full
en attendant, sans creer de nouveau persona (regle n7).
This commit is contained in:
Matthieu
2026-06-01 09:45:17 +02:00
parent e1b8f8a28d
commit 2efdb8fec1
5 changed files with 59 additions and 0 deletions
+7
View File
@@ -103,6 +103,13 @@ return [
'label' => 'sidebar.commercial.section', 'label' => 'sidebar.commercial.section',
'icon' => 'mdi:account-arrow-left-outline', 'icon' => 'mdi:account-arrow-left-outline',
'items' => [ 'items' => [
[
'label' => 'sidebar.commercial.clients',
'to' => '/commercial/clients',
'icon' => 'mdi:account-group-outline',
'module' => 'commercial',
'permission' => 'commercial.clients.view',
],
[ [
'label' => 'sidebar.commercial.suppliers', 'label' => 'sidebar.commercial.suppliers',
'to' => '/suppliers', 'to' => '/suppliers',
+1
View File
@@ -23,6 +23,7 @@
}, },
"commercial": { "commercial": {
"section": "Commercial", "section": "Commercial",
"clients": "Répertoire clients",
"suppliers": "Répertoire fournisseurs" "suppliers": "Répertoire fournisseurs"
}, },
"core": { "core": {
+10
View File
@@ -65,6 +65,16 @@ export const personas: Record<PersonaKey, Persona> = {
'sites.bypass_scope', 'sites.bypass_scope',
'catalog.categories.view', 'catalog.categories.view',
'catalog.categories.manage', 'catalog.categories.manage',
// Commercial — Repertoire clients (M1). Mappe ici sur le persona
// "tout" en attendant les vrais roles metier (bureau/compta/
// commerciale/usine) seedes par ERP-74. Pas de nouveau persona
// (regle ABSOLUE n°7). commercial.clients.view n'ajoute pas de lien
// dans la section Administration, donc expectedAdminLinks reste inchange.
'commercial.clients.view',
'commercial.clients.manage',
'commercial.clients.accounting.view',
'commercial.clients.accounting.manage',
'commercial.clients.archive',
], ],
expectedAdminLinks: ['users', 'roles', 'sites', 'categories', 'audit-log'], expectedAdminLinks: ['users', 'roles', 'sites', 'categories', 'audit-log'],
}, },
@@ -9,4 +9,36 @@ final class CommercialModule
public const string ID = 'commercial'; public const string ID = 'commercial';
public const string LABEL = 'Commercial'; public const string LABEL = 'Commercial';
public const bool REQUIRED = false; public const bool REQUIRED = false;
/**
* Liste declarative des permissions RBAC exposees par le module Commercial.
*
* Consommee par la commande `app:sync-permissions` (SyncPermissionsCommand)
* qui se charge d'upserter ces entrees dans la table `permission`, de
* reactiver les codes precedemment marques orphelins et de marquer comme
* orphelins ceux qui ont disparu du code source.
*
* La cle `module` est auto-injectee par le sync command a partir de
* `self::ID`, il est donc inutile de la repeter dans chaque entree.
*
* Convention de nommage des codes : `module.resource[.sub].action` en
* snake_case, le prefixe module devant correspondre exactement a
* `self::ID` (verifie par la commande de synchronisation).
*
* Granularite alignee sur Core/Catalog (view + manage), plus deux
* permissions dediees a l'onglet Comptabilite et a l'archivage
* (cf. spec-back M1 § 2.7).
*
* @return array<int, array{code: string, label: string}>
*/
public static function permissions(): array
{
return [
['code' => 'commercial.clients.view', 'label' => 'Voir les clients'],
['code' => 'commercial.clients.manage', 'label' => 'Créer / modifier les clients (hors onglet Comptabilité)'],
['code' => 'commercial.clients.accounting.view', 'label' => 'Voir l\'onglet Comptabilité d\'un client'],
['code' => 'commercial.clients.accounting.manage', 'label' => 'Modifier l\'onglet Comptabilité d\'un client'],
['code' => 'commercial.clients.archive', 'label' => 'Archiver / restaurer un client'],
];
}
} }
@@ -186,6 +186,15 @@ final class SeedE2ECommand extends Command
'sites.bypass_scope', 'sites.bypass_scope',
'catalog.categories.view', 'catalog.categories.view',
'catalog.categories.manage', 'catalog.categories.manage',
// Commercial — Repertoire clients (M1). Mappe ici sur le
// persona "tout" en attendant les vrais roles metier
// (bureau/compta/commerciale/usine) seedes par ERP-74.
// Miroir de frontend/tests/e2e/_fixtures/personas.ts.
'commercial.clients.view',
'commercial.clients.manage',
'commercial.clients.accounting.view',
'commercial.clients.accounting.manage',
'commercial.clients.archive',
], ],
], ],
[ [