v0.4.8-pre.007

This commit is contained in:
2026-08-06 00:52:08 +02:00
parent 80c439c988
commit 44088c71c9
122 changed files with 8903 additions and 3914 deletions

View File

@@ -1,5 +1,5 @@
<!-- file: docs/OPERATION_NAMING_CONVENTION.md -->
<!-- version: 2 -->
<!-- version: 3 -->
# Convention canonique des identités runtime et des codes dopération
@@ -82,6 +82,15 @@ kb-lib.materializer.transaction.annotations
Cette identité désigne le composant logiciel, pas une opération on-chain.
Pour un matérialisateur, le tracing target reprend exactement cette identité runtime. La paire avec le `processor_name` est déterministe :
```text
component_name = kb-lib.<processor_name>
processor_name = component_name sans le préfixe kb-lib.
```
Les domaines spécialisés ne doivent pas être raccourcis : utiliser `compliance.audit`, `transaction.annotations` et `token.accounts`, et non les parents génériques `compliance`, `transaction` ou `token`.
### 3.2 `processor_name`
Format :
@@ -265,4 +274,3 @@ Avant de fusionner une nouvelle opération :
6. ajouter ou mettre à jour la matrice normative ;
7. ajouter les tests de cohérence entre constantes et matrice ;
8. vérifier limpact PostgreSQL avant tout backfill ou replay durable.

View File

