From 3ec0eb8d89fab65c14f0b767b1494108c99d403e Mon Sep 17 00:00:00 2001 From: vdorge Date: Mon, 25 Aug 2025 11:14:41 +0000 Subject: [PATCH] Supprimer FK_POLICIES.md --- FK_POLICIES.md | 142 ------------------------------------------------- 1 file changed, 142 deletions(-) delete mode 100644 FK_POLICIES.md diff --git a/FK_POLICIES.md b/FK_POLICIES.md deleted file mode 100644 index 3be63b3..0000000 --- a/FK_POLICIES.md +++ /dev/null @@ -1,142 +0,0 @@ - -# FK_POLICIES.md -**Politique des clés étrangères (ON DELETE / ON UPDATE)** – Sprint 1 - -## 🎯 Objectif -Documenter, de façon unique et partagée, les règles de suppression/mise à jour appliquées aux **clés étrangères** de la base P’titsPas pour : -- préserver l’**intégrité référentielle** ; -- conserver l’**historique** utile (messages, événements…) ; -- respecter les exigences **RGPD** (suppression en cascade lorsque pertinent). - -> Par défaut, **ON UPDATE = NO ACTION** (UUID immuables). -> Ce document couvre **ON DELETE** table par table. - ---- - -## 🧭 Principes généraux - -- **CASCADE** quand la donnée fille **n’a pas de sens sans le parent** - (ex. `dossiers` d’un parent, `avenants` d’un contrat). -- **SET NULL** quand on veut **préserver l’historique** mais que le référent peut disparaître - (ex. auteur d’un message supprimé, créateur d’un événement). -- **RESTRICT/NO ACTION** non utilisé ici pour éviter des blocages au nettoyage. - ---- - -## 📚 Récapitulatif rapide (matrice) - -| Table (colonne FK) → Référence | ON DELETE | Raison | -|---|---:|---| -| **assistantes_maternelles(id_utilisateur)** → `utilisateurs(id)` | **CASCADE** | Profil AM supprimé avec son compte | -| **parents(id_utilisateur)** → `utilisateurs(id)` | **CASCADE** | Extension parent supprimée avec son compte | -| **parents(id_co_parent)** → `utilisateurs(id)` | **SET NULL** | Conserver le parent principal si co-parent disparaît | -| **enfants_parents(id_parent)** → `parents(id_utilisateur)` | **CASCADE** | Nettoyage liaisons N:N | -| **enfants_parents(id_enfant)** → `enfants(id)` | **CASCADE** | Idem | -| **dossiers(id_parent)** → `parents(id_utilisateur)` | **CASCADE** | Dossier n’a pas de sens sans parent | -| **dossiers(id_enfant)** → `enfants(id)` | **CASCADE** | Dossier n’a pas de sens sans enfant | -| **messages(id_dossier)** → `dossiers(id)` | **CASCADE** | Messages détruits avec le dossier | -| **messages(id_expediteur)** → `utilisateurs(id)` | **SET NULL** | Garder l’historique des échanges | -| **contrats(id_dossier)** → `dossiers(id)` | **CASCADE** | 1:1, contrat détruit si dossier supprimé | -| **avenants_contrats(id_contrat)** → `contrats(id)` | **CASCADE** | Avenants détruits avec le contrat | -| **avenants_contrats(initie_par)** → `utilisateurs(id)` | **SET NULL** | Historiser l’avenant sans bloquer | -| **evenements(id_enfant)** → `enfants(id)` | **CASCADE** | Événements n’ont plus de sens | -| **evenements(id_am)** → `utilisateurs(id)` | **SET NULL** | Garder la trace même si AM supprimée | -| **evenements(id_parent)** → `parents(id_utilisateur)` | **SET NULL** | Garder la trace si parent supprimé | -| **evenements(cree_par)** → `utilisateurs(id)` | **SET NULL** | Conserver l’historique de création | -| **signalements_bugs(id_utilisateur)** → `utilisateurs(id)` | **SET NULL** | Conserver le ticket même si compte supprimé | -| **uploads(id_utilisateur)** → `utilisateurs(id)` | **SET NULL** | Fichier reste référencé sans l’auteur | -| **notifications(id_utilisateur)** → `utilisateurs(id)` | **CASCADE** | Notifications propres à l’utilisateur | -| **validations(id_utilisateur)** → `utilisateurs(id)` | **SET NULL** | Garder l’historique de décision | - -> **ON UPDATE** : **NO ACTION** partout (les UUID ne changent pas). - ---- - -## 🔎 Détail par domaine - -### Utilisateurs & extensions -- `assistantes_maternelles.id_utilisateur` → **CASCADE** -- `parents.id_utilisateur` → **CASCADE** -- `parents.id_co_parent` → **SET NULL** (interdit d’être co-parent de soi-même via CHECK déjà posé) - -### Enfants & liaisons -- `enfants_parents.id_parent` → **CASCADE** -- `enfants_parents.id_enfant` → **CASCADE** - -### Dossiers & échanges -- `dossiers.id_parent` → **CASCADE** -- `dossiers.id_enfant` → **CASCADE** -- `messages.id_dossier` → **CASCADE** -- `messages.id_expediteur` → **SET NULL** - -### Contrats & avenants -- `contrats.id_dossier` → **CASCADE** (unique 1:1) -- `avenants_contrats.id_contrat` → **CASCADE** -- `avenants_contrats.initie_par` → **SET NULL** - -### Événements -- `evenements.id_enfant` → **CASCADE** -- `evenements.id_am` → **SET NULL** -- `evenements.id_parent` → **SET NULL** -- `evenements.cree_par` → **SET NULL** - -### Divers -- `signalements_bugs.id_utilisateur` → **SET NULL** -- `uploads.id_utilisateur` → **SET NULL** -- `notifications.id_utilisateur` → **CASCADE** -- `validations.id_utilisateur` → **SET NULL** - ---- - -## 🧪 Scénarios de test (exemples) - -1. **Suppression d’un parent** - - Supprimer `utilisateurs(id=parentX)` - - Attendu : `parents` (CASCADE), ses `dossiers` (CASCADE), `messages` liés aux `dossiers` (CASCADE) sont supprimés. - -2. **Suppression d’un co-parent** - - Supprimer `utilisateurs(id=coParentY)` - - Attendu : `parents.id_co_parent` passe à **NULL**, aucun dossier supprimé. - -3. **Suppression d’un utilisateur auteur de messages** - - Supprimer `utilisateurs(id=uZ)` - - Attendu : les lignes `messages` **restent**, `id_expediteur` devient **NULL**. - -4. **Suppression d’un enfant** - - Supprimer `enfants(id=childA)` - - Attendu : `enfants_parents` (CASCADE), `dossiers` du childA (CASCADE), `evenements` du childA (CASCADE). - -5. **Suppression d’un utilisateur AM** - - Supprimer `utilisateurs(id=amB)` - - Attendu : `evenements.id_am` devient **NULL** (historique conservé). - ---- - -## 🛠 Migrations associées - -Les ajustements sont implémentés dans : -- **`/bdd/migrations/04_fk_policies.sql`** - – redéfinition des contraintes FK avec les bonnes politiques (**DROP puis ADD CONSTRAINT**), de façon idempotente. - ---- - -## 📄 Notes & futures évolutions - -- **RGPD (Sprint 2)** : si vous activez le **soft delete** (`deleted_at`) côté tables métier, ces politiques restent valides (les suppressions logiques se gèrent au niveau applicatif). -- **Audit** : si vous voulez tracer les suppressions, ajoutez des triggers d’audit (voir ticket Sprint 2 – Audit log). -- **Performance** : chaque FK doit être **indexée côté enfant** (cf. `02_indexes.sql`). - ---- - -## ✅ Checklist de conformité - -- [ ] Toutes les FK listées existent dans la base -- [ ] Politique **ON DELETE** conforme au tableau ci-dessus -- [ ] **ON UPDATE = NO ACTION** partout -- [ ] Tests de suppression réalisés sur une base seedée -- [ ] `04_fk_policies.sql` appliqué sans erreur - ---- - -**Mainteneur** : Équipe BDD -**Dernière mise à jour** : Sprint 1 – Politique FK consolidée