feat(erp): enregistrer les charges sociales — script + runbook rationalisés #84

Merged
arcodange merged 1 commits from arcodange/prod-apply into main 2026-08-13 17:27:44 +02:00
Owner

Dolibarr n'expose aucune API REST pour les charges sociales (/taxes, /socialcontributions, /chargesociales répondent tous « API not found »). Le module est actif, seule l'API manque : le pipeline de promotion, qui parle REST, ne peut pas porter cette opération. D'où un script UI, gardé par guard.ts.

La sandbox a joué son rôle : quatre doublons y ont été créés pendant la découverte, sans conséquence, et les quatre pièges du formulaire sont désormais documentés au lieu d'être redécouverts à chaque fois.

Ce qui lande

  • recordSocialCharge.ts — idempotent (cherche la charge avant de créer), vérifie par lecture de la liste, type TNS par défaut, --dry-run.
  • RUNBOOK_charges_sociales.md — écrit pour être suivi par un agent moins performant ou un harness limité : la commande, les garanties, les quatre pièges, et ce que le script ne garantit pas (ni juge indépendant, ni artefact de gate).

Les quatre pièges, tous rencontrés

  1. La date visible est décorative. Le backend ne lit que les champs cachés echday/echmonth/echyear. Remplir le champ texte crée quand même l'enregistrement, avec une période aberrante (20/06/2000 observé) — il n'échoue pas, il ment.
  2. Le bouton de soumission n'a pas d'attribut name — le cibler par value.
  3. L'URL après soumission ne porte pas d'id : vérifier par l'URL fait conclure à un échec sur une création réussie. C'est exactement ce qui a produit les quatre doublons.
  4. Les milliers portent une espace insécable (« 1 215,00 ») : une comparaison littérale casse au-delà de 999 € et l'idempotence saute en silence.

Correction comptable : 645 → 646

Les cotisations d'un gérant TNS sont des cotisations personnelles du dirigeant (646), pas des cotisations patronales sur salaires (645) — Arcodange n'a aucun salarié, le 645 doit rester vide. L'annotation de known-patterns.json disait « account 645x ».

Dans Dolibarr cela se pilote par le type de charge : Securite sociale des indépendants (URSSAF) et non Securite sociale (URSSAF / MSA).

⚠️ Reste à vérifier dans Configuration → Dictionnaires que le type « indépendants » porte bien le code comptable 646 : sinon le bon type enverra quand même l'écriture au mauvais compte.

Appliqué en production

Les trois échéances URSSAF 2026, toutes impayées : 493,00 (22/05) · 1 215,00 (05/08) · 1 333,00 (05/11) = 3 041,00 €.

🤖 Generated with Claude Code

https://claude.ai/code/session_01VRShc4QhLLU73FLHx9vskh

