130 lines
4.9 KiB
Markdown
130 lines
4.9 KiB
Markdown
# Détecteur de schéma HFSQL (DatabaseSchemaDetector)
|
|
|
|
## Stratégie générale
|
|
|
|
Le détecteur détermine la version réelle du schéma de base (Batik ou Omika) à
|
|
partir de la **structure physique** exposée par HFSQL OLE DB, et uniquement à
|
|
partir de celle-ci.
|
|
|
|
La décision ne repose **jamais** sur :
|
|
|
|
- le nom de la base (`BATIK_TEST`, `OMIKA_TEST`, ou tout autre nom client) ;
|
|
- le nom du serveur ;
|
|
- la présence d'un mot de passe ;
|
|
- le nombre de tables ;
|
|
- OpenSchema (`GetSchema`).
|
|
|
|
Chaque canari est testé par une requête structurelle réelle et contrôlée :
|
|
|
|
```sql
|
|
SELECT TOP 0 <colonne> FROM <table>
|
|
```
|
|
|
|
Le **succès / échec structurel** de la requête indique la présence ou l'absence
|
|
de la colonne. Aucune donnée métier n'est lue (`TOP 0` ne retourne aucune ligne).
|
|
|
|
## Canaris utilisés
|
|
|
|
### Socle commun (présent dans Batik et Omika)
|
|
|
|
| Table | Colonne | Rôle |
|
|
|-------|---------|------|
|
|
| `Client` | `CL_PKID` | Confirme que la base est une base Omika/Batik compatible |
|
|
|
|
### Canaris Omika (colonnes Omika-only de `Client`)
|
|
|
|
| Table | Colonne | Rôle |
|
|
|-------|---------|------|
|
|
| `Client` | `CL_CleType` | Marqueur Omika (colonne absente de Batik) |
|
|
| `Client` | `GUID` | Marqueur Omika (colonne absente de Batik) |
|
|
|
|
### Canari de confirmation Omika (table Omika-only)
|
|
|
|
| Table | Colonne | Rôle |
|
|
|-------|---------|------|
|
|
| `Role` | `R_PKID` | Confirme la migration Omika en cas d'ambiguïté |
|
|
|
|
## Pourquoi ces canaris discriminent Batik / Omika
|
|
|
|
Les colonnes `CL_CleType` et `GUID` de la table `Client` sont marquées
|
|
`IsOmikaOnly` dans les modèles physiques générés et ont été **confirmées par le
|
|
model-audit** :
|
|
|
|
- présentes physiquement dans `OMIKA_TEST` (statut `VERIFIED`) ;
|
|
- absentes de `BATIK_TEST`.
|
|
|
|
La table `Role` est une table réellement Omika-only (absente de Batik), confirmée
|
|
par le model-audit. Elle sert de canari de confirmation indépendant.
|
|
|
|
La table `Client` est accessible en accès direct dans les deux bases, ce qui rend
|
|
la détection possible sans dépendre des mots de passe de fichiers protégés.
|
|
|
|
## Algorithme de décision
|
|
|
|
1. **Socle commun** : `SELECT TOP 0 CL_PKID FROM Client` doit réussir.
|
|
Sinon → échec explicite (base non reconnue).
|
|
2. **Canaris Omika** : tester `CL_CleType` et `GUID` dans `Client`.
|
|
3. **Canari de confirmation** : tester `R_PKID` dans `Role`.
|
|
|
|
Décision :
|
|
|
|
- `CL_CleType` **et** `GUID` présents → **Omika**.
|
|
- Un seul des deux présent → ambiguïté :
|
|
- si `Role` présent → **Omika** ;
|
|
- sinon → échec explicite (structure incohérente).
|
|
- Aucun canari Omika présent (socle commun valide) → **Batik**.
|
|
|
|
La base n'est jamais déclarée Batik ou Omika par défaut : la décision repose
|
|
toujours sur la structure réellement observée.
|
|
|
|
## Résultats d'intégration
|
|
|
|
| Base | Résultat attendu | Résultat observé |
|
|
|------|------------------|------------------|
|
|
| `BATIK_TEST` | `DatabaseSchemaVersion.Batik` | `Batik` |
|
|
| `OMIKA_TEST` | `DatabaseSchemaVersion.Omika` | `Omika` |
|
|
|
|
Les tests d'intégration réels utilisent `config/hfsql-test.local.json` et le
|
|
provider OLE DB `PCSOFT.HFSQL`. Ils sont ignorés automatiquement si la
|
|
configuration locale ou le serveur sont indisponibles.
|
|
|
|
Aucun secret, aucune chaîne de connexion, aucune donnée métier n'est exposée.
|
|
|
|
## Tests d'intégration du chemin de création (CreateAsync)
|
|
|
|
En complément de la détection de schéma, des tests d'intégration réels couvrent
|
|
le chemin d'écriture `CreateAsync` sur les deux schémas (Batik et Omika) :
|
|
|
|
- `CreateAsync_Batik_PersistsAndRollsBack`
|
|
- `CreateAsync_Omika_PersistsAndRollsBack`
|
|
|
|
### Principe
|
|
|
|
1. Les mots de passe de fichiers (Extended Properties) sont résolus par
|
|
`HfSqlFileAccessResolver` pour les fichiers nécessaires au chemin Create
|
|
(`Client`, `ParametreMetier`, `Adresse`, `Client_Adresse`).
|
|
2. Une connexion physique OLE DB est ouverte avec ces mots de passe.
|
|
3. Une **transaction externe** est créée sur cette connexion.
|
|
4. `CreateAsync` est exécuté **dans cette transaction** via le repository
|
|
(Batik ou Omika).
|
|
5. Le client canonique retourné est vérifié (nom, identifiant non vide).
|
|
6. La transaction est **annulée (rollback)** : aucune trace n'est laissée en base.
|
|
|
|
### Pourquoi une transaction externe
|
|
|
|
Les repositories `BatikClientRepository` et `OmikaClientRepository` exposent une
|
|
surcharge `CreateAsync(command, DbTransaction?, cancellationToken)` qui réutilise
|
|
une transaction externe fournie par l'appelant. En production, la surcharge
|
|
standard `CreateAsync(command, cancellationToken)` est utilisée et une transaction
|
|
interne est créée puis commitée. Dans les tests, la transaction externe permet de
|
|
**vérifier la persistance réelle puis de l'annuler** sans polluer la base.
|
|
|
|
### Garanties
|
|
|
|
- Aucune donnée métier n'est laissée en base (rollback systématique).
|
|
- Aucun secret, aucune chaîne de connexion, aucun mot de passe n'est exposé.
|
|
- Les tests sont ignorés automatiquement si la configuration locale ou le
|
|
serveur sont indisponibles.
|
|
|
|
|