@@ -1,5 +1,5 @@
<!-- file: docs/README.md -->
<!-- version: 16 -->
<!-- version: 18 -->
# Documentation active de Khadhroony Bot3
@@ -40,6 +40,8 @@ Modèles documentaires non génératifs :
- [`audits/V0_4_7_PRE_016_DOCUMENTATION_AND_HEADERS_AUDIT.md`](audits/V0_4_7_PRE_016_DOCUMENTATION_AND_HEADERS_AUDIT.md) ;
- [`audits/V0_4_8_PRE_002_METADATA_CONTRACT_AUDIT.md`](audits/V0_4_8_PRE_002_METADATA_CONTRACT_AUDIT.md) ;
- [`audits/V0_4_8_PRE_007_METAPLEX_MATERIALIZER_STRUCTURE_AUDIT.md`](audits/V0_4_8_PRE_007_METAPLEX_MATERIALIZER_STRUCTURE_AUDIT.md) ;
- [`audits/V0_4_8_PRE_007_MATERIALIZER_CONVENTION_AUDIT.md`](audits/V0_4_8_PRE_007_MATERIALIZER_CONVENTION_AUDIT.md) ;
- [`decisions/DOCUMENT_ARCHIVE_SELECTION_POLICY.md`](decisions/DOCUMENT_ARCHIVE_SELECTION_POLICY.md) ;
- [`decisions/WINCODE_COMPATIBILITY_POLICY.md`](decisions/WINCODE_COMPATIBILITY_POLICY.md).
@@ -97,7 +99,9 @@ Les onze crates possèdent désormais `README.md`, `TODO.md`, `USAGE.md` et `CHA
## Audits actifs
- [`Audit contractuel 0.4.8-pre.002 — metadata`](audits/V0_4_8_PRE_002_METADATA_CONTRACT_AUDIT.md) ;
- [`Audit 0.4.8-pre.005 — instructions et historique Solana Program Metadata`](audits/V0_4_8_PRE_005_SOLANA_PROGRAM_METADATA_INSTRUCTION_HISTORY_AUDIT.md).
- [`Audit 0.4.8-pre.005 — instructions et historique Solana Program Metadata`](audits/V0_4_8_PRE_005_SOLANA_PROGRAM_METADATA_INSTRUCTION_HISTORY_AUDIT.md) ;
- [`Audit 0.4.8-pre.007 — structure du matérialiseur Metaplex Token Metadata`](audits/V0_4_8_PRE_007_METAPLEX_MATERIALIZER_STRUCTURE_AUDIT.md) ;
- [`Audit 0.4.8-pre.007 — conventions et structure de tous les matérialisateurs`](audits/V0_4_8_PRE_007_MATERIALIZER_CONVENTION_AUDIT.md).
## Plans de version actifs

View File

@@ -1,5 +1,5 @@
<!-- file: docs/audits/V0_4_8_PRE_002_METADATA_CONTRACT_AUDIT.md -->
<!-- version: 1 -->
<!-- version: 2 -->
# Audit contractuel `0.4.8-pre.002` — Solana Program Metadata et Token-2022
@@ -48,11 +48,11 @@ La structure, le Program ID, la version déclarée, les PDA, les comptes et les
### 4.1 PDA
| PDA | Seeds |
|---|---|
| canonical | `[program, seed]` |
| non-canonical | `[program, authority, seed]` |
| metadata | helper conditionnel sélectionnant lune des deux dérivations selon la présence dune autorité tierce |
| PDA | Seeds |
|---------------|------------------------------------------------------------------------------------------------------|
| canonical | `[program, seed]` |
| non-canonical | `[program, authority, seed]` |
| metadata | helper conditionnel sélectionnant lune des deux dérivations selon la présence dune autorité tierce |
`seed` est une chaîne UTF-8 de taille fixe 16 octets dans lIDL. Le code doit distinguer longueur en octets et nombre de caractères Unicode.
@@ -76,27 +76,27 @@ Ces valeurs décrivent uniquement les données on-chain. `Url` ne déclenche auc
### 4.4 Instructions
| Discriminant | Instruction | Comptes | Arguments |
|---:|---|---|---|
| `0` | `write` | `buffer` (writable)<br>`authority` (signer)<br>`sourceBuffer` (optional) | `offset: u32`<br>`data: Option<bytes>` |
| `1` | `initialize` | `metadata` (writable)<br>`authority` (signer)<br>`program`<br>`programData` (optional)<br>`system` (optional) | `seed: Seed`<br>`encoding: Encoding`<br>`compression: Compression`<br>`format: Format`<br>`dataSource: DataSource`<br>`data: Option<bytes>` |
| `2` | `setAuthority` | `account` (writable)<br>`authority` (signer)<br>`program` (optional)<br>`programData` (optional) | `newAuthority: Option<pubkey>` |
| `3` | `setData` | `metadata` (writable)<br>`authority` (signer)<br>`buffer` (writable, optional)<br>`program` (optional)<br>`programData` (optional) | `encoding: Encoding`<br>`compression: Compression`<br>`format: Format`<br>`dataSource: DataSource`<br>`data: Option<bytes>` |
| `4` | `setImmutable` | `metadata` (writable)<br>`authority` (signer)<br>`program` (optional)<br>`programData` (optional) | — |
| `5` | `trim` | `account` (writable)<br>`authority` (signer)<br>`program` (optional)<br>`programData` (optional)<br>`destination` (writable)<br>`rent` | — |
| `6` | `close` | `account` (writable)<br>`authority` (signer)<br>`program` (optional)<br>`programData` (optional)<br>`destination` (writable) | — |
| `7` | `allocate` | `buffer` (writable)<br>`authority` (signer)<br>`program` (optional)<br>`programData` (optional)<br>`system` (optional) | `seed: Option<Seed>` |
| `8` | `extend` | `account` (writable)<br>`authority` (signer)<br>`program` (optional)<br>`programData` (optional) | `length: u16` |
| Discriminant | Instruction | Comptes | Arguments |
|-------------:|----------------|----------------------------------------------------------------------------------------------------------------------------------------|---------------------------------------------------------------------------------------------------------------------------------------------|
| `0` | `write` | `buffer` (writable)<br>`authority` (signer)<br>`sourceBuffer` (optional) | `offset: u32`<br>`data: Option<bytes>` |
| `1` | `initialize` | `metadata` (writable)<br>`authority` (signer)<br>`program`<br>`programData` (optional)<br>`system` (optional) | `seed: Seed`<br>`encoding: Encoding`<br>`compression: Compression`<br>`format: Format`<br>`dataSource: DataSource`<br>`data: Option<bytes>` |
| `2` | `setAuthority` | `account` (writable)<br>`authority` (signer)<br>`program` (optional)<br>`programData` (optional) | `newAuthority: Option<pubkey>` |
| `3` | `setData` | `metadata` (writable)<br>`authority` (signer)<br>`buffer` (writable, optional)<br>`program` (optional)<br>`programData` (optional) | `encoding: Encoding`<br>`compression: Compression`<br>`format: Format`<br>`dataSource: DataSource`<br>`data: Option<bytes>` |
| `4` | `setImmutable` | `metadata` (writable)<br>`authority` (signer)<br>`program` (optional)<br>`programData` (optional) | — |
| `5` | `trim` | `account` (writable)<br>`authority` (signer)<br>`program` (optional)<br>`programData` (optional)<br>`destination` (writable)<br>`rent` | — |
| `6` | `close` | `account` (writable)<br>`authority` (signer)<br>`program` (optional)<br>`programData` (optional)<br>`destination` (writable) | — |
| `7` | `allocate` | `buffer` (writable)<br>`authority` (signer)<br>`program` (optional)<br>`programData` (optional)<br>`system` (optional) | `seed: Option<Seed>` |
| `8` | `extend` | `account` (writable)<br>`authority` (signer)<br>`program` (optional)<br>`programData` (optional) | `length: u16` |
### 4.5 Erreurs officielles
| Code | Erreur |
|---:|---|
| 0 | `NotExecutableAccount` |
| 1 | `InvalidProgramState` |
| 2 | `InvalidProgramDataAccount` |
| 3 | `ImmutableMetadataAccount` |
| 4 | `InvalidDataLength` |
| Code | Erreur |
|-----:|-----------------------------|
| 0 | `NotExecutableAccount` |
| 1 | `InvalidProgramState` |
| 2 | `InvalidProgramDataAccount` |
| 3 | `ImmutableMetadataAccount` |
| 4 | `InvalidDataLength` |
## 5. Décisions de modèles et de validation `ProgM6…`
@@ -113,13 +113,13 @@ Ces valeurs décrivent uniquement les données on-chain. `Url` ne déclenche auc
## 6. Matrice de couverture Token-2022 réelle
| Capacité | Décodage wire | Intent public | Builder | Exécution | Lecture stateful | Matérialisation | Scénario dédié | Desktop | Devnet confirmé |
|---|---|---|---|---|---|---|---|---|---|
| `Initialize` | oui | oui | oui | oui, via builder générique | état extension lisible | extension observée | non dédié | non dédié | non établi |
| `UpdateField` | oui | oui | oui | oui, via builder générique | état extension lisible | extension observée | non dédié | non dédié | non établi |
| `RemoveKey` | oui | oui | oui | oui, via builder générique | état extension lisible | extension observée | non dédié | non dédié | non établi |
| `UpdateAuthority` | oui | non | non | non | état extension lisible | extension observée | non | non | non |
| `Emit` | oui | non | non | non | résultat de retour non orchestré | non dédiée | non | non | non |
| Capacité | Décodage wire | Intent public | Builder | Exécution | Lecture stateful | Matérialisation | Scénario dédié | Desktop | Devnet confirmé |
|-------------------|---------------|---------------|---------|----------------------------|----------------------------------|--------------------|----------------|-----------|-----------------|
| `Initialize` | oui | oui | oui | oui, via builder générique | état extension lisible | extension observée | non dédié | non dédié | non établi |
| `UpdateField` | oui | oui | oui | oui, via builder générique | état extension lisible | extension observée | non dédié | non dédié | non établi |
| `RemoveKey` | oui | oui | oui | oui, via builder générique | état extension lisible | extension observée | non dédié | non dédié | non établi |
| `UpdateAuthority` | oui | non | non | non | état extension lisible | extension observée | non | non | non |
| `Emit` | oui | non | non | non | résultat de retour non orchestré | non dédiée | non | non | non |
Constats complémentaires :

View File

@@ -0,0 +1,189 @@
<!-- file: docs/audits/V0_4_8_PRE_007_MATERIALIZER_CONVENTION_AUDIT.md -->
<!-- version: 3 -->
# Audit des conventions et de la structure des matérialisateurs — `0.4.8-pre.007-fix-004`
## 1. Objet
Cet audit couvre lintégralité de `kb-lib/src/materializer` après lactivation du matérialisateur Solana Program Metadata et lextraction des projections Metaplex Token Metadata et Token-2022.
Les contrôles portent sur :
- les identités runtime et les `processorName` persistés ;
- les tracing targets ;
- la structure des façades et sous-modules ;
- lemplacement, le nommage et la réexportation des constantes ;
- les contrats communs `MtMaterializer` et `MtApiEventMaterializer` ;
- la neutralité effective des matérialisateurs encore réservés ;
- la provenance et les versions de projection des sorties actives.
## 2. Convention retenue
Chaque composant possède une paire didentités issue de son `constants.rs` :
```text
runtime component : kb-lib.materializer.<domain>[.<subsystem>]
processorName : materializer.<domain>[.<subsystem>]
```
Le `processorName` est exactement lidentité runtime privée du préfixe `kb-lib.`. Le tracing target dun composant actif est identique à son identité runtime.
Exemples :
```text
kb-lib.materializer.compliance.audit
materializer.compliance.audit
kb-lib.materializer.transaction.annotations
materializer.transaction.annotations
kb-lib.materializer.metadata.solana_program_metadata
materializer.metadata.solana_program_metadata
```
Les identités runtime servent au code et au routage des logs. Les `processorName` servent aux sorties persistées, au replay et à la provenance. Ils ne doivent pas être interchangeables.
## 3. Inventaire audité
| Composant | Type principal ou API | Statut | Identité runtime | `processorName` |
|-------------------------|---------------------------------------|------------|--------------------------------------------------------|-------------------------------------------------|
| Administration | `MtAdminMaterializer` | actif | `kb-lib.materializer.admin` | `materializer.admin` |
| Bridge | `MtBridgeMaterializer` | réservé | `kb-lib.materializer.bridge` | `materializer.bridge` |
| Compliance audit | `MtComplianceAuditMaterializer` | actif | `kb-lib.materializer.compliance.audit` | `materializer.compliance.audit` |
| Fees | `MtFeesMaterializer` | actif | `kb-lib.materializer.fees` | `materializer.fees` |
| Governance | `MtGovernanceMaterializer` | réservé | `kb-lib.materializer.governance` | `materializer.governance` |
| Lending | `MtLendingMaterializer` | réservé | `kb-lib.materializer.lending` | `materializer.lending` |
| Lifecycle | `MtLifecycleMaterializer` | actif | `kb-lib.materializer.lifecycle` | `materializer.lifecycle` |
| Liquidity | `MtLiquidityMaterializer` | réservé | `kb-lib.materializer.liquidity` | `materializer.liquidity` |
| Metaplex Token Metadata | APIs de snapshots | state-only | `kb-lib.materializer.metadata.metaplex_token_metadata` | `materializer.metadata.metaplex_token_metadata` |
| Solana Program Metadata | `MtSolanaProgramMetadataMaterializer` | actif | `kb-lib.materializer.metadata.solana_program_metadata` | `materializer.metadata.solana_program_metadata` |
| Token-2022 metadata | API de snapshots | state-only | `kb-lib.materializer.metadata.token_2022` | `materializer.metadata.token_2022` |
| NFT | `MtNftMaterializer` | réservé | `kb-lib.materializer.nft` | `materializer.nft` |
| Oracle | `MtOracleMaterializer` | réservé | `kb-lib.materializer.oracle` | `materializer.oracle` |
| Orderbook | `MtOrderbookMaterializer` | réservé | `kb-lib.materializer.orderbook` | `materializer.orderbook` |
| Perpetuals | `MtPerpetualsMaterializer` | réservé | `kb-lib.materializer.perpetuals` | `materializer.perpetuals` |
| Pool state | `MtPoolStateMaterializer` | réservé | `kb-lib.materializer.pool.state` | `materializer.pool.state` |
| Rewards | `MtRewardsMaterializer` | réservé | `kb-lib.materializer.rewards` | `materializer.rewards` |
| Risk | `MtRiskMaterializer` | actif | `kb-lib.materializer.risk` | `materializer.risk` |
| Routing | `MtRoutingMaterializer` | réservé | `kb-lib.materializer.routing` | `materializer.routing` |
| Staking | `MtStakingMaterializer` | actif | `kb-lib.materializer.staking` | `materializer.staking` |
| Token accounts | `MtTokenAccountsMaterializer` | actif | `kb-lib.materializer.token.accounts` | `materializer.token.accounts` |
| Token metadata risk | `MtTokenMetadataRiskMaterializer` | réservé | `kb-lib.materializer.token.metadata_risk` | `materializer.token.metadata_risk` |
| Trades | `MtTradesMaterializer` | réservé | `kb-lib.materializer.trades` | `materializer.trades` |
| Transaction annotations | `MtTransactionAnnotationMaterializer` | actif | `kb-lib.materializer.transaction.annotations` | `materializer.transaction.annotations` |
| Vault | `MtVaultMaterializer` | réservé | `kb-lib.materializer.vault` | `materializer.vault` |
Bilan : **25 composants nommés**, dont **9 matérialisateurs actifs**, **14 coquilles réservées** et **2 composants state-only**.
`MtMetadataMaterializer` reste un wrapper public de compatibilité vers `MtSolanaProgramMetadataMaterializer`. Il ne possède pas une identité distincte et ne crée pas un second propriétaire de projection.
## 4. Structure normalisée
Un matérialisateur simple suit désormais la structure :
```text
<component>.rs
<component>/constants.rs
<component>/materializer.rs
```
La façade `<component>.rs` ne contient que les déclarations de sous-modules et leurs réexports. Les composants complexes peuvent ajouter des fichiers spécialisés, par exemple `state.rs` ou `account.rs`, sans placer dimplémentation dans la façade.
Les domaines imbriqués suivent la même règle :
```text
compliance/audit.rs
compliance/audit/constants.rs
compliance/audit/materializer.rs
transaction/annotations.rs
transaction/annotations/constants.rs
transaction/annotations/materializer.rs
```
Les anciens noms génériques `core.rs` ont été remplacés par `materializer.rs`. Les tables de surfaces, familles acceptées, identités, versions de projection et tracing targets résident dans les `constants.rs`, sont réexportées jusquà `kb-lib/src/lib.rs` et sont consommées via `crate::`.
## 5. Coquilles réservées
Une coquille réservée doit :
- conserver son type public `Mt*Materializer` ;
- implémenter les deux traits communs ;
- exposer une constante `MT_*_ACCEPTED_FAMILIES` vide ;
- retourner `false` depuis lancien `accepts_event` ;
- retourner une liste vide depuis lancien `materialize_event` ;
- retourner `Ignored` depuis le contrat contextuel ;
- ne produire aucun événement, aucune sortie et aucune provenance fictive.
Le comportement antérieur qui pouvait retourner un événement legacy malgré une frontière inactive a été supprimé.
## 6. Provenance et versionnement
Les sorties actives utilisent uniquement leur constante `MT_*_PROCESSOR_NAME`. Aucun `processorName` littéral ne reste dans les implémentations.
Les changements de provenance Metaplex et Token-2022 livrés dans `fix-002` restent associés à `projectionVersion = 2`. Solana Program Metadata conserve `projectionVersion = 1`, car sa projection est introduite dans `0.4.8`.
Lajout dune provenance explicite aux sorties qui ne possédaient encore quune version numérique modifie leur contrat persisté. Les matérialisateurs `admin`, `compliance.audit`, `fees`, `lifecycle` et `staking` passent donc de `projectionVersion = 1` à `projectionVersion = 2`. Les matérialisateurs `risk`, `token.accounts` et `transaction.annotations` conservaient déjà une provenance spécialisée et gardent leurs versions existantes.
Les `output_key` et les familles métier existantes ne sont pas renommées par cet audit.
## 7. Configuration de logging
Les routes de `config/example.config.json` sont alignées sur les tracing targets spécialisés :
```text
kb-lib.materializer.compliance.audit
kb-lib.materializer.transaction.annotations
kb-lib.materializer.token.accounts
```
Les noms de sinks et leurs chemins sont harmonisés avec les mêmes sous-domaines.
## 8. Garde-fous ajoutés
Laudit mécanique du workspace vérifie désormais :
- la paire obligatoire `MT_*_COMPONENT_NAME` / `MT_*_PROCESSOR_NAME` ;
- la relation exacte obtenue par suppression du préfixe `kb-lib.` ;
- labsence de constantes hors `constants.rs` ;
- la présence dun `constants.rs` à côté de chaque implémentation ;
- labsence didentités littérales dans les implémentations ;
- la présence conjointe de `projectionVersion` et `processorName` dans chaque payload versionné ;
- lutilisation obligatoire des constantes `MT_*_PROJECTION_VERSION` et `MT_*_PROCESSOR_NAME` dans ces payloads ;
- la pureté des façades ;
- le résultat vide des deux contrats dune coquille réservée.
Les tests Rust conservent en plus linventaire typé des matérialisateurs et contrôlent la convention de nommage.
## 9. Fichiers obsolètes à supprimer
Les 22 chemins retirés sont fournis dans `delete-files.txt` à la racine du delta. Leur suppression est obligatoire avant la validation, car une extraction ZIP ne peut pas retirer les anciens fichiers.
## 10. Conclusion
Les matérialisateurs utilisent désormais une convention unique pour les identités runtime, les processeurs persistés, les tracing targets, les constantes, les façades et les coquilles réservées. Les différences restantes sont fonctionnelles et explicites : un composant peut être actif, réservé ou state-only, mais il ne change pas de convention structurelle ou de provenance selon son statut.
## 11. Correction des identités opérationnelles et du tracing
La compilation du workspace corrigé a révélé trois tracing targets déclarés mais sans événement réel :
- `kb-lib.materializer.fees` ;
- `kb-lib.materializer.metadata.metaplex_token_metadata` ;
- `kb-lib.materializer.metadata.token_2022`.
Le composant state-only Token-2022 réexportait également `MT_METADATA_TOKEN_2022_COMPONENT_NAME` sans le consommer dans son implémentation. Cette situation ne signifiait pas que les snapshots Token-2022 nétaient pas matérialisés : la fonction `materializer_metadata_materialize_token_2022_snapshot` produisait déjà les projections `TokenMetadata`, `TokenGroup` et `TokenGroupMember`. Elle révélait en revanche que lidentité runtime du composant nétait pas attachée à une opération observable.
Le correctif ajoute des événements structurés réels pour les chemins suivants :
- observation et snapshots de frais Token-2022 ;
- snapshots de comptes Metaplex et `MetadataV1` ;
- snapshots metadata, group et group-member Token-2022.
Les événements portent le tracing target du composant, son `component_name`, son `processor_name`, sa version, le statut et les identités disponibles. Aucun faux `let _target` nest utilisé et aucun champ persistant nest ajouté uniquement pour supprimer un warning.
Laudit mécanique refuse désormais :
- un `TRACING_TARGET_*` de `kb-lib` déclaré sans macro `tracing` réelle ;
- un `MT_*_COMPONENT_NAME` qui nest consommé par aucun fichier dimplémentation du composant.
Les composants state-only restent distincts des matérialiseurs instructionnels : ils nimplémentent pas artificiellement `MtApiEventMaterializer`, mais leur identité runtime est désormais effectivement utilisée par leurs opérations de snapshot.

View File

@@ -0,0 +1,109 @@
<!-- file: docs/audits/V0_4_8_PRE_007_METAPLEX_MATERIALIZER_STRUCTURE_AUDIT.md -->
<!-- version: 4 -->
# Audit `0.4.8-pre.007` — structure et identités des matérialiseurs metadata
## 1. Questions vérifiées
Deux ambiguïtés structurelles ont été vérifiées :
- labsence initiale dun sous-module dédié à Metaplex Token Metadata ;
- lemplacement et la couverture de la matérialisation Token-2022 Token Metadata.
Laudit a également séparé lidentité runtime dun composant de son `processorName` persisté.
## 2. Metaplex Token Metadata
Il nexistait pas doubli fonctionnel en `0.4.7`. Les APIs publiques suivantes étaient déjà implémentées :
- `materializer_metadata_materialize_metaplex_metadata_snapshot` pour létat autoritatif `MetadataV1` ;
- `materializer_metadata_materialize_metaplex_account_snapshot` pour les autres comptes Metaplex canoniques matérialisables.
Le défaut était structurel : ces fonctions partageaient auparavant `metadata/core.rs` avec dautres domaines. Elles sont désormais isolées dans :
```text
kb-lib/src/materializer/metadata/metaplex_token_metadata.rs
kb-lib/src/materializer/metadata/metaplex_token_metadata/constants.rs
kb-lib/src/materializer/metadata/metaplex_token_metadata/state.rs
kb-lib/src/materializer/metadata/metaplex_token_metadata/account.rs
```
Les clés de sortie et la sémantique métier restent inchangées. La provenance utilise désormais le `processorName` dédié :
```text
materializer.metadata.metaplex_token_metadata
```
Comme cette valeur persistée change par rapport au contrat antérieur, `projectionVersion` passe de `1` à `2`.
## 3. Token-2022 Token Metadata
Les états Token-2022 étaient déjà matérialisés par :
```text
materializer_metadata_materialize_token_2022_snapshot
```
Cette fonction projette les extensions de mint suivantes :
- `TokenMetadata` ;
- `TokenGroup` ;
- `TokenGroupMember`.
Elle était cependant placée dans `metadata/core.rs`. Le correctif lextrait vers :
```text
kb-lib/src/materializer/metadata/token_2022.rs
kb-lib/src/materializer/metadata/token_2022/constants.rs
kb-lib/src/materializer/metadata/token_2022/state.rs
```
La fonction publique et les `output_key` restent inchangées. Sa provenance utilise :
```text
materializer.metadata.token_2022
```
Le schéma de projection passe à `2` pour refléter cette correction didentité.
## 4. Écart fonctionnel Token-2022 restant
La matérialisation détat ne couvre pas à elle seule toutes les observations décodées.
Les faits `InitializeMetadataPointer` et `UpdateMetadataPointer` sont déjà possédés par le matérialiseur dadministration. En revanche, les cinq observations de `spl-token-metadata-interface` ne disposent pas encore dune matérialisation dinstruction dédiée :
- `Initialize` ;
- `UpdateField` ;
- `RemoveKey` ;
- `UpdateAuthority` ;
- `Emit`.
Cet écart doit être fermé dans `0.4.8-pre.010`, en même temps que la complétude des intents, builders, lectures avant/après et postconditions Token-2022.
## 5. Solana Program Metadata
Lidentité runtime du composant reste :
```text
kb-lib.materializer.metadata.solana_program_metadata
```
Le `processorName` persistant du composant Solana Program Metadata est corrigé en :
```text
materializer.metadata.solana_program_metadata
```
Le tracing target reste distinct et conserve son préfixe runtime :
```text
kb-lib.materializer.metadata.solana_program_metadata
```
## 6. Conséquence de migration
Les projections dérivées Metaplex et Token-2022 produites avec les anciennes provenances doivent être reconstruites depuis les raws ou migrées si elles sont conservées. Les clés de sortie ne changent pas.
## 7. Conclusion
Metaplex et les états metadata Token-2022 étaient déjà matérialisés. `pre.007-fix-002` corrige leurs identités et leur organisation modulaire. `pre.007-fix-003` étend ensuite la même convention à lintégralité des matérialisateurs ; voir `V0_4_8_PRE_007_MATERIALIZER_CONVENTION_AUDIT.md`. La seule lacune fonctionnelle confirmée concerne les cinq faits dinstructions `spl-token-metadata-interface`, explicitement reportés à `pre.010`.

View File

@@ -1,5 +1,5 @@
<!-- file: docs/guides/LOGGING.md -->
<!-- version: 1 -->
<!-- version: 2 -->
# Guide de logging et tracing
@@ -50,8 +50,13 @@ kb-pipeline.backfill
kb-pipeline.decode-replay
kb-onchain-transport.http
kb-lib.executor.spl.token-2022
kb-lib.materializer.compliance.audit
kb-lib.materializer.token.accounts
kb-lib.materializer.transaction.annotations
```
Pour un matérialisateur, la target de tracing est lidentité runtime `kb-lib.materializer.<domain>[.<subsystem>]`. Elle reste distincte du `processorName` persisté `materializer.<domain>[.<subsystem>]`, qui ne doit pas être utilisé comme target de logs.
Une nouvelle target doit être ajoutée selon `docs/OPERATION_NAMING_CONVENTION.md` et les règles Khadhroony.
## Frontend desktop