Dolibarr **n'expose aucune API REST** pour les charges sociales (`/taxes`, `/socialcontributions`, `/chargesociales` répondent tous « API not found »). Le module est actif, seule l'API manque : le pipeline de promotion, qui parle REST, ne peut pas porter cette opération. D'où un script UI, gardé par `guard.ts`. **La sandbox a joué son rôle** : quatre doublons y ont été créés pendant la découverte, sans conséquence, et les quatre pièges du formulaire sont désormais documentés au lieu d'être redécouverts à chaque fois. ## Ce qui lande - **`recordSocialCharge.ts`** — idempotent (cherche la charge avant de créer), vérifie par **lecture de la liste**, type TNS par défaut, `--dry-run`. - **`RUNBOOK_charges_sociales.md`** — écrit pour être suivi par un agent moins performant ou un harness limité : la commande, les garanties, les quatre pièges, et ce que le script **ne** garantit **pas** (ni juge indépendant, ni artefact de gate). ## Les quatre pièges, tous rencontrés 1. **La date visible est décorative.** Le backend ne lit que les champs **cachés** `echday`/`echmonth`/`echyear`. Remplir le champ texte crée quand même l'enregistrement, avec une période aberrante (`20/06/2000` observé) — il n'échoue pas, il ment. 2. Le bouton de soumission **n'a pas d'attribut `name`** — le cibler par `value`. 3. **L'URL après soumission ne porte pas d'`id`** : vérifier par l'URL fait conclure à un échec sur une création réussie. C'est exactement ce qui a produit les quatre doublons. 4. Les milliers portent une **espace insécable** (« 1 215,00 ») : une comparaison littérale casse au-delà de 999 € et l'idempotence saute en silence. ## Correction comptable : 645 → 646 Les cotisations d'un **gérant TNS** sont des cotisations **personnelles du dirigeant (646)**, pas des cotisations patronales sur salaires (645) — Arcodange n'a aucun salarié, le 645 doit rester vide. L'annotation de `known-patterns.json` disait « account 645x ». Dans Dolibarr cela se pilote par le **type de charge** : `Securite sociale des indépendants (URSSAF)` et non `Securite sociale (URSSAF / MSA)`. ⚠️ **Reste à vérifier** dans Configuration → Dictionnaires que le type « indépendants » porte bien le code comptable **646** : sinon le bon type enverra quand même l'écriture au mauvais compte. ## Appliqué en production Les **trois échéances URSSAF 2026**, toutes **impayées** : 493,00 (22/05) · 1 215,00 (05/08) · 1 333,00 (05/11) = **3 041,00 €**. 🤖 Generated with [Claude Code](https://claude.com/claude-code) https://claude.ai/code/session_01VRShc4QhLLU73FLHx9vskh
arcodange added 1 commit 2026-08-13 17:27:36 +02:00
Dolibarr n'expose AUCUNE API REST pour les charges sociales (/taxes,
/socialcontributions, /chargesociales répondent tous « API not found »). Le
module est actif, seule l'API manque : le pipeline de promotion, qui parle REST,
ne peut pas porter cette opération. D'où un script UI, gardé par guard.ts.

La sandbox a joué son rôle : quatre doublons y ont été créés pendant la
découverte, sans conséquence, et les quatre pièges du formulaire sont désormais
documentés au lieu d'être redécouverts.

- recordSocialCharge.ts : idempotent (cherche la charge avant de créer),
  vérifie par LECTURE de la liste, type TNS par défaut, --dry-run.
- RUNBOOK_charges_sociales.md : écrit pour être suivi par un agent moins
  performant ou un harness limité — la commande, les garanties, les quatre
  pièges, et ce que le script ne garantit PAS (ni juge, ni artefact de gate).

Les quatre pièges, tous rencontrés :
1. La date visible est décorative : le backend ne lit que les champs CACHÉS
   echday/echmonth/echyear. Remplir le champ texte crée l'enregistrement avec
   une période aberrante (20/06/2000 observé) au lieu d'échouer.
2. Le bouton de soumission n'a pas d'attribut name — le cibler par value.
3. L'URL après soumission ne porte pas d'id : vérifier par l'URL fait conclure
   à un échec sur une création réussie. C'est ce qui a produit les doublons.
4. Les milliers portent une espace insécable (« 1 215,00 ») : une comparaison
   littérale casse au-delà de 999 € et l'idempotence saute en silence.

Correction comptable : 645x → 646 dans known-patterns.json. Les cotisations d'un
gérant TNS sont des cotisations personnelles du dirigeant (646), pas des
cotisations patronales sur salaires (645) — Arcodange n'a aucun salarié.

Appliqué en production : les trois échéances URSSAF 2026, toutes IMPAYÉES.
Reste à vérifier dans le dictionnaire Dolibarr que le type « indépendants »
porte bien le code comptable 646.

Co-Authored-By: Claude Opus 5 (1M context) <[email protected]>
Claude-Session: https://claude.ai/code/session_01VRShc4QhLLU73FLHx9vskh
arcodange merged commit 95267784d6 into main 2026-08-13 17:27:44 +02:00
arcodange deleted branch arcodange/prod-apply 2026-08-13 17:27:45 +02:00
Sign in to join this conversation.
No Reviewers
No labels
1 Participants
Notifications
Due Date
No due date set.
Dependencies

No dependencies set.

Reference: arcodange-org/erp#84