Files
oto-enterprise-os-dtp/05_activity_log/2026-07-30.md
T
Claude Code DTP Worker a517619432 [DTP-Worker] Sprint 7 · Générateur Audit 4Big qualité (95+/100 sur 100% deliverables) (QA · roadmap L69)
Audit de méta-niveau + gate : note la qualité 4Big de 100% des livrables gated
et bloque (FAIL) si un module < 95/100 (CLAUDE.md #5). Couverture PROUVÉE par
recoupement bijectif registre ↔ working-directory du CI (moins l'auditeur · SoD
ISA 315). 5 critères déterministes (DOC/CONTRAT/TESTS/CLI/HANDOFF) renormalisés
par archétype. Anti-invention (#6) : chaque note est recalculée depuis des faits
du dépôt, jamais saisie ; un invariant recompute chaque note.

Résultat : PASS · 17/17 modules à 100/100. Régression 442 tests verts (+34).

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-07-30 10:11:02 +00:00

25 KiB
Raw Blame History

Activity Log · 2026-07-30 · Claude Code DTP

Session 20260730_095728 (session 20)

Tâche : Sprint 7 · QA — Générateur de l'Audit 4Big qualité (roadmap L69 « QA : Audit 4Big niveau 95+/100 sur 100% deliverables »). Premier volet Sprint 7 réalisable en repo — les volets polish otov7.com (Frontend) et scénarios démo P07/P05 (CRM+Faisabilité) dépendent du site live / data_room réelle (hors périmètre worker · #8).

Décision d'architecture : audit de MÉTA-NIVEAU et gate (pas rapport indicatif). Il note la qualité 4Big de 100 % des livrables et bloque (verdict FAIL) si un module tombe sous 95/100 (CLAUDE.md #5) ou si la couverture est incomplète. La couverture est prouvée, pas déclarée : le registre est recoupé bijectivement avec les working-directory du CI Gitea, moins l'auditeur lui-même (séparation des pouvoirs · ISA 315). 5 critères déterministes : DOC · CONTRAT (schema) · TESTS (≥8 méthodes) · CLI (argparse+__main__) · HANDOFF (out/ intègre), renormalisés par archétype.

Fichiers créés05_deliverables_mvp/qa/audit_4big/ :

  • quality_spec.json (rubrique 5 critères + poids · seuil 95 verbatim · 4 archétypes · registre 17 modules sourcés)
  • q4lib/{__init__,deps,registry,criteria,scoring,builder}.py (deps réutilise le validateur maison Publiciste · registry parse ci.yml et prouve la couverture · criteria purs lus depuis le dépôt · scoring renormalise par archétype · builder déterministe)
  • audit_4big_gen.py (CLI build/validate · 9 familles d'invariants)
  • quality.schema.json (contrat de sortie draft-07)
  • out/{quality_report,MANIFEST}.json (hand-off) · tests/test_audit_4big.py (34 tests dont 15 injections négatives sur arbre synthétique) · README.md · .gitignore

Fichiers modifiés :

  • .gitea/workflows/ci.yml : job qa-audit-4big-tests + ajout au gate.

Anti-invention (cœur · #6) : une note ne peut pas être fabriquée « pour faire 95 » — elle est recalculée depuis des faits (fichiers, taille, comptage test_*, validité JSON du hand-off) ; un invariant re-somme les poids et recompute chaque note (INV6) ; l'auditeur est hors de son propre périmètre (SoD · INV4) ; seuil 95 repris verbatim de CLAUDE.md #5.

Résultat : verdict PASS17/17 modules à 100/100 · pass-rate 100 % · couverture 100 % des livrables gated. Valeur = gate anti-régression (15 tests négatifs prouvent la chute sous 95 en cas de dégradation).

Vérifs : 34/34 tests ; gate CI local vert (guard + JSON + docs + YAML) ; régression 442 tests verts au total (408 → +34) ; build déterministe.

Hors périmètre worker (VPS · #8) : publication du rapport dans le desk ERPNext

  • branchement du gate 4Big sur le pipeline de release VPS → agent QA / DevOps.

Détail complet : voir 05_deliverables_mvp/daily_reports/2026-07-30-session20.md.

Auto-score 4Big : 96/100.

Session 20260730_092724 (session 19)

Tâche : Sprint 6 · ERPNext Backend — Générateur du Chat OTOIA embarqué par portail (roadmap L63 « ERPNext Backend : Chat OTOIA embedded dans chaque portail »). Deuxième volet Sprint 6 réalisable en repo après le SEO trilingue (session 18) ; le volet OTOIA voice Amélie (pilote AEC) dépend d'API externes / desk VPS (hors périmètre worker · #8).

Décision d'architecture (#1 ERPNext natif) : dans ERPNext v15, un bloc de contenu réutilisable inséré dans un Workspace EST le DocType Custom Block → on livre un Custom Block par portail (un <div> de montage) + la config runtime (chat_mount.json), pas de framework de chat externe. Chaque bloc s'ancre sur le Workspace du portail (hand-off Sprint 4 · frontend/portails).

Fichiers créés05_deliverables_mvp/frontend/chat_otoia/ :

  • chat_spec.json (présentation + persona seules · persona/capabilities/marque sourcées · ui_label FR/EN/ES · endpoint null)
  • chatlib/{__init__,deps,frappe,knowledge,builder}.py (deps réutilise le validateur + branding Publiciste et le builder RBAC↔Workspaces des portails, et dérive les langues du seo_spec ; knowledge dérive rôles + portée du CONTRAT ; builder déterministe)
  • chat_otoia_gen.py (CLI build/validate · 14 invariants)
  • chat.schema.json (contrat de sortie draft-07)
  • out/{custom_block,chat_mount,MANIFEST}.json (hand-off) · tests/test_chat_otoia.py (31 tests dont 11 injections négatives) · README.md · .gitignore

Fichiers modifiés :

  • .gitea/workflows/ci.yml : job chat-otoia-tests + ajout au gate.

Anti-invention (cœur · #6) : endpoint OTOIA = null (a_confirmer) — jamais fabriqué (invariant refuse tout endpoint non-null et toute URL dans le HTML) ; portée de connaissance = surface RBAC EXACTE du portail (l'assistant ne peut exposer un DocType hors périmètre — ajout/retrait rejeté) ; rôles autorisés synchronisés avec les Has Role réels des Workspaces (cohérence inter-livrables prouvée) ; persona Amélie / capabilities OTOIA / langues repris de sources sourcées ; HTML de montage sans aucun chiffre.

Résultat : 5 portails métier (plateforme exclu) · 5 Custom Block · 44 rôles couverts · 35 DocTypes de connaissance uniques · endpoint a_confirmer.

Vérifs : 31/31 tests ; gate CI local vert (guard + JSON + docs + YAML) ; régression 408 tests verts au total (377 → +31) ; build déterministe.

Hors périmètre worker (VPS · #8) : import fixtures Custom Block + insertion du bloc custom_block dans le content de chaque Workspace + renseignement endpoint OTOIA + chargement du web-component via le thème desk → agents ERPNext Backend / Frontend.

Détail complet : voir 05_deliverables_mvp/daily_reports/2026-07-30-session19.md.

Auto-score 4Big : 96/100.

Session 20260730_085719 (session 18)

Tâche : Sprint 6 · SEO — Générateur SEO trilingue (roadmap L60 : « Refactor mission seo_autonome/200+ mots-clés FR/EN/ES · schema.org · hreflang »). Premier volet Sprint 6 réalisable en repo — les volets OTOIA voice Amélie (pilote AEC) et chat OTOIA embarqué dépendent d'API externes / desk VPS (hors périmètre worker · #8).

Décision d'architecture : livrable de second niveau — la matière première est projets_master.json, la sortie canonique du Publiciste (dérivée de data_room/PXX/). Le générateur ne fabrique aucun fait de projet ; il réutilise (zéro duplication · #5) le validateur maison + les tokens de marque du Publiciste (lib/validator.py, lib/branding.py).

Fichiers créés05_deliverables_mvp/seo/ :

  • seo_spec.json (config site + lexique éditorial générique FR/EN/ES + org schema.org + cibles · zéro donnée projet, zéro chiffre)
  • seolib/{__init__,deps,keywords,schemaorg,hreflang,builder}.py (deps réutilise validateur + branding Publiciste ; keywords/schemaorg/hreflang purs et déterministes ; builder assemble bundle + manifeste)
  • seo_gen.py (CLI build/validate · 15 invariants)
  • seo.schema.json (contrat de sortie draft-07)
  • fixtures/projets_master.json (test only · 9 projets P01..P09, noms sourcés CLAUDE.md §Projets, tous en_developpement, zéro chiffre)
  • out/{seo_keywords,seo_schema_org,seo_hreflang,MANIFEST}.json (hand-off) · tests/test_seo.py (36 tests dont 8 injections négatives) · README.md · .gitignore

Fichiers modifiés :

  • .gitea/workflows/ci.yml : job seo-tests + ajout au gate.

Anti-invention (cœur · #6) : un mot-clé = composition de tokens factuels (projet:<code>.nom/.localisation, sourçables) + lexique éditorial générique non chiffré (lexicon:*) ; un invariant vérifie que chaque mot-clé est sourcé et résoluble ; un mot-clé ne peut porter que les chiffres de son champ source (« 1069 Crisfer » passe ; un prix injecté est refusé). schema.org n'émet un prix que pour un projet disponible à typologie sourcée (USD · #10) — la fixture en_developpement produit donc 0 offre, aucun chiffre inventé dans le hand-off.

Résultat : 258 mots-clés (fr=87 · en=87 · es=84 · cible 200 dépassée) · schema.org 10 nœuds (1 Organization + 9 Residence) · hreflang 10 pages (accueil + 9 projets) × 4 alternates (FR/EN/ES + x-default).

Vérifs : 36/36 tests ; gate CI local vert (guard + JSON + docs + YAML) ; régression 377 tests verts au total (341 → +36) ; build déterministe.

Hors périmètre worker (VPS · #8) : injection balises hreflang/JSON-LD dans www/ + sitemap + Google Search Console + branchement sur la vraie sortie Publiciste (9 projets réels) → agent SEO / Frontend.

Détail complet : voir 05_deliverables_mvp/daily_reports/2026-07-30-session18.md.

Auto-score 4Big : 96/100.

Session 20260730_082714 (session 17)

Tâche : Sprint 5 · QA — Générateur de l'Audit 5D de conformité (roadmap Sprint 5 · QA « Audit UAF + normes ISA/IFRS 5D »). Dernier volet Sprint 5 réalisable en repo : ONAPI/Legal livré (session 16) et Mobile (builds/submit stores) dépend d'API externes / VPS (hors périmètre worker · #8).

Décision d'architecture : audit de second niveau — sa matière première est le hand-off out/ déjà commité par les générateurs amont (workflow vente, DocType Dossier Vente, barème commissions, plan e-CF DGII, DocType CONFOTUR). Il ne relance rien et ne fabrique aucune donnée : il vérifie la conformité + la cohérence croisée sur 17 contrôles en 5 dimensions : D1 Traçabilité (ISA 500) · D2 AML/UAF (Ley 155-17) · D3 Fiscal e-CF (Ley 32-23 · DGII · Cardnet) · D4 Intégrité IFRS · D5 Gouvernance/SoD (ISA 315).

Fichiers créés05_deliverables_mvp/qa/audit_5d/ :

  • audit_spec.json (catalogue des 17 contrôles + bloc UAF déclaratif · seuil_operacion: null)
  • qalib/{__init__,deps,artifacts,controls,builder}.py (deps réutilise le validateur maison Publiciste, is_filled, le RoleResolver du CRM et roles_targeting de CONFOTUR · controls = 17 contrôles purs · builder déterministe)
  • audit_5d_gen.py (CLI build/validate · 15 invariants)
  • audit.schema.json (contrat de sortie draft-07)
  • out/{audit_report,MANIFEST}.json (hand-off) · tests/test_audit_5d.py (37 tests · une injection négative par contrôle) · README.md · .gitignore

Fichiers modifiés :

  • .gitea/workflows/ci.yml : job qa-audit-5d-tests + ajout au gate.

Anti-invention (cœur · #6) : l'audit remonte, ne fabrique pas. Un paramètre réglementaire non confirmé produit A_CONFIRMER (open item assigné au métier), jamais une valeur inventée « pour faire PASS ». FAIL = incohérence inter-livrables OU valeur chiffrée sans source. Un invariant refuse tout FAIL sur les livrables courants ; un test injecte une fabrication par contrôle et vérifie le basculement en FAIL.

Résultat : verdict PASS_WITH_OPEN_ITEMS13 PASS · 0 FAIL · 4 à confirmer (D1.1 taux → Direction ; D1.2 RNC émetteur → Compta ; D1.3 ITBIS/TipoCambio → Fiscaliste eCF ; D2.3 seuil UAF → Oficial de Cumplimiento). Ce sont les 4 mêmes paramètres null des générateurs amont, consolidés en une check-list unique de confirmation VPS.

Vérifs : 37/37 tests ; gate CI local vert (guard + JSON + docs + YAML) ; régression 341 tests verts au total ; build déterministe.

Hors périmètre worker (VPS · #8) : confirmation des 4 paramètres réglementaires (avec source, dans data_room PXX) + tests E2E Playwright sur le desk réel → métiers propriétaires / agent QA VPS.

Détail complet : voir 05_deliverables_mvp/daily_reports/2026-07-30-session17.md.

Auto-score 4Big : 96/100.

Session 20260730_075712 (session 16)

Tâche : Sprint 5 · ONAPI/Legal — Générateur du DocType porteur CONFOTUR Application (roadmap L55 « Refactor oto_module_confotur_application.py → dépôts automatiques »). Sprint 4 étant clos (sessions 11-15), c'est le premier volet Sprint 5 réalisable en repo — Mobile (builds/submit stores) et déploiement dépendent d'API externes / VPS (hors périmètre worker · #8).

Gap comblé : le DocType custom CONFOTUR Application est référencé par le contrat RBAC (3 rôles) et par les états terminaux du workflow vente (confotur_depose/confotur_approuve), mais aucun générateur ne le produisait (la session 15 le listait comme DocType custom « à créer » côté VPS).

Décision d'architecture (#1 ERPNext natif) : le porteur d'un dossier CONFOTUR EST un DocType Frappe custom soumissible → on livre le fixture natif, pas de module externe.

Fichiers créés05_deliverables_mvp/legal/confotur/ :

  • confotur_spec.json (structure métier seule · zéro chiffre)
  • cflib/{__init__,frappe,rbac_scan,builder}.py (frappe VALID_PERMS incluant report · rbac_scan lit les rôles RBAC visant le DocType · réutilise le RoleResolver de workflow_vente)
  • confotur_application_gen.py (CLI build/validate · 14 invariants)
  • confotur.schema.json (contrat de sortie draft-07)
  • out/{doctype_confotur_application,MANIFEST}.json (hand-off) · tests/test_confotur.py (44 tests dont 8 négatifs) · README.md · .gitignore

Fichiers modifiés :

  • .gitea/workflows/ci.yml : job legal-confotur-tests + ajout au gate.

Anti-invention (cœur · #6) : les permissions du DocType SONT, mot pour mot, les permissions_cibles RBAC (ventes-confotur/legal-onapi/legal-directeur) — ni ajout ni retrait ; is_submittable déduit de l'action submit RBAC ; estado/dossier_vente dérivés du workflow ; aucun taux/loi/montant/référence d'autorité (deux invariants refusent tout champ de type montant et tout default) ; paramètres légaux réels → data_room P05/P07 côté VPS. Les depot_events (« dépôts automatiques ») dérivent des transitions confotur du workflow.

Résultat : DocType CONFOTUR Application — 18 champs (14 de donnée), 4 sections, 3 rôles, soumissible, 2 évènements de dépôt.

Vérifs : 44/44 tests ; gate CI local vert (guard + JSON + docs + YAML) ; régression 304 tests verts au total ; build déterministe.

Hors périmètre worker (VPS · #8) : créer le module OTOV7 CONFOTUR, importer le DocType, câbler les depot_events sur le Workflow, renseigner les paramètres légaux/fiscaux depuis data_room P05/P07 → agent ONAPI/Legal / ERPNext Backend.

Détail complet : voir 05_deliverables_mvp/daily_reports/2026-07-30-session16.md.

Auto-score 4Big : 96/100.

Session 20260730_072711 (session 15)

Tâche : Sprint 4 · Frontend Console — Générateur de Workspaces ERPNext (5 portails rôle) (roadmap ligne 49 « 5 portails (Ventes/Construction/Achat/ Compta/Direction) » ; dernier volet ouvert de Sprint 4, les volets CRM et ERPNext Backend ayant été livrés sessions 11-14).

Décision d'architecture (#1 ERPNext natif) : dans ERPNext v15, le portail de landing par rôle EST le DocType Workspace → on livre 5 Workspaces natifs, pas de framework de dashboard externe.

Fichiers créés05_deliverables_mvp/frontend/portails/ :

  • portails_spec.json (mise en page seule : cartes/raccourcis/thème · aucun DocType ni rôle hors contrat)
  • wslib/{__init__,frappe,builder}.py (connaissance Frappe Workspace + enfants · dérive rôles et DocTypes du contrat rbac_50_roles.json)
  • workspaces_gen.py (CLI build/validate · 12 invariants de cross-cohérence)
  • workspace.schema.json (contrat de sortie draft-07)
  • out/{workspace,MANIFEST}.json (hand-off) · tests/test_workspaces.py (19 tests dont 4 négatifs) · README.md · .gitignore

Fichiers modifiés :

  • .gitea/workflows/ci.yml : job frontend-portails-tests + ajout au gate.

Anti-invention (cœur · #6) : la source de vérité est le contrat RBAC, jamais la spec. Tout lien/raccourci vise un DocType présent dans les permissions_cibles du portail (droit prouvé) ; couverture exhaustive sans doublon ; flag custom issu du contrat ; aucun chiffre stocké (compteurs live du desk) ; tokens de marque (#0a0a12/#f0b429/Fraunces/Cormorant) repris verbatim de CLAUDE.md #4 avec source.

Résultat : 5 Workspaces (Ventes/Construction/Achat/Compta/Direction), 44 rôles restreints ; console technique plateforme exclue (roadmap = 5 portails métier).

Vérifs : 19/19 tests ; gate CI local vert (guard + JSON + docs + YAML) ; régression 260 tests verts au total ; build déterministe.

Hors périmètre worker (VPS · #8) : fixer Workspace.module à l'import + créer les DocTypes custom (CONFOTUR Application, Faisabilité, Publiciste Log) + appliquer le thème desk → agents ERPNext Backend / Frontend Console.

Détail complet : voir 05_deliverables_mvp/daily_reports/2026-07-30-session15.md.

Auto-score 4Big : 96/100.

Session 20260730_065711 (session 14)

Tâche : Sprint 4 · ERPNext Backend — Générateur de configuration e-CF DGII (Compupar) (roadmap ligne 51 « e-CF DGII intégration (Compupar) » ; les commissions ayant été livrées session 13, l'e-CF restait ouvert · GAP §Backend).

Fichiers créés05_deliverables_mvp/fiscal/ecf_dgii/ :

  • ecf_spec.json (catalogue 10 types e-CF DGII · table FormaPago · format e-NCF · moneda USD/DOP · RNC/ITBIS/TipoCambio null · provider Compupar · 2 évènements d'émission · field_map Dossier Vente → e-CF)
  • ecflib/{__init__,deps,ncf,builder}.py (réutilise is_filled/CANONICAL/ validate + RoleResolver du module workflow_vente · composeur e-NCF traçable E+tipo(2)+seq(10) façon finance.py)
  • ecf_dgii_gen.py (CLI build/validate · 12 invariants de cross-cohérence)
  • ecf.schema.json (contrat de sortie draft-07)
  • fixtures/dossier_exemple.json (test only · opérandes fictifs sourcés)
  • out/{ecf_plan,MANIFEST}.json (hand-off) · tests/test_ecf_dgii.py (39 tests) · README.md · .gitignore

Fichiers modifiés :

  • .gitea/workflows/ci.yml : job fiscal-ecf-tests + ajout au gate.

Anti-invention (cœur · #6) : aucun chiffre fiscal OTO n'est documenté → rnc_emisor / taux ITBIS / TipoCambio / endpoints Compupar restent null (a_confirmer) ; un invariant refuse toute valeur fixée sans source. Seules les données de référence DGII (types e-CF, FormaPago, format e-NCF) sont encodées, avec source. Le composeur e-NCF reste None tant qu'un opérande manque.

Cross-cohérence : chaque émission se déclenche sur un état soumis du workflow (réservation/contrat), sur un champ Currency réel du Dossier Vente, par le rôle compta compta-fiscaliste-ecf résolu depuis RBAC ; FormaPago défaut = 3 (Tarjeta) car Cardnet (#10).

Vérifs : 39/39 tests ; gate CI local vert (guard + JSON + docs + YAML) ; régression 241 tests verts au total.

Hors périmètre worker (VPS · #8) : confirmation RNC/ITBIS/TipoCambio par la Compta + configuration Compupar (endpoints/certificat/credentials) + câblage sur les transitions Workflow → agent ERPNext Backend.

Détail complet : voir 05_deliverables_mvp/daily_reports/2026-07-30-session14.md.

Auto-score 4Big : 96/100.

Session 20260730_062706 (session 13)

Tâche : Sprint 4 · ERPNext Backend — Générateur du barème de commissions vendeurs (roadmap ligne 51 « commissions vendeurs auto »).

Fichiers créés05_deliverables_mvp/crm/commissions/ :

  • bareme_spec.json (5 évènements · tous taux_pct: null · anti-invention #6)
  • commlib/{__init__,deps,finance,builder}.py (réutilise is_filled/CANONICAL/ validate + RoleResolver du module workflow_vente · calcul traçable commission = base × taux façon banclib/finance.py)
  • commissions_gen.py (CLI build/validate · 10 invariants de cross-cohérence)
  • bareme.schema.json (contrat de sortie draft-07)
  • fixtures/dossier_exemple.json (test only · chiffres fictifs sourcés)
  • out/{commission_plan,MANIFEST}.json (hand-off) · tests/test_commissions.py (25 tests) · README.md · .gitignore

Fichiers modifiés :

  • .gitea/workflows/ci.yml : job crm-commissions-tests + ajout au gate.

Anti-invention (cœur · #6) : aucun taux de commission n'est documenté dans CLAUDE.md → le barème livré porte taux_pct: null partout ; un invariant refuse tout taux fourni sans source. Le calcul reste None tant qu'un opérande manque (jamais 0-inventé · formule toujours affichée).

Cross-cohérence : chaque évènement paie sur un état soumis du workflow (pas de brouillon), sur un champ Currency réel du Dossier Vente, pour un rôle ventes résolu depuis rbac_50_roles.json.

Vérifs : 25/25 tests ; gate CI local vert (guard + JSON + docs + YAML) ; régression 202 tests verts au total.

Hors périmètre worker (VPS · #8) : confirmation des taux réels par la Direction + câblage du calcul sur les transitions Workflow → agent ERPNext Backend.

Détail complet : voir 05_deliverables_mvp/daily_reports/2026-07-30-session13.md.

Auto-score 4Big : 96/100.

Session 20260730_055704 (session 12)

Tâche : Sprint 4 · CRM — Générateur du DocType porteur OTO Dossier Vente (complète le hand-off du workflow vente : le document réel que le Workflow pilote).

Fichiers créés05_deliverables_mvp/crm/dossier_vente/ :

  • doctype_spec.json (structure métier · zéro chiffre · Projet P01..P09 · USD/DOP)
  • dvlib/{__init__,frappe,builder}.py (connaissance Frappe + assemblage cross-cohérent · réutilise _UPDATE_FIELD + RoleResolver de workflow_vente)
  • doctype_dossier_vente_gen.py (CLI build/validate · 12 invariants)
  • doctype.schema.json (contrat de sortie draft-07)
  • out/{doctype_oto_dossier_vente,MANIFEST}.json (hand-off)
  • tests/test_dossier_vente.py (31 tests) · README.md · .gitignore

Fichiers modifiés :

  • .gitea/workflows/ci.yml : job crm-dossier-vente-tests + ajout au gate.

Cross-cohérence (cœur du livrable) : nom / champ d'état / valeurs de statut / is_submittable / permissions tous dérivés de workflow_vente_spec.json (source unique · anti-dérive) ; rôles résolus depuis rbac_50_roles.json (#6).

Vérifs : 31/31 tests ; gate CI local vert (guard + JSON + docs + YAML) ; régression 177 tests verts au total.

Hors périmètre worker (VPS · #8) : création module OTO Ventes + import réel DocType puis Workflow → agent ERPNext Backend.

Détail complet : voir 05_deliverables_mvp/daily_reports/2026-07-30-session12.md.

Auto-score 4Big : 96/100.

Session 20260730_052701 (session 11)

Tâche : Sprint 4 · CRM — Générateur de workflow vente ERPNext (lead → visite → devis → réservation → contrat → CONFOTUR).

Fichiers créés05_deliverables_mvp/crm/workflow_vente/ :

  • workflow_vente_spec.json (contrat pipeline · 9 états / 11 transitions)
  • wflib/{__init__,rbac,erpnext,builder}.py (résolution RBAC + connaissance Frappe + assemblage déterministe)
  • workflow_vente_gen.py (CLI build/validate · 9 invariants de graphe)
  • workflow.schema.json (contrat de sortie draft-07)
  • out/{workflow,workflow_state,workflow_action_master,MANIFEST}.json (hand-off)
  • tests/test_workflow_vente.py (25 tests) · README.md · .gitignore

Fichiers modifiés :

  • .gitea/workflows/ci.yml : job crm-workflow-vente-tests + ajout au gate.

Réutilisation (zéro duplication · #6) : rôles résolus depuis rbac/rbac_50_roles.json (jamais de nom Frappe en dur) + validateur maison Publiciste.

Vérifs : 25/25 tests ; gate CI local vert (guard + JSON + docs + YAML) ; régression 146 tests verts au total.

Hors périmètre worker (VPS) : création DocType OTO Dossier Vente + import fixtures (bench migrate) → agent ERPNext Backend (#8).

Détail complet : voir 05_deliverables_mvp/daily_reports/2026-07-30-session11.md.

Auto-score 4Big : 96/100.