Application de réconciliation des paiements fournisseurs pour les grands comptes de la grande distribution. Génère des écritures comptables au format MyUnisoft à partir des exports de paiement des enseignes.
Prérequis : Python 3.11+
pip install flask
python app.pyOu double-cliquer sur run.bat.
Accès : http://localhost:5000
En production, l'application tourne sur le serveur Docker à
https://grandpayeur.nxtfood.local(serveur test :10.0.10.130)
- Charger la base VIF — export VIF interne qui fait le lien entre chaque numéro de facture et le code magasin/compte comptable
- Importer les fichiers de paiement — exports fournis par l'enseigne (CSV, XLS, XLSX)
- Analyser — l'app rapproche les factures, groupe par virement, détecte les écarts
- Exporter — téléchargement d'un CSV prêt à importer dans MyUnisoft
| Enseigne | Filtre automatique |
|---|---|
| Auchan | Suppression des lignes "Paiement à échéance" |
| Carrefour | — |
| E.Leclerc | — |
| Casino | — |
| Intermarché | — |
Chaque rôle accepte plusieurs variantes de noms de colonnes. Si la détection automatique échoue, une erreur "Colonnes manquantes" s'affiche.
Filtre automatique : lignes
Type de paiement = "Paiement à échéance"supprimées
| Rôle | Variantes acceptées |
|---|---|
| Ref facture | Référence, Reference, Reference du fournisseur, Ref fournisseur, Reference fournisseur |
| Montant | Montant, Montant appliqué, Montant applique, Montant facture |
| Montant partiel | Montant de paiement, Montant du paiement, Montant paiement |
| Ref paiement | Num. transaction, Num transaction, Numero transaction, Reference du paiement, Reference paiement, Ref paiement |
| Date paiement | Date de paiement, Date paiement |
| Statut | Statut, Status, Etat |
| Rôle | Variantes acceptées |
|---|---|
| Ref facture | Numéro, Numero, No Facture Fournisseur, Numero facture fournisseur, Reference fournisseur |
| Montant | Montant, Montant Facture, Montant HT |
| Ref paiement | Référence de paiement, Reference de paiement, Reference Virement, Ref virement |
| Date paiement | Date de paiement, Date Reglement, Date reglement, Date virement |
| Statut | Statut du réglement, Statut du reglement, Etat, Statut |
| Rôle | Variantes acceptées |
|---|---|
| Ref facture | Num piece, Num Piece Fournisseur, Reference piece, Numero piece |
| Montant | Montant piece, Montant |
| Montant partiel | Montant paiement, Montant du paiement, Montant virement |
| Ref paiement | Reference paiement, Ref paiement, Num virement |
| Date paiement | Date paiement, Date du paiement |
| Statut | Statut, Status, Etat |
| Rôle | Variantes acceptées |
|---|---|
| Ref facture | Numero de facture, Facture N, Ref facture fournisseur, Numero facture |
| Montant | Montant facture, Montant TTC, Montant |
| Montant partiel | Montant paye, Montant du virement, Montant virement |
| Ref paiement | Numero de virement, Numero virement, Ref virement |
| Date paiement | Date de virement, Date virement, Date de paiement |
| Statut | Statut, Status, Etat |
| Rôle | Variantes acceptées |
|---|---|
| Ref facture | N Facture, Numero facture, Num facture fournisseur, Ref doc fournisseur |
| Montant | Montant facture, Montant, Valeur facture |
| Montant partiel | Montant paye, Montant virement, Montant reglement |
| Ref paiement | Reference virement, N virement, Num virement |
| Date paiement | Date virement, Date de reglement, Date paiement |
La base VIF est l'export interne qui contient la correspondance numéro de facture → code magasin.
Format attendu (colonnes minimales) :
Facture— numéro de facture fournisseurFacturé à(ou variante) — code/libellé du magasin
Comportement :
- La base est stockée dans une base SQLite (
vif.db) côté serveur - Elle est partagée entre tous les clients
- Chaque nouvel upload fusionne avec la base existante (nouvelles factures ajoutées, existantes mises à jour)
- Le bouton Réinitialiser vide complètement la base
JournalCode;EcritureDate;CompteNum;EcritureLib;Piece 1;Piece 2;Debit;Credit;Auxiliaire;DateEcheance;LibelleCompte;CodeLettrage
Une ligne par facture (compte 411XXX) + une ligne de contrepartie (compte banque ou client central).
Appliquées dans csvLine par ordre de priorité sur Piece 1 :
| Condition sur Piece 1 | CompteNum | Enseigne concernée |
|---|---|---|
Commence par 2025 ou 2026 |
401INTERDIS |
Toutes |
Commence par FOP |
401CARREFO0 |
Carrefour |
Commence par DOI ou ADI |
411CARRLITI |
Carrefour |
Commence par H, P, Q, R ou I |
401EURAUCHA |
Auchan |
Égal à 10 |
411AUCHLITI |
Auchan |
| Autre | Compte du VIF | — |
compta_facture/
├── index.html # Application frontend (bundle standalone)
├── app.py # Backend Flask + API SQLite
├── requirements.txt # Dépendances Python
├── vif.db # Base SQLite (créée automatiquement)
├── Dockerfile
├── docker-compose.yml # Flask + oauth2-proxy
├── grandpayeur-nginx.conf # Config nginx avec SSO (auth_request)
└── run.bat # Lancement en local (Windows)
Flux de requête (production) :
Browser → nginx (HTTPS) → auth_request → oauth2-proxy → Microsoft login
↓ authentifié
Flask :5000
API Flask :
| Méthode | Route | Description |
|---|---|---|
| GET | /api/vif |
Charger la base VIF |
| POST | /api/vif |
Sauvegarder/fusionner la base VIF |
| DELETE | /api/vif |
Réinitialiser la base VIF |
Prérequis : Python 3.11+
# Installer les dépendances
pip install flask
# Lancer l'application
python app.pyOu double-cliquer sur run.bat.
Accès : http://localhost:5000
Prérequis : Docker + Docker Compose installés sur le serveur
- Docker + Docker Compose v2 installés
- nginx installé
- Fichier
.envcréé dans~/compta_facture/avec les secrets Azure AD (voir CLAUDE.md) - Certificat SSL pour
grandpayeur.nxtfood.local(auto-signé ou CA interne)
SERVER="farid@10.0.10.130"
DST="~/compta_facture/"
scp Dockerfile docker-compose.yml app.py requirements.txt index.html grandpayeur-nginx.conf $SERVER:$DSTssh farid@10.0.10.130
cd ~/compta_facture
sudo docker compose up -dsudo cp ~/compta_facture/grandpayeur-nginx.conf /etc/nginx/conf.d/grandpayeur.conf
sudo nginx -t && sudo nginx -s reloadURL : https://grandpayeur.nxtfood.local (authentification Microsoft requise)
La base VIF est stockée dans un volume Docker persistant (grandpayeur_compta_data) — elle survit aux redémarrages et rebuilds.
| Ce qui a changé | Fichier(s) à pousser |
|---|---|
| Interface / logique client (colonnes, règles comptables) | index.html |
| API backend (routes Flask, SQLite) | app.py |
| Ports, volumes, réseau Docker | docker-compose.yml |
| Config nginx (reverse proxy) | grandpayeur-nginx.conf |
| Nouvelles dépendances Python | requirements.txt + Dockerfile |
patch_bundle.pytourne uniquement en local. Il modifieindex.htmlsur ton poste. C'est ce fichier déjà patché que tu pousses sur le serveur —patch_bundle.pyn'a pas besoin d'exister sur le serveur.
# 1. (Si modification de index.html) Appliquer les patches en local
python3 patch_bundle.py
# 2. Pousser le ou les fichiers modifiés
scp /home/faridigouti/projets/compta_facture/index.html farid@10.0.10.130:~/compta_facture/
# 3. Rebuilder le container
ssh farid@10.0.10.130 "cd ~/compta_facture && sudo docker compose up -d --build"
# 4. Si nginx modifié
scp .../grandpayeur-nginx.conf farid@10.0.10.130:~/compta_facture/
ssh farid@10.0.10.130 "sudo cp ~/compta_facture/grandpayeur-nginx.conf /etc/nginx/conf.d/grandpayeur.conf && sudo nginx -s reload"Les colonnes et paramètres par client sont définis dans index.html (objet CLIENTS). Toute modification passe par le script patch_bundle.py qui extrait, modifie et ré-encode le bundle correctement.
python patch_bundle.pyLes patches sont idempotents : relancer le script ne casse rien si les patches sont déjà appliqués.
| Problème | Cause probable | Solution |
|---|---|---|
| "Colonnes manquantes" | Noms de colonnes non reconnus | Ajouter les variantes dans la config client |
| Factures "INCONNU" | Factures absentes de la base VIF | Charger un VIF plus complet |
| Site inaccessible | Container arrêté | sudo docker compose up -d |
| Base VIF perdue | Volume Docker supprimé | Recharger le fichier VIF depuis l'interface |
| Redirection SSO en boucle | Cookie de session invalide | Vider les cookies du navigateur |
502 sur /oauth2/callback |
Buffer nginx trop petit | Vérifier proxy_buffer_size 32k dans nginx |
| Erreur Azure AADSTS54005 | Code OAuth déjà utilisé (double requête) | Réessayer en navigation privée |