LifePlay-Revival/Docs/Migration/etat/ST/STE/STE-H3g-IMPL.md

160 lines
19 KiB
Markdown
Raw Normal View History

Fiche STE-H3g-I — Niveau N3 — Modèle prévu opus (xhigh) | utilisé claude-opus-5-5 — Agent lp-mcp-bp — Skills sk-protocol, sk-change-safety, lp-mcp, lp-lot
# STE-H3g-IMPL : garde G16 (`GI:EventGraph`, `UpdateDefaultHair`) écrite par MCP (2026-10-13)
Copie `D:\Game\LifePlay-master 5.8`, branche `ue5.8`, HEAD `0745917`. SPEC : `STE-H3g-SPEC.md` § 2.0, 2.1, 2.3, 3, 4, 7 (G16 seule ; G15 non écrite, décision Q-H3g-1 = c).
UE-GO de Big Boss reçu (fiche, rubrique 3). Éditeur headless lancé et fermé par l'agent (lp-mcp § 2). Un appel MCP par message, outils Epic seulement (aucun `hyper_*`, aucun `execute_tool_script`).
## 1. Fichiers modifiés
Un seul : `Content\BPs\GI.uasset`, graphe `/Game/BPs/GI.GI:EventGraph`, enregistré par `save_assets {asset_paths:["/Game/BPs/GI"]}` → `true`.
**Empreintes** (Git Bash, copie 5.8, `md5sum Content/BPs/GI.uasset Content/BPs/Person.uasset Content/BPs/Room.uasset "/d/Game/LifePlay_Backup_5.5/STE-H3g/Content/BPs/GI.uasset"`) :
| Fichier | Avant (17:53) | Après (18:07, éditeur fermé) |
|---|---|---|
| `Content/BPs/GI.uasset` | `c4817b847ecf246c859647577647d6e9` | **`0e6aedcccd1a6522282f9a423843ce45`** |
| instantané `D:\Game\LifePlay_Backup_5.5\STE-H3g\Content\BPs\GI.uasset` | `c4817b847ecf246c859647577647d6e9` | `c4817b847ecf246c859647577647d6e9` (inchangé) |
| `Content/BPs/Person.uasset` (autre lot, non ouvert) | `8668a47c627f7a5254910cf0ac33b12a` | `8668a47c627f7a5254910cf0ac33b12a` |
| `Content/BPs/Room.uasset` (autre lot, non ouvert) | `ca2a9a0baaca4130fd5c318797f008ae` | `ca2a9a0baaca4130fd5c318797f008ae` |
`git status --short -- Content` : avant ` M Person`, ` M Room` ; après ` M Content/BPs/GI.uasset`, ` M Content/BPs/Person.uasset`, ` M Content/BPs/Room.uasset`.
**Comptes de `GI:EventGraph`** (`find_nodes {graph:{refPath:"/Game/BPs/GI.GI:EventGraph"}, title:""}`, sortie enregistrée par le client puis comptée par `grep -o 'GI\.GI:EventGraph\.K2Node_[A-Za-z]*_[0-9]*'`) :
**6 247 → 6 251** nœuds `K2Node` (+4, exactement les 4 nouveaux) ; avec les 2 commentaires (`EdGraphNode_Comment_0`, `_1`) que `find_nodes` ne liste pas : **6 249 → 6 253**, compte du dump. Voir § 2 E1.
### 1.1 P4 : nœuds existants relus avant écriture (`get_node_infos`, deux appels de 8 nœuds)
Préfixe des `refPath` : `/Game/BPs/GI.GI:EventGraph.K2Node_`. Les 16 nœuds de la SPEC § 2.0 P4 retrouvés, **tous conformes** à la colonne « Avant » (§ 2.3.1).
| Nœud | type_id relu, position | Liens et indices relevés |
|---|---|---|
| `CustomEvent_5` | `AddEvent|Custom|UpdateDefaultHair`, (-10432, 9584) | out `then` 1 → `IfThenElse_104` (0) |
| `IfThenElse_104` | `Utilitaires|ContrôleDeFlux|Branche`, (-9872, 9600) | in `execute` 0 ← `CallFunction_250`, `CustomEvent_5` ; `Condition` 1 ← `VariableGet_3775` ; `then` 0 → `IfThenElse_65`, `else` 1 → `IfThenElse_66` |
| `IfThenElse_65` / `_66` | Branche, (-9648, 9504) / (-9712, 9744) | `Condition` ← `CallFunction_235` ; `then` 0 → `CallFunction_662` / `_661` ; `else` 1 → `CallFunction_259` / `_287` |
| `CallFunction_259` / `_287` | `|LoadHairMeshIfNeeded` | `then` 0 → `CallFunction_662` / `_661` (in 0) |
| `CallFunction_662` / `_661` | `Composants|Maillagesurfacé|SetSkinnedAssetAndUpdate`, (-9216, 9472) / (-9184, 9696) | in `execute` 0 ← `_259` + `IfThenElse_65` / `_287` + `IfThenElse_66` ; `self` 1 ← `VariableGet_241` ; `NewMesh` 2 ← `BreakStruct_12` / `_13` (0) ; `bReinitPose` 3 = `true` ; **out `then` 0 → `MacroInstance_5` / `_4` (in 0), seul lien** |
| `MacroInstance_5` / `_4` | `Utilities|Array|ForEachLoop`, (-8928, 9520) / (-8656, 9712) | in `Exec` 0 ← `CallFunction_662` / `_661` seul ; `Array` 1 ← `VariableGet_1147` / `_64` ; out `LoopBody` 0 → `CallFunction_2918` / `_2917` ; `Array Element` 1 → `BreakStruct_101` / `_100` ; `Array Index` 2 → `CallFunction_2918` / `_2917` (in 2) ; **`Completed` 3 → `CallFunction_5654` (in 0), seul lien** |
| `CallFunction_5654` | `|TurnMaterialDynamic`, (-8176, 9552) | in `execute` 0 ← `MacroInstance_4` (3), `MacroInstance_5` (3) ; `Mesh` 2 ← `VariableGet_241` ; `then` 0 → `CallFunction_237` |
| `CallFunction_237` | `|FitMorphableHair`, (-7856, 9648) | in `execute` 0 ← `CallFunction_5654` ; `self` ← `VariableGet_2404` ; `then` sans lien |
| `BreakStruct_12` / `_13` | `Utilitaires|Structure|BreakSMBool`, (-9344, 9232) / (-9216, 9872) | in `SMBool` ← `GetArrayItem_4` / `_6` ; **out `SkeletalMesh_2_93573D9945CD4136090CCBA1F1188DAC` = 0** → `VariableGet_1147` / `_64` (in 0) + `CallFunction_662` / `_661` (in 2) ; sorties 1-7 sans lien |
| `VariableGet_1147` / `_64` | `|GetMaterials`, (-9312, 9440) / (-8976, 9904) | in `self` 0 ← `BreakStruct_12` / `_13` (0) ; out `Materials` 0 → `MacroInstance_5` / `_4` (in 1) |
### 1.2 Nœuds créés (correspondance SPEC → nom réel → type_id)
Chaque `type_id` vérifié par `find_node_types {graph, type_id_filter, context_pins:[]}` juste avant son `create_node` (4 appels), nœuds relus par `get_node_infos` avant tout câblage.
| SPEC | Nœud réel (`refPath` `/Game/BPs/GI.GI:EventGraph.K2Node_…`) | Filtre → réponse | type_id de création = relu | Broches (index) | Position |
|---|---|---|---|---|---|
| G16a-V IsValid | `CallFunction_715` | `Utilitaires|IsValid` → 5 : `…IsValidSoftObjectReference`, `…IsValidSoftClassReference`, `…IsValidInterface`, `…IsValidClass`, `Utilitaires|IsValid` | `Utilitaires|IsValid` | pur ; in `Object` 0 ; out `ReturnValue` 0 | -9072, 9296 |
| G16a-B Branche | `IfThenElse_219` | `ContrôleDeFlux|Branche` → 1 : `Utilitaires|ContrôleDeFlux|Branche` | `Utilitaires|ContrôleDeFlux|Branche` | in `execute` 0, `Condition` 1 (= `true` par défaut) ; out `then` 0, `else` 1 | -8944, 9376 |
| G16b-V IsValid | `CallFunction_720` | idem G16a-V (5) | `Utilitaires|IsValid` | idem | -8960, 9600 |
| G16b-B Branche | `IfThenElse_220` | idem G16a-B (1) | `Utilitaires|ContrôleDeFlux|Branche` | idem | -8864, 9712 |
Aucun `set_pin_value`, aucun `delete_node`.
### 1.3 Coupures et liens (un appel MCP par message, réponse `null` pour chacun)
| # | Geste | Sortie (index) | Entrée (index) |
|---|---|---|---|
| C1 | `break_pins` | `CallFunction_662.then` (0) | `MacroInstance_5.Exec` (0) |
| 1 | `connect_pins` | `BreakStruct_12.SkeletalMesh_2_93573D9945CD4136090CCBA1F1188DAC` (0) | `CallFunction_715.Object` (0) |
| 2 | `connect_pins` | `CallFunction_662.then` (0) | `IfThenElse_219.execute` (0) |
| 3 | `connect_pins` | `CallFunction_715.ReturnValue` (0) | `IfThenElse_219.Condition` (1) |
| 4 | `connect_pins` | `IfThenElse_219.then` (0) | `MacroInstance_5.Exec` (0) |
| 5 | `connect_pins` | `IfThenElse_219.else` (1) | `CallFunction_5654.execute` (0) |
| C2 | `break_pins` | `CallFunction_661.then` (0) | `MacroInstance_4.Exec` (0) |
| 6 | `connect_pins` | `BreakStruct_13.SkeletalMesh_2_93573D9945CD4136090CCBA1F1188DAC` (0) | `CallFunction_720.Object` (0) |
| 7 | `connect_pins` | `CallFunction_661.then` (0) | `IfThenElse_220.execute` (0) |
| 8 | `connect_pins` | `CallFunction_720.ReturnValue` (0) | `IfThenElse_220.Condition` (1) |
| 9 | `connect_pins` | `IfThenElse_220.then` (0) | `MacroInstance_4.Exec` (0) |
| 10 | `connect_pins` | `IfThenElse_220.else` (1) | `CallFunction_5654.execute` (0) |
**Relecture** (`get_node_infos` de 20 nœuds en deux appels : les 4 nouveaux + les 16 de P4 + `CallFunction_2917` / `_2918`), conforme au § 2.3.2 :
- `CallFunction_662.then` → `IfThenElse_219.execute` **seul** ; `MacroInstance_5.Exec` ← `IfThenElse_219.then` **seul** ; idem `CallFunction_661.then` → `IfThenElse_220` seul, `MacroInstance_4.Exec` ← `IfThenElse_220.then` seul.
- `IfThenElse_219` : `Condition` ← `CallFunction_715.ReturnValue` ; `else` → `CallFunction_5654.execute`. `IfThenElse_220` : `Condition` ← `CallFunction_720.ReturnValue` ; `else` → `CallFunction_5654.execute`.
- `CallFunction_715.Object` ← `BreakStruct_12` (0) ; `CallFunction_720.Object` ← `BreakStruct_13` (0).
- `BreakStruct_12.SkeletalMesh_2_…` → `VariableGet_1147` (0), `CallFunction_662.NewMesh` (2), `CallFunction_715.Object` (0) ; `BreakStruct_13.SkeletalMesh_2_…` → `VariableGet_64`, `CallFunction_661.NewMesh`, `CallFunction_720.Object`.
- `CallFunction_5654.execute` : **4 sources** : `MacroInstance_4` (3), `MacroInstance_5` (3), `IfThenElse_219` (1), `IfThenElse_220` (1).
- Inchangés : `SetSkinnedAssetAndUpdate` ×2 (`execute`, `self`, `NewMesh`, `bReinitPose = true`), `MacroInstance_4/_5` (`Array`, `LoopBody`, `Array Element`, `Array Index`, `Completed`), `VariableGet_1147/_64`, `CallFunction_5654.then` → `CallFunction_237`, `CustomEvent_5`, `IfThenElse_104/_65/_66`, `CallFunction_259/_287`, `CallFunction_2917/_2918`.
### 1.4 Compilation et enregistrement
Journal : `D:\Game\LifePlay-master 5.8\Saved\Logs\STE-H3g-headless-20261013-175345.log` (heures UTC = locale − 2 h).
- `compile_blueprint {blueprint:{refPath:"/Game/BPs/GI.GI"}, warnings_as_errors:true}` → `null`. Journal l. 2332, `16.06.47:036` : `LogBlueprint: Compiling Blueprint '/Game/BPs/GI.GI'` ; l. 2333 `16.06.51:737` : `LogUObjectHash: Compacting …`.
`tail -n +2330 <journal> | grep -c -E 'Error|Warning'` → `0`. `hyper_blueprint_debug_inspect` non utilisé (absent du serveur, H3dI:156 ; fiche).
- `save_assets {asset_paths:["/Game/BPs/GI"]}` (`editor_toolset.toolsets.asset.AssetTools`) → `true`. Journal l. 2340, `16.07.00:306` : `Cmd: OBJ SAVEPACKAGE PACKAGE="/Game/BPs/GI" FILE="…/Content/BPs/GI.uasset" SILENT=true` ;
`16.07.04:595` : déplacement du `.tmp` vers `Content/BPs/GI.uasset` ; `AssetCheck: /Game/BPs/GI` (1 ressource validée), sans échec listé. `grep -n SAVEPACKAGE <journal>` → 2 lignes : 2274 (autosave, § 2 E4) et 2340 (seul enregistrement dans `Content`).
- Éditeur : lancé 17:54:02 (PID 36020), `Stop-Process -Id 36020` à 18:07:12 ; `Tools\UeState.ps1` à 18:07:24 → `processus=0 editeur=0 compilation=0 shaders=0 jeu=0` (code 0).
### 1.5 Garde `Accessed None` (lp-mcp § 1 règle 4) et comportement
- `IsValid` justifié : « maillage vide » est un **état normal** ici : l'entrée de `HairstyleTable` lue par `GetArrayItem_4/_6` peut rendre `SkeletalMesh_2 = None` (observé 2 fois dans HJ:16058, 16086), et l'utilisateur a décidé de garder « pas de coiffure, comme aujourd'hui » (décision Q1, SPEC § 1).
- Cascade de Branche seule, aucun AND / OR / Select. `SetSkinnedAssetAndUpdate(HairSM, None)` reste appelé avant la garde (la coiffure est toujours vidée).
- Maillage valide : `then` → boucle, chemin d'origine (établi par construction). Maillage None : `else` → `CallFunction_5654` → `CallFunction_237`, sans lecture `Materials` (estimé identique à l'exécution actuelle, voir R-H3g-4 ci-dessous).
### 1.6 Réponse au point amont R-H3g-4 (successeurs des boucles)
**Établi** (relecture `get_node_infos` du jour) : `MacroInstance_5` et `_4` n'ont, en exécution, que deux sorties reliées : `LoopBody` (0) → `CallFunction_2918` / `_2917` (`Rendu|Matériau|SetMaterial`, dont la sortie `then` (0) **n'a aucun lien**) et `Completed` (3) → `CallFunction_5654.execute` **seul**. Aucun autre successeur que `CallFunction_5654` après la boucle ; le corps de boucle s'arrête à `SetMaterial`.
Donc l'`else` des gardes (→ `CallFunction_5654`) reproduit la suite d'exécution actuelle dès que la boucle fait 0 itération. Le « 0 itération sur tableau effacé » reste **estimé** (macro `ForEachLoop` non lue, SPEC § 6) ; s'il était faux, la seule différence serait des `SetMaterial` sur `HairSM` sans maillage.
## 2. Écarts à la SPEC
- **E1 (compte)** : `find_nodes title:""` rend **6 247** nœuds avant écriture, pas 6 249. Les 2 manquants sont les commentaires du graphe, que `find_nodes` ne liste pas : le dump compte `EdGraphNode_Comment_0` et `_1` (GEV, premier listing : 6 249 noms dont 6 247 `K2Node_*`) ;
`diff` des noms `K2Node_*` du dump et de la liste MCP → aucune différence (code 0) ; `get_node_infos` sur les deux commentaires → `'EdGraphNode_Comment' object has no attribute 'get_node_title'` (objets résolus, non K2). Le graphe est donc celui du dump (MD5 identique en plus). J'ai poursuivi : l'écart est dans la méthode de comptage, pas dans l'état.
Après : 6 251 par `find_nodes` = **6 253** au sens du dump (à confirmer par le dump de VAL, § 5).
- **E2 (attente MCP)** : `Wait-HyperAIStudioMCP.ps1 -Port 8000 -UrlPath /mcp -TimeoutSeconds 540` → code 1, sans sortie, après 540 s (17:54 → 18:03), alors que le serveur écoutait depuis `15.54.14:094` UTC (journal l. 1903-1906 : `Starting MCP server on port 8000`, `Created new HttpListener on 127.0.0.1:8000` ; `Get-NetTCPConnection -LocalPort 8000` → propriétaire 36020) ; `get_current_level` a répondu `/Game/Scenes/CentralLondon`. Cause du code 1 non instruite.
- **E3 (lecture hors liste)** : un `get_node_infos` sur les deux commentaires (E1) a laissé `LogScript: Warning: 'EdGraphNode_Comment' object has no attribute 'get_node_title'` au journal (16.04.18, avant la compilation) ; lecture seule.
- **E4 (autosave)** : l'éditeur a écrit `Saved\Autosaves\Game\BPs\GI_Auto1.uasset` à `16.05.07` UTC (l. 2274, pendant le câblage). Déplacé (pas supprimé) vers `D:\Game\LifePlay_Backup_5.5\STE-H3g\autosave\GI_Auto1.uasset` (52 611 967 octets, MD5 `4740351cdf4d3733f990922f87367723`) ; plus aucun `GI_Auto*` sous `Saved\Autosaves`. Les autres autosaves (`Person_Auto1`, `Room_Auto1-4`, `TestStatic_Auto1`, `UI\MainMenu_Auto1`) préexistaient et n'ont pas été touchés.
- **E5 (P5)** : `get_node_infos` des nouveaux nœuds fait par paire (après les deux créations de chaque garde), avant tout câblage, au lieu d'un appel après chaque création.
- **E6 (budget)** : 53 tours pour un budget ≈ 50 (plafond 60).
- Aucun autre : 4 nœuds, 2 coupures, 10 liens exactement selon § 2.3.2 ; G15 non écrite ; aucun autre graphe ni asset ouvert en écriture ; Person et Room ni chargés ni enregistrés.
## 3. Instantané
Pris par l'orchestrateur avant la fiche (pas de `Snapshot.ps1` relancé) : `D:\Game\LifePlay_Backup_5.5\STE-H3g\Content\BPs\GI.uasset`, MD5 `c4817b847ecf246c859647577647d6e9` = GI de départ, relu identique après l'enregistrement. Manifeste `D:\Game\LifePlay_Backup_5.5\STE-H3g\manifest.csv` non relu par l'agent.
Retour arrière (proposé, non lancé ; décision de l'orchestrateur, éditeur fermé) : `.\Tools\Restore.ps1 -Lot STE-H3g -Only Content\BPs\GI.uasset -WhatIf`, puis sans `-WhatIf` ; MD5 attendu `c4817b847ecf246c859647577647d6e9`. Après commit : `git revert` du commit du ticket STE-H3g.
Entrée de journal (sk-change-safety) : `2026-10-13 | G16 (2 IsValid + 2 Branche) dans GI:EventGraph | Content/BPs/GI.uasset | retour arrière : Restore.ps1 -Lot STE-H3g -Only Content\BPs\GI.uasset | instantané : D:\Game\LifePlay_Backup_5.5\STE-H3g\ | vérification : 6 247 → 6 251 K2Node (+4), relecture conforme, compilation 0 / 0, MD5 0e6aedcc…`
## 4. Ce qui n'a pas été fait
- G15 (`isSameAs`) : non écrite (décision Q-H3g-1 = c) ; `isSameAs` non chargé en lecture ni en écriture.
- Dumps `LPDumpFunction` après IMPL, `CompileAllBlueprints`, `LPTestStringCompat`, build et journal de jeu : à la VAL / au BUILD (SPEC § 7).
- Cause du maillage None (piste `Daz`) : hors périmètre (SPEC § 2.3.3, R-H3g-7).
- Gel annoncé aux autres sessions et `BUILD-FIN` : à l'orchestrateur.
## 5. Points à confirmer en VAL
- Dump `-BP=GI -Fn=EventGraph -Pins -Exec` → `(6253 noeuds)` ; liens du § 7.1 de la SPEC avec les noms réels : G16a-V = `CallFunction_715`, G16a-B = `IfThenElse_219`, G16b-V = `CallFunction_720`, G16b-B = `IfThenElse_220`.
- `DiffRemplacementNoeuds.py` sur EventGraph (avant = `dumps\GI__EventGraph_P2.txt`) : seuls ces 4 nœuds, 2 coupures, 10 liens.
- **`isSameAs` reste à 11 nœuds** (G15 abandonnée : le « 15 » de la SPEC § 7.1 ne s'applique plus) ; `GetVariable` 53, `Action:EventGraph` 363, `CallFunctionReturnBool` 594 inchangés.
- `CompileAllBlueprints` éditeur fermé : BP `/Game/` 0 erreur ; `LPTestStringCompat` 3120 / 0 / 60.
- MD5 de GI = `0e6aedcccd1a6522282f9a423843ce45` au départ de la VAL ; Person `8668a47c…` et Room `ca2a9a0b…` inchangés.
- Journal de jeu (build, même ligne de commande que HJ) : `SkeletalMesh_2_93573D` 2 → 0, `UpdateDefaultHair` 4 → 0 ; `Person_24_.*of length 0` (2) et `isSameAs` (3) **attendus inchangés** (G15 non écrite) ; preuve de parcours rejoué de la SPEC § 7.4 (G16).
- R-H3g-4 : 0 itération sur tableau effacé reste estimé (§ 1.6) ; aucune autre suite d'exécution que `CallFunction_5654` (établi).
- Code 1 de `Wait-HyperAIStudioMCP.ps1` alors que le serveur répondait (E2) : à instruire hors lot.
## 6. Fichiers à commiter
Dépôt jeu, branche `ue5.8`, ticket au gardien :
- M `Content/BPs/GI.uasset`
- A `Docs/Migration/etat/ST/STE/STE-H3g-IMPL.md`
Ne pas inclure `Content/BPs/Person.uasset` ni `Content/BPs/Room.uasset` (autres lots, ` M` préexistants).
Tours : 53 / 50 (plafond 60)
## Constats
Commandes et sorties brutes (extraits) :
- Entrée : `md5sum Content/BPs/GI.uasset Content/BPs/Person.uasset Content/BPs/Room.uasset <instantané GI>` → `c4817b847ecf246c859647577647d6e9`, `8668a47c627f7a5254910cf0ac33b12a`, `ca2a9a0baaca4130fd5c318797f008ae`, `c4817b847ecf246c859647577647d6e9` ; `git rev-parse --short HEAD` → `0745917` ; `Tools/UeState.ps1` → `processus=0 editeur=0 compilation=0 shaders=0 jeu=0`.
- Lancement : `Start-Process UnrealEditor.exe "<copie>\LifePlay.uproject" -RenderOffScreen -unattended -nosplash -NoSound -ModelContextProtocolStartServer -ModelContextProtocolPort=8000 "-abslog=<copie>\Saved\Logs\STE-H3g-headless-20261013-175345.log"` → `PID=36020`, `17:54:02`. Aucune demande de recompilation de modules : `grep -i -E "modules are missing|rebuild|out of date|built with a different"` → aucune ligne utile (le seul « Took … seconds » relevé concerne la configuration).
- Comptes (`grep -o 'GI\.GI:EventGraph\.K2Node_[A-Za-z]*_[0-9]*' <sortie find_nodes>`, sorties enregistrées par le client sous `%USERPROFILE%\.claude\projects\D--Game-LifePlay-master-5-8\36e41eab-6dbf-4c01-adea-9fe53389b8ce\tool-results\mcp-unreal-mcp-call_tool-1791907424673.txt` (avant) et `…-1791907595179.txt` (après)) :
```
avant: total 6247, uniques 6247
apres: total 6251, uniques 6251, refPath 6251
-- presents dans une seule liste :
> GI.GI:EventGraph.K2Node_CallFunction_715
> GI.GI:EventGraph.K2Node_CallFunction_720
> GI.GI:EventGraph.K2Node_IfThenElse_219
> GI.GI:EventGraph.K2Node_IfThenElse_220
```
- Dump : `head -n 30176 GI__EventGraph_P2.txt | grep -E '^ [A-Za-z]' | awk '{print $1}' | sort -u | wc -l` → `6249` ; non `K2Node_` → `EdGraphNode_Comment_0`, `EdGraphNode_Comment_1` ; `K2Node_` → `6247` ; `diff` avec la liste MCP avant → code 0.
- Lignes Error / Warning du journal avant la compilation (l. 1990-2329) : sessions MCP (`Unknown session id … client should reinitialize`, `Call to unknown method "server/discover"`, 16.03.25-16.03.26, reconnexion du client), E3 (16.04.18), `LogHttp: Warning: HTTP request timed out … generate_204` (16.05.09) ; 20 `LogAutomationTest: Error: Condition failed` au démarrage (l. 1730-1747…, 15.54.13, tests du moteur au chargement). Aucune liée à GI.
- Lecture seule de Person et Room respectée : ni `load_asset`, ni `save_assets` ; MD5 identiques.