---
suivi: 1878
date: 2026-10-14
sujet: Facture rejetée encore en tâche de virement
chantier: factures / mes tâches
type: correctif
statut: poussé
hash: 4df74badf
fichiers:
  - app/Services/FactureVirementExecuteService.php
  - app/Http/Controllers/FactureController.php
  - app/Http/Controllers/ValidationController.php
  - app/Services/FactureComptabilisationRejetService.php
  - app/Services/FactureSuperAdminCorrectionService.php
  - app/Services/DepotReglementStatutService.php
  - app/Services/Tasks/VirementAExecuterTaskSync.php
  - app/Services/FactureExtourneSageConstatService.php
  - app/Models/Task.php
  - app/Http/Controllers/MesTachesController.php
  - app/Services/MesTachesResumeService.php
  - app/Console/Commands/FermerTachesFacturesRejeteesCommand.php
  - tests/Unit/FactureRejeteeTacheVirement1878Test.php
  - database/data/journal_mises_a_jour_post_2026_06_12.php
  - docs/suivi/SUIVI_1878_facture_rejetee_tache_virement.md
---

# SUIVI #1878 — facture rejetée hors file de virement

## Fiches lues

- #1871 (4fadefb34, sur origin/main) : la levée automatique des tâches foncières passe par `TacheLeveeAutomatiqueService`. Leçon retenue : ne pas modifier cette classe. Le filet Mes tâches s’ajoute au contrôleur et au résumé, pas au moteur de levée.
- #1620 : `peutMarquer` et la fiche n’avaient pas la même garde. Leçon retenue : la fiche appelle `peutMarquerPourUser`, comme la liste.
- #1876 est poussé (b08c83b91). Aucun `.vue` n’est modifié : pas de rebuild.

Le diagnostic #1875 n’est pas dans `docs/suivi/`.

## PROMPT ENVOYÉ

Une facture rejetée sort de toute file de tâches de paiement. Elle ne propose ni « Virement exécuté » ni le sélecteur de règlement, y compris pour l’administration. Une extourne ne ressuscite pas une facture rejetée et ne la marque pas payée. Un payé confirmé Sage ne recule jamais. Les quatre chemins de rejet ferment la tâche de virement. Commande `factures:fermer-taches-rejetees` en simulation par défaut. Aucun appel Sage. Aucune lecture de la base de production.

## SYNTHÈSE

La fiche utilise `peutMarquerPourUser`. `peutMarquer` et `executer` refusent une facture rejetée avant toute écriture (`skipped_rejetee`, HTTP 422). Le sélecteur À régler est invisible et refusé, y compris Admin ERP, dès que la facture ou le dépôt est rejeté.

Les quatre rejets (fiche, validation, comptabilisation, forçage d’étape vers rejetée) appellent `closeForFacture` avec `rejet_erp`. Le forçage n’écrit toujours pas `rejet_at`.

La synchro ne crée plus de tâche de virement si la facture ou le dépôt est rejeté, avant l’appel Graph. Mes tâches et le compteur du résumé excluent les tâches ouvertes dont la facture est rejetée. La levée #1871 n’est pas touchée.

Le constat d’extourne refuse une facture rejetée : `applied` faux, statut inchangé, aucun champ de paiement écrit.

La commande liste les tâches `nouveau`, `en_cours` et `non_realise` rattachées à une facture rejetée. `--appliquer` ne met à jour que `statut`, `closed_reason`, `auto_closed` et `closed_at`.

### Mapping

| Libellé affiché | Valeur | Colonne | Garde |
| --- | --- | --- | --- |
| Virement exécuté | POST virement | `etat_paiement_sage` | refusé si `factures.statut` = rejetee |
| À régler | sélecteur règlement | `depot_factures.deja_reglee` | invisible et refusé si facture ou dépôt rejeté |
| Tâche de virement | fermeture | `tasks.statut` = annule, `closed_reason` = rejet_erp | les quatre rejets et la commande |

## DÉPLOIEMENT-TEST

```
git pull origin main
php artisan optimize:clear
php artisan view:clear
php artisan journal:sync
php artisan factures:fermer-taches-rejetees
php artisan factures:fermer-taches-rejetees --appliquer
```

Pas de migration. Pas de rebuild. Ne pas lancer npm sur le serveur. La commande n’appelle pas Sage. La lancer d’abord sans option (liste), puis avec `--appliquer` après lecture de la liste.

Tests locaux : `FactureRejeteeTacheVirement1878Test` et `FoncierTacheLevee1871Test` : OK (9 tests, 95 assertions). `php artisan journal:controler` : Journal conforme : 281 entrées. `pdo_sqlite` est absent : pas de test HTTP avec base. Les gardes (refus, sources des quatre chemins, filet, commande) sont verrouillées sans base.

## LEÇON

`closeForFacture` ne voit que les tâches `nouveau` et `en_cours`. Une tâche `non_realise` se ferme par la commande. L’override Admin du règlement doit être court-circuité avant lui dès qu’il y a rejet. Une extourne sur une facture encore en « paiement disponible » mais rejetée ne doit pas la ramener en comptabilisée. `upsertForFacture` retourne avant l’appel Graph.