View File

@@ -1,11 +1,11 @@
<!-- file: docs/plans/V0_4_8_SOLANA_PROGRAM_METADATA_AND_TOKEN_2022_COMPLETENESS_PLAN.md -->
<!-- version: 7 -->
<!-- version: 10 -->
# Plan `0.4.8` — Solana Program Metadata et complétude Token-2022
## 1. Statut et rôle
Ce document est le livrable principal de `0.4.8-pre.001`, réconcilié après laudit contractuel de `0.4.8-pre.002`, les modèles de `pre.003`, les décodeurs de comptes de `pre.004`, le décodeur dinstructions de `pre.005` et la matérialisation de `pre.006`. Il constitue le plan vivant de la version et reste modifiable lorsque laudit du code, des interfaces officielles, de lIDL ou des validations Devnet impose un ajustement.
Ce document est le livrable principal de `0.4.8-pre.001`, réconcilié après laudit contractuel de `0.4.8-pre.002`, les modèles de `pre.003`, les décodeurs de comptes de `pre.004`, le décodeur dinstructions de `pre.005`, la matérialisation de `pre.006` et lexécuteur de `pre.007`. Il constitue le plan vivant de la version et reste modifiable lorsque laudit du code, des interfaces officielles, de lIDL ou des validations Devnet impose un ajustement.
Il doit être maintenu pendant chaque prerelease, puis archivé pendant la dernière prerelease après transfert des décisions durables vers le ROADMAP, les matrices, les guides, les rapports, les TODO et les changelogs concernés.
@@ -15,13 +15,13 @@ Il doit être maintenu pendant chaque prerelease, puis archivé pendant la derni
### 2.1 Surfaces strictement distinctes
| Surface | Program ID ou frontière | Rôle dans `0.4.8` |
|---|---|---|
| Metaplex Token Metadata | `metaqbxxUerdq28cj1RbAWkYQm3ybzjb6a8bt518x1s` | surface clôturée en `0.4.7`, hors développement principal |
| Token-2022 Token Metadata | programme Token-2022 `TokenzQdBNbLqP5VEhdkAS6EPFLC1PHnBqCXEpPxuEb` | compléter le contrat déjà partiellement pris en charge |
| `spl-token-metadata-interface` | interface sans Program ID autonome imposé | source contractuelle des instructions metadata implémentées par Token-2022 |
| Solana Program Metadata | `ProgM6JCCvbYkfKqJYHePx4xxSUSqJp7rh8Lyv7nk7S` | nouvelle surface on-chain à implémenter sous `metadata/solana_program_metadata` |
| contenu distant HTTP/IPFS/Arweave | transport off-chain indépendant | hors `0.4.8`, reporté à lhorizon `0.15+` |
| Surface | Program ID ou frontière | Rôle dans `0.4.8` |
|-----------------------------------|--------------------------------------------------------------------|---------------------------------------------------------------------------------|
| Metaplex Token Metadata | `metaqbxxUerdq28cj1RbAWkYQm3ybzjb6a8bt518x1s` | surface clôturée en `0.4.7`, hors développement principal |
| Token-2022 Token Metadata | programme Token-2022 `TokenzQdBNbLqP5VEhdkAS6EPFLC1PHnBqCXEpPxuEb` | compléter le contrat déjà partiellement pris en charge |
| `spl-token-metadata-interface` | interface sans Program ID autonome imposé | source contractuelle des instructions metadata implémentées par Token-2022 |
| Solana Program Metadata | `ProgM6JCCvbYkfKqJYHePx4xxSUSqJp7rh8Lyv7nk7S` | nouvelle surface on-chain à implémenter sous `metadata/solana_program_metadata` |
| contenu distant HTTP/IPFS/Arweave | transport off-chain indépendant | hors `0.4.8`, reporté à lhorizon `0.15+` |
Aucun décodeur Token-2022 existant nest un décodeur partiel de `ProgM6…`. Les deux contrats doivent conserver des namespaces, modèles, matrices, tests et scénarios distincts.
@@ -259,16 +259,22 @@ Résultat durable : les deux comptes décodés et les neuf instructions stables
- matrice de onze projections et test de façade externe ;
- aucune résolution de contenu distant ni lecture implicite dun compte externe.
Critère atteint côté delta : tout ce qui est décodé dans la surface `ProgM6…` est matérialisable. Compilation, Clippy et tests Rust restent à exécuter dans lenvironnement du projet avant validation définitive.
Validation définitive reçue le 5 août 2026 : `cargo fmt --all`, `cargo check --workspace`, `cargo clippy --all-targets` et laudit workspace sont propres ; `cargo test -p kb-lib` réussit avec 667 tests unitaires, les tests dAPI externes et les doc-tests.
### `0.4.8-pre.007` — builders et exécuteur Solana Program Metadata
### `0.4.8-pre.007` — builders et exécuteur Solana Program Metadata — terminé côté delta
- PDA, calculs de taille et rent ;
- builders contractuellement équivalents pour toutes les opérations courantes, y compris les mutations destructrices, irréversibles ou écrasantes ;
- politiques de signataires, autorités, coûts, confirmations, postconditions et capacités ;
- intégration explicite au cadre commun `crate::ExSafetyChecker` : le builder expose le plan complet, tandis que la politique de sécurité décide si ce plan peut progresser vers la simulation, la signature et lenvoi ;
- classification opérationnelle conforme aux règles : opérations courantes exécutables, opérations officiellement obsolètes annotées `#[deprecated]` avec approbation explicite, versions officiellement remplacées conservées en decode-only ;
- état audit actuel : les neuf instructions stables `0..8` sont courantes, sans instruction remplacée ou obsolète, donc toutes les neuf doivent être ciblées par lexécuteur sauf découverte officielle contraire documentée avant code.
Résultat durable : les neuf instructions stables possèdent une opération typée, un builder wire exact et une capacité dexécution. Les mutations dangereuses restent constructibles mais exigent une approbation explicite ; tous les plans traversent `ExSafetyChecker` avant dêtre remis à lorchestration.
- helpers de PDA canonical et non-canonical avec seed exact de 16 octets ;
- sélection de canonicité explicite dans lintent, indépendante de la seule présence de `ProgramData` ;
- builders des neuf opérations, comptes positionnels, signataires et variantes inline/Buffer ;
- simulation et quatre postconditions obligatoires ;
- approbation explicite pour `Write`, `SetAuthority`, `SetData`, `SetImmutable`, `Trim` et `Close` ;
- matrice dexécution et test dAPI externe ;
- aucune opération stable classée deprecated ou replaced faute de preuve officielle ;
- financement de rent volontairement laissé à la fixture et à lorchestration RPC : le programme exige que les comptes à allouer ou étendre soient préfinancés.
Travaux parallèles intégrés : les fonctions de matérialisation Metaplex existaient déjà dans `materializer/metadata/core.rs`; il ne sagissait donc pas dun oubli fonctionnel de `0.4.6/0.4.7`. Elles sont déplacées dans un sous-module dédié sans changement de clé métier. Token-2022 reçoit également son composant state-only dédié. Laudit est ensuite étendu à lensemble de `src/materializer` : 25 identités sont harmonisées, les façades deviennent pures, les implémentations utilisent `materializer.rs`, les constantes sont centralisées et les coquilles réservées ne produisent plus de faux événements legacy. Les constats sont consignés dans `docs/audits/V0_4_8_PRE_007_METAPLEX_MATERIALIZER_STRUCTURE_AUDIT.md` et `docs/audits/V0_4_8_PRE_007_MATERIALIZER_CONVENTION_AUDIT.md`. Un audit transversal de toutes les surfaces déjà livrées est planifié en `0.5.x` pour vérifier les règles de décodage exhaustif, propriété de matérialisation, exécution des opérations dangereuses via `ExSafetyChecker`, dépréciation officielle et versions remplacées decode-only.
### `0.4.8-pre.008` — pipeline stateful Solana Program Metadata
@@ -283,6 +289,9 @@ Critère atteint côté delta : tout ce qui est décodé dans la surface `ProgM6
### `0.4.8-pre.010` — complétude Token-2022 Token Metadata
- implémentation des écarts confirmés de `Initialize`, `UpdateField`, `RemoveKey`, `UpdateAuthority` et `Emit` ;
- conservation du matérialiseur détat dédié `metadata/token_2022/` pour les extensions `TokenMetadata`, `TokenGroup` et `TokenGroupMember` ;
- ajout dune matérialisation explicite des cinq observations dinstructions `spl-token-metadata-interface`, actuellement absente ;
- maintien de `InitializeMetadataPointer` et `UpdateMetadataPointer` dans le matérialiseur dadministration qui en possède déjà les faits ;
- tests synthétiques et stateful.
### `0.4.8-pre.011` — campagne Devnet Token-2022 Token Metadata

View File

@@ -1,5 +1,5 @@
<!-- file: docs/rules/RULES_SPECIFIC_KHADHROONY.md -->
<!-- version: 8 -->
<!-- version: 10 -->
# Règles spécifiques à `khadhroony-bot3`
@@ -53,6 +53,13 @@ Toute divergence avec une règle générale doit être explicitement documentée
- Une même réalité métier doit avoir une seule projection canonique. Les snapshots de comptes sont la source autoritative de l'état final lorsqu'ils sont disponibles ; les instructions et événements corrélés restent des observations de mutation et ne doivent pas produire un doublon concurrent du même état.
- Les matérialisateurs doivent refuser les transactions non commitées pour les mutations d'état, tout en pouvant conserver séparément une intention non commitée lorsque le modèle métier le prévoit explicitement.
- Toute absence volontaire de projection doit être documentée avec une justification technique précise. Un matérialisateur ne doit inventer ni état final, ni montant, ni autorité, ni frais, ni agrégation que l'observation ne prouve pas.
- Chaque matérialisateur concret possède un composant structuré avec une façade limitée aux déclarations de sous-modules et réexports, un `constants.rs` et un `materializer.rs`. Les fichiers spécialisés `state.rs`, `account.rs` ou équivalents sont ajoutés seulement lorsque leur responsabilité est distincte.
- Lidentité runtime suit `kb-lib.materializer.<domain>[.<subsystem>]`. Le `processorName` persisté suit `materializer.<domain>[.<subsystem>]` et doit être exactement lidentité runtime sans le préfixe `kb-lib.`. Le tracing target dun composant actif est identique à son identité runtime.
- Les constantes dun composant utilisent le préfixe `MT_<COMPONENT>_`, résident dans son `constants.rs`, sont réexportées par chaque façade jusquà `kb-lib/src/lib.rs` et sont consommées par `crate::`, y compris dans les tests lorsquelles sont `pub` ou `pub(crate)`.
- Toute sortie persistée contient un `processorName` issu de la constante du composant et une `projectionVersion` explicite. Une correction de provenance persistée impose une nouvelle version de projection.
- Une coquille réservée implémente `MtMaterializer` et `MtApiEventMaterializer`, expose une constante `MT_*_ACCEPTED_FAMILIES` vide, refuse tous les événements, retourne une liste legacy vide et un résultat contextuel `Ignored`. Elle ne doit jamais créer un faux événement de transition.
- Un composant state-only peut exposer uniquement des APIs de snapshots sans implémenter `MtApiEventMaterializer`; ce statut doit être explicite et ne crée pas artificiellement un matérialisateur instructionnel.
- Un wrapper public de compatibilité délègue vers le composant canonique et conserve exactement la même identité. Il ne constitue pas un second propriétaire de faits.
### Couverture des exécuteurs
@@ -178,7 +185,7 @@ Aucun renommage massif de modules n'est autorisé sans étape de contrôle dédi
- Les targets historiques `khbot.*` et les targets de fenêtre sont interdits dans les nouvelles modifications.
- Les macros `tracing` doivent utiliser `target: crate::TRACING_TARGET` et des champs structurés stables. La granularité interne passe par `action`, `stage`, `window`, `campaign_id`, `signature`, `instruction_path`, `program_id`, `processor_name`, `processor_version`, `status` et `error_code`.
- Les crates passives de types, contrats, DTO, API sans exécution, registres ou constantes restent sans dépendance `tracing`. `kb-config` reste une exception de bootstrap tant que sa validation précède linstallation du subscriber.
- Il est interdit dajouter `tracing` sans événement réel ou de conserver un faux target uniquement consommé par `let _target`.
- Il est interdit dajouter `tracing` sans événement réel, de conserver un tracing target déclaré mais inutilisé ou de consommer artificiellement un target avec `let _target`.
- Une décision interne doit être journalisée par la crate responsable ; `kb-app-demo-desktop` ne journalise que les frontières Tauri/UI, les actions utilisateur et les résumés dorchestration.
- Tout input sélectionné sans décodeur compatible, tout résultat de décodage `failed` ou `unsupported`, tout résultat de matérialisation `failed`, toute validation de résultat invalide et toute erreur de persistance doivent émettre un événement `error` avant le retour ou la persistance terminale.
- Une transaction Solana échouée mais correctement décodée nest pas une erreur du logiciel. Une décision `ignored`, un refus de matérialisation conforme à la politique ou une annulation coopérative ne doivent pas être promus artificiellement au niveau `error`.
@@ -187,7 +194,7 @@ Aucun renommage massif de modules n'est autorisé sans étape de contrôle dédi
- Chaque profil doit router les événements vers les sorties globales `debug.log`, `info.log`, `error.jsonl` et `app.log`, puis vers `debug.log`, `info.log` et `error.jsonl` dans un répertoire propre à chaque crate utilisant `tracing`.
- Lajout ou la suppression de `tracing.workspace = true` dans une crate impose la mise à jour simultanée de la matrice de routes, de ses tests et de `docs/TRACING_CONTRACT.md`.
- Le contrat détaillé est défini dans `docs/TRACING_CONTRACT.md`.
- Laudit mécanique spécifique au projet est exécuté par `python3 scripts/audit_khadhroony_workspace_rules.py`. Il couvre notamment `TRACING_TARGET_DECODER_METADATA_METAPLEX_TOKEN_METADATA` et lusage obligatoire de `solana_pubkey::Pubkey` à la place de `solana_address::Address`.
- Laudit mécanique spécifique au projet est exécuté par `python3 scripts/audit_khadhroony_workspace_rules.py`. Il couvre notamment les conventions de composants et `processorName` des matérialisateurs, la pureté de leurs façades, la neutralité des coquilles réservées, `TRACING_TARGET_DECODER_METADATA_METAPLEX_TOKEN_METADATA` et lusage obligatoire de `solana_pubkey::Pubkey` à la place de `solana_address::Address`.
## Règles de réutilisation des interfaces Solana et SPL