Files
Starseed/src/Module/Commercial/Domain
matthieu 145d4362db
Auto Tag Develop / tag (push) Successful in 7s
feat(commercial) : sous-ressources M2 fournisseurs (contacts/adresses/ribs) (ERP-88) (#67)
## ERP-88 — Sous-ressources M2 (contacts / adresses / ribs)

Étape 4/7 du pipeline M2. Dépend de #86 (entités) et #87 (Provider/Processor). Bloque #92.

### Contenu
Opérations API Platform + Processors d'écriture des sous-collections du fournisseur (POST/PATCH/DELETE + GET unitaire).

**SupplierContactProcessor**
- Rattachement au fournisseur parent (404 si absent).
- Normalisation serveur RG-2.12 (Title Case nom/prénom, téléphones chiffres seuls, email lowercase).
- RG-2.04 : firstName **ou** lastName obligatoire (422 sur `firstName`).
- DELETE libre (RG-2.13 front-driven : collection peut rester vide côté back).

**SupplierAddressProcessor**
- Rattachement au fournisseur parent.
- RG-2.05 (CP `^[0-9]{4,5}$`), RG-2.06 (≥1 site), RG-2.09 (type d'adresse) portées par les contraintes d'entité (ERP-86).
- RG-2.10 (catégorie de type FOURNISSEUR) ajoutée via `Assert\Callback validateCategoryType` (propertyPath=`categories`).

**SupplierRibProcessor**
- Rattachement au fournisseur parent.
- RG-2.08 : refus du DELETE du dernier RIB quand `paymentType.code = LCR` → **409**.

### Security différenciée
| Sous-ressource | Écriture | Lecture |
|---|---|---|
| contacts / adresses | `commercial.suppliers.manage` | `commercial.suppliers.view` |
| ribs | `commercial.suppliers.accounting.manage` | `commercial.suppliers.accounting.view` |

POST en `read:false` (parent rattaché manuellement) — parade NonUniqueResult héritée du M1. Messages FR (ERP-107) + `violations[].propertyPath` aligné (ERP-101).

### Vérifications
- `make php-cs-fixer-allow-risky` : 0 fichier à corriger
- `make test` : 483 tests OK
- `debug:router` : 12 routes générées (4 par sous-ressource)

### Hors périmètre (tickets suivants)
- Déclaration RBAC `commercial.suppliers.*` dans `CommercialModule` (#7) — sans elle, l'accès reste 403.
- Tests fonctionnels de la matrice RG (#8) — dépendent du RBAC + fixtures Supplier.

### Notes de review (non bloquantes, alignées M1)
- `position` des sous-collections non exposé à l'API (décision ERP-86, géré serveur).
- M2M `SupplierAddress.contacts` non vérifié same-supplier — comportement identique au M1 (ClientAddress), à traiter globalement si besoin.

---------

Co-authored-by: Matthieu <contact@malio.fr>
Reviewed-on: #67
Co-authored-by: THOLOT DECHENE Matthieu <matthieu@yuno.malio.fr>
Co-committed-by: THOLOT DECHENE Matthieu <matthieu@yuno.malio.fr>
2026-06-08 07:31:48 +00:00
..