1408 lines
37 KiB
Markdown
1408 lines
37 KiB
Markdown
# Audit du schéma SQLite V9
|
||
|
||
> [!IMPORTANT]
|
||
> Ce document audite la V9 visible sur la branche publique au commit indiqué.
|
||
> Il ne doit pas être utilisé comme audit du schéma V10 local sans une nouvelle
|
||
> vérification du code, des migrations et des tests V10.
|
||
|
||
> **Projet :** Labfy Investigation
|
||
> **Date de l’audit :** 2026-07-24
|
||
> **Branche auditée :** `main` publique sur Forgejo
|
||
> **Commit audité :** `8bc3b43d63f4bd3da673ddf86a7e4b7a81e28604`
|
||
> **Version de schéma confirmée par le code public :** **V9**
|
||
> **Statut du document :** audit historique vérifié de la V9 publique
|
||
> **Périmètre :** schémas SQL, mécanisme de migration, couche Database, DAO principaux, tests et tickets Forgejo associés
|
||
|
||
---
|
||
|
||
## Avertissement important concernant la V10
|
||
|
||
Le propriétaire du projet indique que le dépôt de travail local est déjà en **V10**.
|
||
|
||
Au moment de cet audit, la branche `main` publique consultée sur Forgejo expose toutefois :
|
||
|
||
- `DATABASE_SCHEMA_VERSION_CURRENT 9` dans `src/database/database.c` ;
|
||
- des scripts versionnés allant de `database/schema_v1.sql` à
|
||
`database/schema_v9.sql` ;
|
||
- `database/schema_current.sql` explicitement présenté comme le schéma courant
|
||
V9 ;
|
||
- aucun fichier `schema_v10.sql` dans la branche publique auditée.
|
||
|
||
Ce document décrit donc **l’état public V9 vérifiable**, et non la V10 locale
|
||
non encore accessible dans les sources consultées.
|
||
|
||
Il ne doit pas être présenté comme l’audit définitif de la V10 tant que les
|
||
fichiers suivants n’ont pas été publiés ou fournis :
|
||
|
||
- le script de migration V10 ;
|
||
- les fonctions C d’installation et de migration vers V10 ;
|
||
- la nouvelle constante de version ;
|
||
- les tests de création et de migration V10 ;
|
||
- les tickets et commits correspondants.
|
||
|
||
---
|
||
|
||
# 1. Résumé exécutif
|
||
|
||
Le schéma public de Labfy Investigation est un schéma SQLite versionné, propre
|
||
à chaque enquête et construit autour de quatre objectifs principaux :
|
||
|
||
1. préserver les preuves et leurs métadonnées ;
|
||
2. structurer les entités et leurs relations ;
|
||
3. conserver la provenance des traitements OSINT ;
|
||
4. permettre l’évolution du modèle par migrations transactionnelles.
|
||
|
||
La version publique courante est la V9.
|
||
|
||
Le mécanisme général est cohérent :
|
||
|
||
- la version est stockée dans `metadata.schema_version` ;
|
||
- une base plus récente que l’application est refusée ;
|
||
- chaque migration possède une fonction dédiée ;
|
||
- chaque migration s’exécute dans une transaction ;
|
||
- la version n’est mise à jour qu’après l’application du SQL ;
|
||
- un échec provoque un rollback ;
|
||
- une nouvelle base reçoit immédiatement V1 à V9 dans une seule transaction ;
|
||
- `schema_current.sql` ajoute des extensions idempotentes à chaque ouverture.
|
||
|
||
Les points les plus solides sont :
|
||
|
||
- activation explicite des clés étrangères ;
|
||
- usage des requêtes préparées pour les valeurs variables ;
|
||
- migration V9 conservatrice des types de relations ;
|
||
- contrôle `PRAGMA foreign_key_check` avant validation de la V9 ;
|
||
- tests de création d’une base neuve ;
|
||
- test de migration d’une ancienne base V1 ;
|
||
- test de rollback d’une migration V2 défaillante.
|
||
|
||
Les principales faiblesses documentaires ou techniques observées sont :
|
||
|
||
- la documentation principale de la base reste annoncée comme « stable V1 »
|
||
alors que le code public est en V9 ;
|
||
- la version courante est dupliquée sous forme numérique et textuelle dans un
|
||
fichier C privé ;
|
||
- les tests de migration ne couvrent pas systématiquement chaque version et
|
||
chaque rollback ;
|
||
- `schema_current.sql` mélange rattrapage idempotent et migration de données de
|
||
présentation ;
|
||
- aucune sauvegarde préalable automatique n’a été observée dans le mécanisme de
|
||
migration consulté ;
|
||
- la V10 locale ne peut pas être auditée tant qu’elle n’est pas disponible.
|
||
|
||
---
|
||
|
||
# 2. Méthode et hiérarchie des sources
|
||
|
||
L’audit applique l’ordre de confiance suivant :
|
||
|
||
1. code présent dans la branche auditée ;
|
||
2. scripts de schéma et fonctions de migration ;
|
||
3. tests automatisés ;
|
||
4. commits associés ;
|
||
5. tickets Forgejo fermés ;
|
||
6. documentation d’architecture ;
|
||
7. anciens audits et feuilles de route.
|
||
|
||
Cette hiérarchie est nécessaire parce qu’un document historique peut décrire
|
||
une intention ou une ancienne version sans représenter l’état courant.
|
||
|
||
## 2.1 Sources principales examinées
|
||
|
||
### Schémas
|
||
|
||
- `database/schema_v1.sql`
|
||
- `database/schema_v2.sql`
|
||
- `database/schema_v3.sql`
|
||
- `database/schema_v4.sql`
|
||
- `database/schema_v5.sql`
|
||
- `database/schema_v6.sql`
|
||
- `database/schema_v7.sql`
|
||
- `database/schema_v8.sql`
|
||
- `database/schema_v9.sql`
|
||
- `database/schema_current.sql`
|
||
|
||
### Infrastructure SQLite
|
||
|
||
- `src/database/database.c`
|
||
- `src/database/schema.c`
|
||
- `src/database/statement.c`
|
||
- `src/database/transaction.c`
|
||
- `include/database/database.h`
|
||
- `include/database/schema.h`
|
||
|
||
### Accès métier et modèles
|
||
|
||
- contenu de `include/dao/`
|
||
- contenu de `src/dao/`
|
||
- contenu de `include/models/`
|
||
- modules liés aux preuves, entités, relations, provenance OSINT, extractions
|
||
et positions du graphe
|
||
|
||
### Tests
|
||
|
||
- `tests/test_database.c`
|
||
- `tests/test_statement.c`
|
||
- `tests/test_transaction.c`
|
||
- tests des DAO et services visibles dans `tests/`
|
||
- tests des types canoniques de relations
|
||
|
||
### Documentation et tickets
|
||
|
||
- `docs/database/DATABASE_ARCHITECTURE.md`
|
||
- `docs/database/SCHEMA_AUDIT_V1.md`
|
||
- ticket Forgejo `#106` : normalisation des types de relations
|
||
- commit `8bc3b43d63` : centralisation des types de relations
|
||
|
||
## 2.2 Limites de l’audit
|
||
|
||
Cet audit est une analyse statique du dépôt public.
|
||
|
||
Il n’a pas exécuté :
|
||
|
||
- `make -j8` ;
|
||
- la suite de tests ;
|
||
- une migration réelle sur une base synthétique ;
|
||
- `PRAGMA integrity_check` sur une base V9 produite localement ;
|
||
- `PRAGMA foreign_key_check` sur une base V9 produite localement ;
|
||
- une comparaison binaire entre une base migrée et une base fraîche.
|
||
|
||
Les procédures de vérification reproductible sont proposées plus loin.
|
||
|
||
---
|
||
|
||
# 3. Source de vérité de la version
|
||
|
||
## 3.1 Constante courante
|
||
|
||
La source de vérité publique se trouve dans :
|
||
|
||
```text
|
||
src/database/database.c
|
||
```
|
||
|
||
avec les deux définitions :
|
||
|
||
```c
|
||
#define DATABASE_SCHEMA_VERSION_CURRENT 9
|
||
#define DATABASE_SCHEMA_VERSION_CURRENT_TEXT "9"
|
||
```
|
||
|
||
La première sert aux comparaisons numériques.
|
||
|
||
La seconde est enregistrée dans :
|
||
|
||
```text
|
||
metadata.schema_version
|
||
```
|
||
|
||
## 3.2 Lecture de la version
|
||
|
||
La fonction :
|
||
|
||
```c
|
||
database_read_schema_version()
|
||
```
|
||
|
||
effectue les contrôles suivants :
|
||
|
||
- prépare une requête vers `metadata` ;
|
||
- lie la clé `schema_version` ;
|
||
- refuse l’absence de valeur ;
|
||
- refuse une chaîne vide ;
|
||
- convertit la valeur en entier ;
|
||
- refuse une valeur non numérique ;
|
||
- refuse une version inférieure à 1 ;
|
||
- refuse une valeur supérieure à `G_MAXINT` ;
|
||
- vérifie qu’aucune seconde ligne n’est retournée.
|
||
|
||
## 3.3 Base plus récente que l’application
|
||
|
||
La fonction :
|
||
|
||
```c
|
||
database_migrate_to_latest()
|
||
```
|
||
|
||
refuse une base dont la version est supérieure à :
|
||
|
||
```c
|
||
DATABASE_SCHEMA_VERSION_CURRENT
|
||
```
|
||
|
||
Cela évite qu’une ancienne version de Labfy Investigation ouvre et modifie une
|
||
base créée par une version plus récente.
|
||
|
||
## 3.4 Version inconnue ou non migrable
|
||
|
||
La boucle de migration utilise un `switch` sur la version actuelle.
|
||
|
||
Une version ancienne qui ne possède aucun chemin connu produit une erreur
|
||
d’état au lieu d’essayer une transformation implicite.
|
||
|
||
## 3.5 Mise à jour de la version
|
||
|
||
La fonction :
|
||
|
||
```c
|
||
database_update_schema_version()
|
||
```
|
||
|
||
utilise une requête préparée et met à jour la clé `schema_version`.
|
||
|
||
Dans chaque migration examinée, cette mise à jour intervient après
|
||
l’installation de la nouvelle structure et avant le `COMMIT`.
|
||
|
||
En cas d’erreur, la transaction est annulée et la version ne doit pas avancer.
|
||
|
||
---
|
||
|
||
# 4. Installation d’une base neuve
|
||
|
||
La fonction :
|
||
|
||
```c
|
||
database_initialize()
|
||
```
|
||
|
||
crée une base neuve dans une transaction initiale unique.
|
||
|
||
L’ordre public V9 est le suivant :
|
||
|
||
1. ouverture de SQLite ;
|
||
2. activation de `PRAGMA foreign_keys = ON` ;
|
||
3. début de transaction ;
|
||
4. installation de V1 ;
|
||
5. installation de V2 ;
|
||
6. installation de V3 ;
|
||
7. installation de V4 ;
|
||
8. installation de V5 ;
|
||
9. installation de V6 ;
|
||
10. installation de V7 ;
|
||
11. installation de V8 ;
|
||
12. installation de V9 ;
|
||
13. application de `schema_current.sql` ;
|
||
14. insertion des métadonnées ;
|
||
15. insertion de l’enquête ;
|
||
16. commit.
|
||
|
||
Un échec provoque un rollback de l’ensemble.
|
||
|
||
## Observation
|
||
|
||
Une base neuve rejoue toute l’histoire du schéma.
|
||
|
||
Cette méthode garantit qu’une base neuve et une base migrée utilisent les mêmes
|
||
étapes. Elle impose cependant que chaque ancien script reste compatible avec
|
||
le moteur SQLite utilisé aujourd’hui.
|
||
|
||
À moyen terme, le projet pourra envisager un schéma de référence consolidé pour
|
||
les bases neuves, tout en conservant les migrations historiques pour les
|
||
anciennes bases. Ce changement ne doit être réalisé qu’avec des tests comparant
|
||
strictement les deux chemins.
|
||
|
||
---
|
||
|
||
# 5. Chaîne publique des migrations
|
||
|
||
| Passage | Script | Fonction C | Objet principal |
|
||
|---|---|---|---|
|
||
| création | `schema_v1.sql` | `schema_install_v1()` | socle métier complet |
|
||
| V1 → V2 | `schema_v2.sql` | `schema_install_v2()` | renforcement des preuves |
|
||
| V2 → V3 | `schema_v3.sql` | `schema_install_v3()` | provenance OSINT |
|
||
| V3 → V4 | `schema_v4.sql` | `schema_install_v4()` | comptes sociaux |
|
||
| V4 → V5 | `schema_v5.sql` | `schema_install_v5()` | rôles des personnes |
|
||
| V5 → V6 | `schema_v6.sql` | `schema_install_v6()` | identité usurpée |
|
||
| V6 → V7 | `schema_v7.sql` | `schema_install_v7()` | extractions |
|
||
| V7 → V8 | `schema_v8.sql` | `schema_install_v8()` | viewport du graphe |
|
||
| V8 → V9 | `schema_v9.sql` + migration C | `schema_install_v9()` | types canoniques de relations |
|
||
| complément | `schema_current.sql` | `schema_ensure_current()` | extensions idempotentes V9 |
|
||
|
||
## 5.1 V1 — Socle métier
|
||
|
||
La V1 crée notamment :
|
||
|
||
### Métadonnées
|
||
|
||
- `metadata`
|
||
- `investigation`
|
||
|
||
### Classification et référentiels
|
||
|
||
- `categories`
|
||
- `tags`
|
||
- `types_preuve`
|
||
- `types_entite`
|
||
- `types_source`
|
||
- `types_outil`
|
||
|
||
### Collecte
|
||
|
||
- `sources`
|
||
- `preuves`
|
||
- `recherches`
|
||
|
||
### Connaissance
|
||
|
||
- `entites`
|
||
- `relations`
|
||
|
||
### Raisonnement et traçabilité
|
||
|
||
- `hypotheses`
|
||
- `chronologie`
|
||
- `journal`
|
||
|
||
### Tables de liaison
|
||
|
||
- `tag_preuves`
|
||
- `tag_recherches`
|
||
- `tag_entites`
|
||
- `tag_relations`
|
||
- `tag_hypotheses`
|
||
- `tag_chronologie`
|
||
- `recherche_preuves`
|
||
- `recherche_entites`
|
||
- `preuve_entites`
|
||
- `relation_preuves`
|
||
- `recherche_relations`
|
||
- `recherche_chronologie`
|
||
- `preuve_chronologie`
|
||
- `entite_chronologie`
|
||
- `relation_chronologie`
|
||
- `hypothese_preuves`
|
||
- `hypothese_entites`
|
||
- `hypothese_relations`
|
||
- `recherche_hypotheses`
|
||
|
||
La V1 constitue un schéma étendu, et non un simple prototype à deux tables.
|
||
|
||
## 5.2 V2 — Renforcement des preuves
|
||
|
||
La V2 ajoute à `preuves` :
|
||
|
||
- `original_name` ;
|
||
- `collected_at` ;
|
||
- `source` ;
|
||
- `integrity_status`.
|
||
|
||
Elle effectue également :
|
||
|
||
- un backfill de `original_name` depuis `name` ;
|
||
- la création de `idx_preuves_imported_at` ;
|
||
- un trigger de validation à l’insertion ;
|
||
- un trigger de validation à la mise à jour.
|
||
|
||
Les triggers renforcent notamment :
|
||
|
||
- le nom original obligatoire ;
|
||
- la taille non négative ;
|
||
- le SHA-256 en minuscules sur 64 caractères ;
|
||
- la plage valide de `integrity_status`.
|
||
|
||
## 5.3 V3 — Provenance OSINT structurée
|
||
|
||
La V3 ajoute :
|
||
|
||
- `osint_executions`
|
||
- `osint_execution_entities`
|
||
- `osint_execution_relations`
|
||
|
||
La table principale conserve notamment :
|
||
|
||
- l’outil ;
|
||
- sa version ;
|
||
- l’action ;
|
||
- la sélection d’origine ;
|
||
- la cible ;
|
||
- les arguments ;
|
||
- les dates de début et de fin ;
|
||
- le code de sortie ;
|
||
- l’état final ;
|
||
- les sorties standard et erreur brutes ;
|
||
- le SHA-256 de la sortie.
|
||
|
||
Les tables de liaison indiquent si les entités ou relations ont été créées ou
|
||
réutilisées.
|
||
|
||
## 5.4 V4 — Comptes sociaux
|
||
|
||
La V4 :
|
||
|
||
- ajoute les types TikTok, X, Telegram et compte social générique ;
|
||
- crée `comptes_sociaux`.
|
||
|
||
Cette table est une extension spécialisée d’une entité et conserve :
|
||
|
||
- la plateforme ;
|
||
- l’URL du profil ;
|
||
- le pseudonyme ;
|
||
- un identifiant de plateforme facultatif ;
|
||
- la première observation ;
|
||
- l’état du compte ;
|
||
- des notes.
|
||
|
||
## 5.5 V5 — Rôles des personnes
|
||
|
||
La V5 crée `person_roles`.
|
||
|
||
Le rôle est limité à une liste contrôlée comprenant notamment :
|
||
|
||
- non catégorisé ;
|
||
- escroc présumé ;
|
||
- victime ;
|
||
- témoin ;
|
||
- suspect ;
|
||
- personne liée.
|
||
|
||
## 5.6 V6 — Identité usurpée
|
||
|
||
La V6 reconstruit `person_roles` afin d’ajouter :
|
||
|
||
```text
|
||
impersonated_identity
|
||
```
|
||
|
||
Elle :
|
||
|
||
1. renomme la table V5 ;
|
||
2. crée la nouvelle table ;
|
||
3. recopie les données ;
|
||
4. supprime l’ancienne table ;
|
||
5. recrée l’index.
|
||
|
||
Cette migration est sensible aux clés étrangères et doit rester couverte par un
|
||
test de migration réel.
|
||
|
||
## 5.7 V7 — Extractions
|
||
|
||
La V7 crée `extractions`.
|
||
|
||
Elle conserve :
|
||
|
||
- l’identifiant de l’extraction ;
|
||
- une preuve associée facultative ;
|
||
- le type de source ;
|
||
- l’identifiant de la source ;
|
||
- l’outil ;
|
||
- la date de création.
|
||
|
||
La provenance est partiellement polymorphe via :
|
||
|
||
```text
|
||
source_kind
|
||
source_id
|
||
```
|
||
|
||
SQLite ne peut pas imposer directement une clé étrangère vers plusieurs tables
|
||
possibles. La cohérence de `source_id` dépend donc aussi de la couche métier.
|
||
|
||
## 5.8 V8 — État du viewport
|
||
|
||
La V8 crée `graph_viewport`.
|
||
|
||
La table ne peut contenir qu’une ligne :
|
||
|
||
```text
|
||
id = 1
|
||
```
|
||
|
||
Elle persiste :
|
||
|
||
- le zoom ;
|
||
- le décalage horizontal ;
|
||
- le décalage vertical ;
|
||
- la date de mise à jour.
|
||
|
||
Il s’agit d’un état de présentation, pas d’une donnée métier.
|
||
|
||
## 5.9 V9 — Types canoniques de relations
|
||
|
||
La V9 crée `relation_types` avec :
|
||
|
||
- un identifiant entier ;
|
||
- un code métier stable facultatif ;
|
||
- un libellé canonique ;
|
||
- une clé normalisée unique ;
|
||
- une description facultative ;
|
||
- un indicateur système.
|
||
|
||
Elle insère dix types système initiaux, dont :
|
||
|
||
- `resolves_to`
|
||
- `aliases_to`
|
||
- `uses_name_server`
|
||
- `links_to`
|
||
- `sends`
|
||
- `uses`
|
||
- `controls`
|
||
- `owns`
|
||
- `knows`
|
||
- `redirects_to`
|
||
|
||
La migration ne se limite pas au fichier SQL.
|
||
|
||
La fonction :
|
||
|
||
```c
|
||
schema_v9_migrate_relation_types()
|
||
```
|
||
|
||
réalise également les opérations suivantes :
|
||
|
||
1. ajoute `relations.relation_type_id` si nécessaire ;
|
||
2. parcourt les anciennes relations dans un ordre déterministe ;
|
||
3. normalise l’ancien texte `type_relation` ;
|
||
4. recherche un type existant par code ou clé normalisée ;
|
||
5. crée un type personnalisé lorsqu’aucun type ne correspond ;
|
||
6. rattache chaque relation au type canonique ;
|
||
7. crée l’index d’unicité canonique ;
|
||
8. crée l’index sur `relation_type_id` ;
|
||
9. crée des triggers interdisant un type canonique nul ;
|
||
10. exécute `PRAGMA foreign_key_check`.
|
||
|
||
La colonne historique :
|
||
|
||
```text
|
||
relations.type_relation
|
||
```
|
||
|
||
reste présente pour compatibilité.
|
||
|
||
Depuis V9, l’identité logique du type doit être :
|
||
|
||
```text
|
||
relations.relation_type_id
|
||
```
|
||
|
||
et non le texte historique.
|
||
|
||
---
|
||
|
||
# 6. Rôle de `schema_current.sql`
|
||
|
||
`schema_current.sql` est présenté comme un ensemble d’extensions idempotentes
|
||
du schéma courant V9.
|
||
|
||
Il crée si nécessaire :
|
||
|
||
- `graph_node_positions`
|
||
- `extractions`
|
||
- `graph_layout_positions`
|
||
- `graph_viewport`
|
||
- `relation_types`
|
||
|
||
Il ajoute également deux triggers nettoyant les positions de graphe orphelines
|
||
après suppression d’une entité ou d’une relation.
|
||
|
||
## 6.1 Migration des positions
|
||
|
||
Le script copie les anciennes positions :
|
||
|
||
```sql
|
||
INSERT OR IGNORE INTO graph_layout_positions (...)
|
||
SELECT ... FROM graph_node_positions;
|
||
```
|
||
|
||
puis exécute :
|
||
|
||
```sql
|
||
DELETE FROM graph_node_positions;
|
||
```
|
||
|
||
L’objectif est de migrer l’ancien état limité aux entités vers une disposition
|
||
générique acceptant aussi les relations.
|
||
|
||
## 6.2 Point d’attention
|
||
|
||
Le script est exécuté après les migrations lors de l’ouverture.
|
||
|
||
Il contient donc à la fois :
|
||
|
||
- des créations idempotentes ;
|
||
- une migration de données de présentation ;
|
||
- une suppression des anciennes lignes.
|
||
|
||
Le comportement peut être légitime, mais il doit être explicitement couvert par
|
||
des tests vérifiant plusieurs exécutions successives afin de garantir :
|
||
|
||
- l’absence de perte de positions courantes ;
|
||
- l’absence de réimport d’anciennes coordonnées ;
|
||
- la stabilité après plusieurs ouvertures ;
|
||
- le nettoyage correct des positions orphelines.
|
||
|
||
---
|
||
|
||
# 7. Inventaire statique du schéma public V9
|
||
|
||
L’application statique des scripts publics produit **45 tables distinctes**.
|
||
|
||
Ce nombre est dérivé des scripts, et doit être confirmé sur une base générée par
|
||
une requête sur `sqlite_master`.
|
||
|
||
## 7.1 Métadonnées
|
||
|
||
| Table | Rôle |
|
||
|---|---|
|
||
| `metadata` | version et informations techniques |
|
||
| `investigation` | enquête unique contenue dans la base |
|
||
|
||
## 7.2 Référentiels et classification
|
||
|
||
| Table | Rôle |
|
||
|---|---|
|
||
| `categories` | classement principal |
|
||
| `tags` | annotations multiples |
|
||
| `types_preuve` | types de preuves |
|
||
| `types_entite` | types d’entités |
|
||
| `types_source` | types de sources |
|
||
| `types_outil` | types d’outils |
|
||
| `relation_types` | types canoniques de relations |
|
||
|
||
## 7.3 Données métier principales
|
||
|
||
| Table | Rôle |
|
||
|---|---|
|
||
| `sources` | origine d’une information |
|
||
| `preuves` | métadonnées des fichiers collectés |
|
||
| `recherches` | actions d’investigation |
|
||
| `entites` | objets identifiés |
|
||
| `relations` | liens orientés entre entités |
|
||
| `hypotheses` | raisonnements provisoires |
|
||
| `chronologie` | événements de l’enquête |
|
||
| `journal` | journal technique |
|
||
|
||
## 7.4 Extensions spécialisées
|
||
|
||
| Table | Version | Rôle |
|
||
|---|---:|---|
|
||
| `osint_executions` | V3 | provenance des traitements OSINT |
|
||
| `osint_execution_entities` | V3 | entités créées ou réutilisées |
|
||
| `osint_execution_relations` | V3 | relations créées ou réutilisées |
|
||
| `comptes_sociaux` | V4 | données propres aux comptes sociaux |
|
||
| `person_roles` | V5/V6 | rôle d’enquête d’une personne |
|
||
| `extractions` | V7 | provenance d’une extraction |
|
||
| `graph_viewport` | V8 | zoom et position du canevas |
|
||
| `graph_node_positions` | courant | ancien stockage des positions d’entités |
|
||
| `graph_layout_positions` | courant | positions génériques entités/relations |
|
||
|
||
## 7.5 Tables de liaison V1
|
||
|
||
| Domaine | Tables |
|
||
|---|---|
|
||
| tags | `tag_preuves`, `tag_recherches`, `tag_entites`, `tag_relations`, `tag_hypotheses`, `tag_chronologie` |
|
||
| recherches | `recherche_preuves`, `recherche_entites`, `recherche_relations`, `recherche_chronologie`, `recherche_hypotheses` |
|
||
| preuves | `preuve_entites`, `preuve_chronologie`, `relation_preuves` |
|
||
| chronologie | `entite_chronologie`, `relation_chronologie` |
|
||
| hypothèses | `hypothese_preuves`, `hypothese_entites`, `hypothese_relations` |
|
||
|
||
---
|
||
|
||
# 8. Intégrité et sécurité des données
|
||
|
||
## 8.1 Clés étrangères
|
||
|
||
`database_open()` exécute :
|
||
|
||
```sql
|
||
PRAGMA foreign_keys = ON;
|
||
```
|
||
|
||
Les stratégies observées sont :
|
||
|
||
- `CASCADE` pour les objets strictement dépendants ;
|
||
- `RESTRICT` lorsque la suppression risquerait de casser l’historique ;
|
||
- `SET NULL` pour les références facultatives.
|
||
|
||
## 8.2 Requêtes préparées
|
||
|
||
Les valeurs variables de la couche Database et des DAO utilisent les fonctions
|
||
de préparation et de liaison.
|
||
|
||
Les requêtes statiques sans donnée utilisateur peuvent être exécutées avec
|
||
`sqlite3_exec()`.
|
||
|
||
La règle à conserver est :
|
||
|
||
> aucune valeur externe ou utilisateur ne doit être concaténée dans une chaîne
|
||
> SQL.
|
||
|
||
Le caractère append-only du journal ne constitue jamais une exception à cette
|
||
règle.
|
||
|
||
## 8.3 Transactions
|
||
|
||
Les migrations publiques V1 à V9 sont pilotées par des fonctions dédiées.
|
||
|
||
Chaque passage de version :
|
||
|
||
- démarre une transaction ;
|
||
- applique le changement ;
|
||
- met à jour la version ;
|
||
- commit en cas de succès ;
|
||
- rollback en cas d’échec.
|
||
|
||
La création d’une base neuve est également atomique.
|
||
|
||
## 8.4 Preuves
|
||
|
||
Le schéma et la couche métier conservent notamment :
|
||
|
||
- UUID ;
|
||
- chemin relatif ;
|
||
- nom interne ;
|
||
- nom original ;
|
||
- taille ;
|
||
- SHA-256 ;
|
||
- type MIME ;
|
||
- date du fichier ;
|
||
- date de collecte ;
|
||
- date d’import ;
|
||
- statut d’intégrité ;
|
||
- statut logique.
|
||
|
||
Le fichier original reste dans l’arborescence de l’enquête. SQLite conserve ses
|
||
métadonnées et ses relations.
|
||
|
||
## 8.5 Suppression logique
|
||
|
||
Plusieurs objets V1 utilisent des statuts tels que :
|
||
|
||
```text
|
||
active
|
||
archived
|
||
deleted
|
||
```
|
||
|
||
Certaines suppressions physiques existent néanmoins dans les DAO, notamment
|
||
pour les relations.
|
||
|
||
Le document d’architecture doit donc éviter d’affirmer que toute suppression
|
||
est systématiquement logique. La stratégie réelle doit être documentée table
|
||
par table.
|
||
|
||
## 8.6 Journal et chronologie
|
||
|
||
Le schéma distingue :
|
||
|
||
- `chronologie` : événements significatifs de l’enquête ;
|
||
- `journal` : trace technique des actions de l’application.
|
||
|
||
Le journal est conçu comme append-only dans la documentation, mais cet audit
|
||
n’a pas identifié de trigger SQLite interdisant une mise à jour ou une
|
||
suppression. Cette propriété repose donc actuellement au moins en partie sur la
|
||
couche applicative.
|
||
|
||
---
|
||
|
||
# 9. Correspondance SQL, modèles, DAO et tests
|
||
|
||
| Domaine | Table principale | Modèle ou structure | DAO/service observé | Tests observés |
|
||
|---|---|---|---|---|
|
||
| enquête | `investigation` | `InvestigationRecord` | `InvestigationDao` | `test_investigation_record`, `test_investigation_dao` |
|
||
| preuves | `preuves` | `EvidenceRecord` | `EvidenceDao`, `EvidenceTypeDao` | nombreux tests preuve/import/intégrité |
|
||
| preuve-entité | `preuve_entites` | — | `EvidenceEntityDao` | `test_evidence_entity_dao` |
|
||
| entités | `entites` | `EntityRecord` | `EntityDao`, `EntityTypeDao` | tests modèle et DAO |
|
||
| relations | `relations` | `RelationRecord` | `RelationDao`, `RelationService` | tests DAO, modèle et service |
|
||
| types de relation | `relation_types` | `RelationType` | `RelationTypeDao`, `RelationTypeService` | normalisation et service |
|
||
| relation-preuve | `relation_preuves` | — | `RelationEvidenceDao` | `test_relation_evidence_dao` |
|
||
| provenance OSINT | `osint_executions` | `OsintExecutionRecord` | `OsintExecutionDao` | DAO et intégrité |
|
||
| extractions | `extractions` | contexte métier | `ExtractionDao`, service de dépôt | `test_extraction_drop_service` |
|
||
| positions graphe | tables de graphe | `GraphNodePosition`, layout | `GraphNodePositionDao` | `test_graph_node_position_dao` |
|
||
| comptes sociaux | `comptes_sociaux` | plateforme sociale | service compte social | `test_social_account_service` |
|
||
| personnes | `person_roles` | extension d’entité | service personne | `test_person_entity_service` |
|
||
|
||
## Observation
|
||
|
||
La V1 contient davantage de domaines que les DAO publics actuellement exposés.
|
||
|
||
Aucun DAO dédié n’a été observé dans `include/dao/` pour plusieurs tables, dont :
|
||
|
||
- `sources` ;
|
||
- `recherches` ;
|
||
- `hypotheses` ;
|
||
- `chronologie` ;
|
||
- `journal` ;
|
||
- `categories` ;
|
||
- `tags`.
|
||
|
||
Cela ne signifie pas que ces tables sont inutilisables. Cela indique seulement
|
||
qu’aucune interface DAO publique dédiée n’est visible dans le dossier audité au
|
||
commit indiqué.
|
||
|
||
---
|
||
|
||
# 10. Couverture de tests observée
|
||
|
||
## 10.1 Points couverts par `test_database.c`
|
||
|
||
Le fichier vérifie notamment :
|
||
|
||
- l’initialisation d’une base valide ;
|
||
- le rollback d’une initialisation défaillante ;
|
||
- la présence de la version `9` dans une base neuve ;
|
||
- la présence de plusieurs tables ajoutées après V1 ;
|
||
- la migration d’une base V1 vers la version courante ;
|
||
- la conservation d’une preuve V1 ;
|
||
- le backfill V2 de `original_name` ;
|
||
- l’ajout des colonnes V2 ;
|
||
- l’ajout des triggers V2 ;
|
||
- le rollback complet d’une migration V2 provoquée en échec ;
|
||
- `PRAGMA integrity_check` après le rollback.
|
||
|
||
## 10.2 Tests spécialisés observés
|
||
|
||
Le dépôt possède également des tests pour :
|
||
|
||
- les preuves et leur intégrité ;
|
||
- les entités ;
|
||
- les relations ;
|
||
- les types canoniques de relations ;
|
||
- les exécutions OSINT ;
|
||
- les extractions ;
|
||
- les positions du graphe ;
|
||
- les comptes sociaux ;
|
||
- les rôles des personnes.
|
||
|
||
## 10.3 Lacunes de couverture à traiter
|
||
|
||
Le test principal de migration ne fournit pas une fixture indépendante pour
|
||
chaque version V2 à V9.
|
||
|
||
Il manque une matrice explicite de ce type :
|
||
|
||
| Base d’entrée | Migration | Vérifications minimales |
|
||
|---|---|---|
|
||
| V1 | V1 → V9 | données, version, FK, intégrité |
|
||
| V2 | V2 → V9 | preuve V2 conservée |
|
||
| V3 | V3 → V9 | provenance OSINT conservée |
|
||
| V4 | V4 → V9 | comptes sociaux conservés |
|
||
| V5 | V5 → V9 | rôles conservés pendant reconstruction V6 |
|
||
| V6 | V6 → V9 | identité usurpée conservée |
|
||
| V7 | V7 → V9 | extractions conservées |
|
||
| V8 | V8 → V9 | viewport et positions conservés |
|
||
| V9 | réouverture | idempotence de `schema_current.sql` |
|
||
|
||
Chaque fixture devrait vérifier au minimum :
|
||
|
||
```sql
|
||
PRAGMA integrity_check;
|
||
PRAGMA foreign_key_check;
|
||
SELECT value FROM metadata WHERE key = 'schema_version';
|
||
```
|
||
|
||
---
|
||
|
||
# 11. Constats d’audit
|
||
|
||
## AUD-001 — Documentation courante restée en V1
|
||
|
||
**Sévérité : élevée**
|
||
|
||
`docs/database/DATABASE_ARCHITECTURE.md` s’annonce encore comme :
|
||
|
||
```text
|
||
Statut : Stable (V1)
|
||
Schéma : V1
|
||
```
|
||
|
||
alors que le code public utilise V9.
|
||
|
||
### Risque
|
||
|
||
- confusion des développeurs ;
|
||
- erreurs des agents locaux ;
|
||
- mauvaise interprétation de l’état du projet ;
|
||
- décisions basées sur des structures historiques ;
|
||
- oubli des tables V2 à V9.
|
||
|
||
### Action recommandée
|
||
|
||
Créer :
|
||
|
||
```text
|
||
docs/database/SCHEMA_AUDIT_CURRENT.md
|
||
```
|
||
|
||
et déplacer les audits historiques vers :
|
||
|
||
```text
|
||
docs/database/audits/SCHEMA_AUDIT_V1.md
|
||
docs/database/audits/SCHEMA_AUDIT_V9.md
|
||
```
|
||
|
||
Le document courant doit indiquer le commit exact qu’il audite.
|
||
|
||
---
|
||
|
||
## AUD-002 — V10 locale non représentée dans la branche publique
|
||
|
||
**Sévérité : bloquante pour un audit « courant »**
|
||
|
||
La branche publique s’arrête à V9 tandis que le dépôt local est annoncé en V10.
|
||
|
||
### Action recommandée
|
||
|
||
Avant de finaliser ce document :
|
||
|
||
1. publier ou fournir les fichiers V10 ;
|
||
2. vérifier la constante courante ;
|
||
3. vérifier la chaîne de migration ;
|
||
4. vérifier les tests ;
|
||
5. compléter l’inventaire ;
|
||
6. remplacer le statut V9 par V10 ;
|
||
7. enregistrer le commit audité.
|
||
|
||
---
|
||
|
||
## AUD-003 — Version courante dupliquée
|
||
|
||
**Sévérité : moyenne**
|
||
|
||
La version est définie deux fois :
|
||
|
||
```c
|
||
DATABASE_SCHEMA_VERSION_CURRENT
|
||
DATABASE_SCHEMA_VERSION_CURRENT_TEXT
|
||
```
|
||
|
||
Les tests comparent aussi directement la chaîne `"9"`.
|
||
|
||
### Risque
|
||
|
||
Une future migration peut modifier une valeur et oublier l’autre.
|
||
|
||
### Action recommandée
|
||
|
||
Conserver une seule constante numérique et produire la représentation textuelle
|
||
au moment de l’écriture, ou centraliser les deux valeurs dans un fichier
|
||
d’interface unique couvert par une assertion de test.
|
||
|
||
---
|
||
|
||
## AUD-004 — `schema_current.sql` mélange plusieurs responsabilités
|
||
|
||
**Sévérité : moyenne**
|
||
|
||
Le fichier sert à la fois à :
|
||
|
||
- créer des structures manquantes ;
|
||
- maintenir la compatibilité ;
|
||
- migrer des positions ;
|
||
- supprimer les anciennes positions ;
|
||
- installer des triggers.
|
||
|
||
### Risque
|
||
|
||
Une opération supposée idempotente peut finir par modifier des données à chaque
|
||
ouverture.
|
||
|
||
### Action recommandée
|
||
|
||
Documenter chaque opération et ajouter un test exécutant
|
||
`schema_ensure_current()` plusieurs fois sur la même fixture.
|
||
|
||
---
|
||
|
||
## AUD-005 — Contrôle des clés étrangères non généralisé
|
||
|
||
**Sévérité : moyenne**
|
||
|
||
La migration V9 exécute explicitement :
|
||
|
||
```sql
|
||
PRAGMA foreign_key_check;
|
||
```
|
||
|
||
Aucun contrôle générique similaire n’a été observé dans le pilote commun de
|
||
toutes les migrations.
|
||
|
||
### Action recommandée
|
||
|
||
Exécuter un contrôle générique avant le commit de chaque migration, ou fournir
|
||
une justification documentée lorsqu’une migration ne le nécessite pas.
|
||
|
||
---
|
||
|
||
## AUD-006 — Couverture de migration incomplète par version
|
||
|
||
**Sévérité : élevée**
|
||
|
||
Le test principal couvre :
|
||
|
||
- création d’une base neuve ;
|
||
- migration V1 vers la version courante ;
|
||
- rollback V2.
|
||
|
||
Il ne constitue pas une matrice complète de fixtures V2 à V9.
|
||
|
||
### Action recommandée
|
||
|
||
Ajouter une fixture synthétique minimale pour chaque version publiée et migrer
|
||
chacune vers la version courante.
|
||
|
||
---
|
||
|
||
## AUD-007 — Absence de sauvegarde préalable observée
|
||
|
||
**Sévérité : élevée pour des enquêtes réelles**
|
||
|
||
Aucun appel de sauvegarde SQLite ou copie préalable n’a été observé dans
|
||
`database_migrate_to_latest()`.
|
||
|
||
La transaction protège la cohérence logique, mais elle ne remplace pas une
|
||
copie de sécurité face à :
|
||
|
||
- panne disque ;
|
||
- interruption brutale ;
|
||
- défaut SQLite ou système de fichiers ;
|
||
- erreur de migration non anticipée ;
|
||
- corruption déjà présente.
|
||
|
||
### Action recommandée
|
||
|
||
Avant toute migration d’une base existante :
|
||
|
||
1. fermer ou stabiliser les accès concurrents ;
|
||
2. créer une sauvegarde cohérente ;
|
||
3. vérifier sa création ;
|
||
4. lancer la migration ;
|
||
5. conserver la sauvegarde tant que la validation n’est pas terminée.
|
||
|
||
Cette fonctionnalité doit être testée uniquement sur des bases synthétiques.
|
||
|
||
---
|
||
|
||
## AUD-008 — Ancienne et nouvelle identité du type de relation coexistent
|
||
|
||
**Sévérité : moyenne**
|
||
|
||
V9 conserve :
|
||
|
||
```text
|
||
relations.type_relation
|
||
```
|
||
|
||
et ajoute :
|
||
|
||
```text
|
||
relations.relation_type_id
|
||
```
|
||
|
||
La documentation du commit précise que la première colonne ne doit plus servir
|
||
d’identité.
|
||
|
||
### Risque
|
||
|
||
Un module ancien peut encore filtrer ou détecter les doublons par texte.
|
||
|
||
### Action recommandée
|
||
|
||
Auditer tous les producteurs et lecteurs de relations, puis ajouter un test
|
||
interdisant toute régression vers `type_relation` comme clé métier.
|
||
|
||
La colonne historique pourra être supprimée dans une future migration seulement
|
||
après validation de toutes les anciennes bases et de tous les adaptateurs.
|
||
|
||
---
|
||
|
||
## AUD-009 — Append-only non imposé par SQLite
|
||
|
||
**Sévérité : faible à moyenne**
|
||
|
||
Le journal est documenté comme append-only, mais aucun trigger interdisant
|
||
`UPDATE` ou `DELETE` n’a été identifié dans les scripts examinés.
|
||
|
||
### Action recommandée
|
||
|
||
Choisir explicitement l’une des deux politiques :
|
||
|
||
- garantie applicative documentée et testée ;
|
||
- garantie SQLite par triggers de refus.
|
||
|
||
Le document courant doit dire laquelle est réellement retenue.
|
||
|
||
---
|
||
|
||
## AUD-010 — Paramètres SQLite de durabilité non documentés dans le code audité
|
||
|
||
**Sévérité : à évaluer**
|
||
|
||
Aucun réglage explicite n’a été identifié dans `database.c` pour :
|
||
|
||
- `journal_mode` ;
|
||
- `synchronous` ;
|
||
- `busy_timeout`.
|
||
|
||
SQLite applique donc probablement ses valeurs par défaut, sauf réglage réalisé
|
||
ailleurs.
|
||
|
||
### Action recommandée
|
||
|
||
Documenter volontairement les paramètres retenus et leurs conséquences avant
|
||
un usage opérationnel.
|
||
|
||
Ne pas activer WAL ou modifier `synchronous` sans étudier la portabilité d’une
|
||
enquête et les procédures de copie de ses fichiers annexes.
|
||
|
||
---
|
||
|
||
# 12. Exigences proposées pour la V10
|
||
|
||
La V10 doit être considérée incomplète tant que les éléments suivants ne sont
|
||
pas présents et cohérents.
|
||
|
||
## 12.1 Code
|
||
|
||
- `database/schema_v10.sql`
|
||
- `schema_install_v10()`
|
||
- `database_migrate_v9_to_v10()`
|
||
- cas `9` dans `database_migrate_to_latest()`
|
||
- installation V10 dans `database_initialize()`
|
||
- mise à jour de la version numérique
|
||
- mise à jour de la version textuelle ou suppression de cette duplication
|
||
- mise à jour du commentaire de `schema_current.sql`
|
||
|
||
## 12.2 Intégrité
|
||
|
||
- migration transactionnelle ;
|
||
- conservation des UUID ;
|
||
- conservation des preuves ;
|
||
- conservation des liaisons ;
|
||
- conservation de la provenance OSINT ;
|
||
- conservation des positions du graphe ;
|
||
- `PRAGMA foreign_key_check` avant commit ;
|
||
- version mise à jour uniquement après réussite ;
|
||
- rollback complet au premier échec.
|
||
|
||
## 12.3 Tests
|
||
|
||
- création d’une base neuve V10 ;
|
||
- migration V9 vers V10 ;
|
||
- migration V1 vers V10 ;
|
||
- fixture contenant des données réelles synthétiques de chaque domaine ;
|
||
- rollback V10 provoqué volontairement ;
|
||
- deuxième ouverture sans modification inattendue ;
|
||
- `PRAGMA integrity_check` ;
|
||
- `PRAGMA foreign_key_check` ;
|
||
- comparaison des objets SQLite attendus ;
|
||
- tests des DAO concernés.
|
||
|
||
## 12.4 Documentation
|
||
|
||
- mise à jour du présent audit ;
|
||
- résumé de la migration ;
|
||
- inventaire des tables et colonnes nouvelles ;
|
||
- ticket Forgejo associé ;
|
||
- commit exact audité ;
|
||
- statut explicite : implémenté, partiel, futur, historique ou abandonné.
|
||
|
||
---
|
||
|
||
# 13. Procédure de vérification reproductible
|
||
|
||
> Utiliser uniquement une copie synthétique.
|
||
> Ne jamais exécuter cette procédure sur une base d’enquête réelle sans
|
||
> sauvegarde et validation préalable.
|
||
|
||
## 13.1 Compilation
|
||
|
||
```bash
|
||
make clean
|
||
make -j8
|
||
make -j8 test
|
||
git diff --check
|
||
```
|
||
|
||
En cas d’échec provoqué par la parallélisation, revenir temporairement à :
|
||
|
||
```bash
|
||
make
|
||
make test
|
||
```
|
||
|
||
## 13.2 Création d’une base synthétique
|
||
|
||
Créer une enquête de test par l’API normale de l’application ou par un test
|
||
dédié, puis vérifier :
|
||
|
||
```bash
|
||
sqlite3 /chemin/test/Enquete.sqlite \
|
||
"SELECT value FROM metadata WHERE key = 'schema_version';"
|
||
|
||
sqlite3 /chemin/test/Enquete.sqlite \
|
||
"PRAGMA integrity_check;"
|
||
|
||
sqlite3 /chemin/test/Enquete.sqlite \
|
||
"PRAGMA foreign_key_check;"
|
||
```
|
||
|
||
Résultats attendus :
|
||
|
||
```text
|
||
<version courante>
|
||
ok
|
||
<aucune ligne pour foreign_key_check>
|
||
```
|
||
|
||
## 13.3 Inventaire du schéma
|
||
|
||
```bash
|
||
sqlite3 /chemin/test/Enquete.sqlite \
|
||
"SELECT type, name
|
||
FROM sqlite_master
|
||
WHERE name NOT LIKE 'sqlite_%'
|
||
ORDER BY type, name;"
|
||
```
|
||
|
||
## 13.4 Vérification de l’idempotence
|
||
|
||
1. ouvrir la base ;
|
||
2. fermer la base ;
|
||
3. enregistrer un dump du schéma et les données de présentation ;
|
||
4. rouvrir la base plusieurs fois ;
|
||
5. comparer les résultats ;
|
||
6. vérifier les positions du graphe ;
|
||
7. vérifier les types de relations ;
|
||
8. exécuter à nouveau les deux PRAGMA d’intégrité.
|
||
|
||
## 13.5 Vérification de migration
|
||
|
||
Pour chaque fixture V1 à V9 :
|
||
|
||
1. calculer une copie de travail ;
|
||
2. relever la version initiale ;
|
||
3. compter les objets métier ;
|
||
4. migrer ;
|
||
5. vérifier la version finale ;
|
||
6. comparer les UUID ;
|
||
7. comparer les empreintes des preuves ;
|
||
8. comparer les liaisons ;
|
||
9. vérifier les contraintes ;
|
||
10. vérifier le rollback sur une copie volontairement invalide.
|
||
|
||
---
|
||
|
||
# 14. Règle de maintenance proposée
|
||
|
||
Toute nouvelle version du schéma doit livrer ensemble :
|
||
|
||
```text
|
||
migration SQL
|
||
+ fonction d’installation
|
||
+ fonction de migration
|
||
+ incrément de version
|
||
+ tests de base neuve
|
||
+ tests d’ancienne base
|
||
+ test de rollback
|
||
+ contrôle d’intégrité
|
||
+ mise à jour de SCHEMA_AUDIT_CURRENT.md
|
||
+ ticket Forgejo
|
||
+ commit vérifiable
|
||
```
|
||
|
||
Un ticket de migration ne doit pas être fermé tant que cette chaîne n’est pas
|
||
complète.
|
||
|
||
## Statuts documentaires obligatoires
|
||
|
||
Chaque table, colonne ou fonctionnalité mentionnée dans la documentation devrait
|
||
porter l’un des statuts suivants :
|
||
|
||
```text
|
||
IMPLÉMENTÉ
|
||
PARTIELLEMENT IMPLÉMENTÉ
|
||
DOCUMENTÉ MAIS NON IMPLÉMENTÉ
|
||
HISTORIQUE
|
||
ABANDONNÉ
|
||
```
|
||
|
||
Cette règle évitera de confondre :
|
||
|
||
- une architecture cible ;
|
||
- un ancien audit ;
|
||
- une fonctionnalité réellement présente ;
|
||
- un ticket encore ouvert ;
|
||
- une migration locale non publiée.
|
||
|
||
---
|
||
|
||
# 15. Conclusion
|
||
|
||
Le schéma public V9 repose sur une base technique sérieuse :
|
||
|
||
- modèle relationnel riche ;
|
||
- versionnement explicite ;
|
||
- migrations transactionnelles ;
|
||
- provenance OSINT ;
|
||
- contraintes sur les preuves ;
|
||
- normalisation des types de relations ;
|
||
- séparation des données métier et de l’état du graphe ;
|
||
- tests nombreux autour des DAO et services.
|
||
|
||
Le problème principal n’est plus l’absence de structure.
|
||
|
||
Le problème principal est désormais **l’écart entre le code et la
|
||
documentation de référence**.
|
||
|
||
`SCHEMA_AUDIT_V1.md` reste utile comme document historique, mais ne doit plus
|
||
servir à déterminer l’état courant.
|
||
|
||
La prochaine étape correcte est :
|
||
|
||
1. fournir ou publier la V10 ;
|
||
2. auditer le delta V9 → V10 ;
|
||
3. exécuter la procédure reproductible sur des données synthétiques ;
|
||
4. remplacer le présent statut de brouillon par un audit V10 validé ;
|
||
5. conserver l’audit V9 dans un dossier historique.
|
||
|
||
---
|
||
|
||
# 16. Références du dépôt
|
||
|
||
## Commit public audité
|
||
|
||
```text
|
||
8bc3b43d63f4bd3da673ddf86a7e4b7a81e28604
|
||
feat(relations): centraliser les types et améliorer les aperçus
|
||
```
|
||
|
||
## Ticket principal lié à V9
|
||
|
||
```text
|
||
#106 — Normaliser et centraliser les types de relations
|
||
État : fermé
|
||
```
|
||
|
||
## Documents historiques
|
||
|
||
```text
|
||
docs/database/DATABASE_ARCHITECTURE.md
|
||
docs/database/SCHEMA_AUDIT_V1.md
|
||
```
|
||
|
||
## Fichiers constituant la source de vérité technique publique
|
||
|
||
```text
|
||
database/schema_v1.sql
|
||
database/schema_v2.sql
|
||
database/schema_v3.sql
|
||
database/schema_v4.sql
|
||
database/schema_v5.sql
|
||
database/schema_v6.sql
|
||
database/schema_v7.sql
|
||
database/schema_v8.sql
|
||
database/schema_v9.sql
|
||
database/schema_current.sql
|
||
|
||
src/database/database.c
|
||
src/database/schema.c
|
||
src/database/statement.c
|
||
src/database/transaction.c
|
||
|
||
include/database/database.h
|
||
include/database/schema.h
|
||
|
||
tests/test_database.c
|
||
tests/test_statement.c
|
||
tests/test_transaction.c
|
||
```
|