0.7.51
This commit is contained in:
@@ -338,10 +338,34 @@ La re-vérification Raydium CLMM introduit une table dédiée `k_sol_token_accou
|
||||
|
||||
Cette table permet de suivre les événements Token-2022/ATA significatifs sans les confondre avec les trades ou les liquidités.
|
||||
|
||||
## Note `0.7.50-final` — FK-safe cleanup for instruction observations
|
||||
## Note `0.7.51` — impact AMM v4 sur le modèle DB
|
||||
|
||||
`k_sol_instruction_observations` is a technical index table. When a legacy `*.instruction_audit` decoded event is replaced by a local specialized event, existing observation rows can still point to the old decoded event id on already-created SQLite databases.
|
||||
Aucune nouvelle table n'est ajoutée pour `raydium_amm_v4`.
|
||||
|
||||
The final 0.7.50 cleanup therefore unlinks `k_sol_instruction_observations.decoded_event_id` before deleting replaced CPMM instruction-audit rows. New databases define the `decoded_event_id` foreign key with `ON DELETE SET NULL` for the same reason.
|
||||
Décisions DB maintenues :
|
||||
|
||||
This is not a business-table promotion. It only keeps the technical observation index consistent with decoded event cleanup.
|
||||
- `k_sol_instruction_observations` reste une table technique d'indexation instruction/discriminant ;
|
||||
- AMM v4 utilise des discriminants d'un octet, donc l'index technique doit conserver `09`, `0b`, `10`, `11`, etc. sans les convertir en discriminants Anchor huit octets ;
|
||||
- le refresh de `k_sol_instruction_observations` reconstruit les observations par transaction avant upsert, afin de supprimer les restes historiques en huit octets après changement de stratégie d'indexation ;
|
||||
- les side effects SPL Token / Token-2022 restent transversaux et ne doivent pas être promus comme events directs `raydium_amm_v4.*` ;
|
||||
- les side effects Serum/OpenBook de AMM v4 doivent être documentés comme contexte orderbook, pas comme trades OpenBook autonomes ;
|
||||
- `raydium_pool_v4` ne justifie aucune table ni aucun decoder séparé sans corpus local.
|
||||
|
||||
Le modèle actuel suffit pour ouvrir la tranche : decoded events + coverage entries + instruction observations + matérialisations existantes trade/liquidity/lifecycle/fee/admin/orderbook. Une extension future orderbook/vault/token-account ne doit être ajoutée qu'après preuves multi-DEX.
|
||||
|
||||
|
||||
|
||||
### Clôture `0.7.51` — AMM v4 et modèle DB
|
||||
|
||||
La validation finale AMM v4 confirme qu'aucune nouvelle table n'est requise pour `raydium_amm_v4`.
|
||||
|
||||
Règles validées :
|
||||
|
||||
- chaque decoded event AMM v4 matérialisé cible au plus une table métier principale ;
|
||||
- `migrate_to_open_book`, `monitor_step` et `admin_cancel_orders` alimentent `k_sol_orderbook_events` uniquement ;
|
||||
- `pre_initialize` alimente `k_sol_pool_lifecycle_events` comme audit deprecated/partial, sans création de paire exploitable ;
|
||||
- `simulate_info` reste dans `k_sol_dex_decoded_events` uniquement ;
|
||||
- les `deposit` / `withdraw` sans pool/pair catalogue ou sans deltas exploitables restent decoded-only expliqués ;
|
||||
- les side effects SPL Token / Token-2022 restent transversaux.
|
||||
|
||||
Contrôle final AMM v4 : le SQL `materialized_target_count > 1` doit rester vide.
|
||||
|
||||
@@ -31,7 +31,7 @@ Cette matrice complète `kb_lib/src/dex_support_matrix.rs`. Elle documente **ce
|
||||
| 1 | `raydium_cpmm` | `supported / 0.7.50-pre-r2 closure recheck` | Couverture CPMM clôturée : swaps, lifecycle, fees, admin/config, deposit/withdraw, `lp_change_event`, `swap_event` decoded-only, `cpi_event` transport Carbon et `anchor_idl_instruction` Solscan/manual pour `40f4bc78a7e9690a`. | Ne pas promouvoir `anchor_idl_instruction` : c'est de la gestion Anchor IDL, pas un événement AMM métier. |
|
||||
| 2 | `raydium_clmm` | `supported / 0.7.50-pre-r2 closure recheck` | Couverture CLMM complétée : `cpi_event`, `update_dynamic_fee_config`, Program-data events locaux, `create_support_mint_associated` vers `k_sol_token_account_events`, familles sans `unknown`, router/swap Program-data en decoded-only. | Rejouer la base CLMM et confirmer que les seuls résidus sont `decoded_events_only`, transactions failed ou absence prouvée de contexte pool/pair. |
|
||||
| 3 | `raydium_launchpad` | `bootstrap / 0.7.50` | Surface canonique normalisée, 1 entrée programme + 26 discriminants Carbon/IDL listés, fallback audit/mapped decoder, SQL dédié. | Créer DB neuve, backfill par discriminant, replay forcé, promouvoir seulement après corpus local. |
|
||||
| 4 | `raydium_amm_v4` | `supported / 0.7.51 planned` | Swaps AMM v4 legacy matérialisés. | Reprendre AMM v4 au niveau CPMM/CLMM : pool lifecycle, liquidity, fees/admin, side effects, fallback cleanup. |
|
||||
| 4 | `raydium_amm_v4` | `supported / 0.7.51 closed` | Decoder maximal AMM v4 `00..11`, swaps spécialisés, lifecycle/liquidity/fees/admin/orderbook validés. | Rechecks CPMM/CLMM/Launchpad puis `raydium_stable`. |
|
||||
| 5 | `raydium_stable_swap` | `planned / 0.7.52` | Entrée conservée. | Reprendre Stable séparément : swaps stables, pool lifecycle, liquidity, fees/admin, montants/prix exploitables. |
|
||||
| 6 | `raydium_pool_v4` | `to_verify / 0.7.53 conditional audit` | IDL annexe mentionnée par fnzero, non présente dans l'archive locale, pas de program id/rôle confirmé ici. | Ne pas promouvoir tant que program id distinct, rôle exact et corpus exploitable ne sont pas confirmés. |
|
||||
| 7 | `pump_swap` | `supported / 0.7.54 planned` | `buy`/`sell` décodés et matérialisés ; trade/candle OK. | Ajouter tous les events Carbon/Solana Streamer : cashback, fee, volume accumulator, admin/config ; conserver les non-trades hors candles. |
|
||||
@@ -249,6 +249,20 @@ La clôture `0.7.50-pre-r2` complète les tranches `0.7.48` et `0.7.49` sans rou
|
||||
- Les Program-data events CLMM reçoivent des `local_event_kind` et familles explicites.
|
||||
- `create_support_mint_associated` introduit une cible métier spécialisée : `k_sol_token_account_events`.
|
||||
|
||||
## Note `0.7.50-final` — Raydium CPMM post-Launchpad recheck
|
||||
## Note `0.7.51` — `raydium_amm_v4`
|
||||
|
||||
| Champ | Décision `0.7.51` |
|
||||
|---|---|
|
||||
| Code local | `raydium_amm_v4` |
|
||||
| Program id canonique | `675kPX9MHTjS2zt1qfr1NYHuzeLXfQM9H24wFSUt1Mp8` |
|
||||
| Statut | `supported / 0.7.51 closed` ; max-decoder local `00..11` validé |
|
||||
| Sources principales | Carbon `raydium-amm-v4-decoder`, Pinax `src/raydium/amm`, fnzero `raydium_amm_v4.json`, Solscan Program IDL |
|
||||
| Swaps | `swap_base_in`, `swap_base_out`, `swap_base_in_v2`, `swap_base_out_v2` |
|
||||
| Pool lifecycle | `initialize`, `initialize2`, `pre_initialize` |
|
||||
| Liquidity | `deposit`, `withdraw` |
|
||||
| Fees/admin/orderbook side effects | `withdraw_pnl`, `withdraw_srm`, `set_params`, `monitor_step`, `admin_cancel_orders`, `migrate_to_open_book`, config account ops |
|
||||
| SPL Token / Token-2022 side effects | transversaux, non promus comme `raydium_amm_v4.*` directs |
|
||||
| `raydium_pool_v4` | audit comparatif uniquement ; pas de decoder autonome sans program id et corpus local |
|
||||
|
||||
La tranche a été validée sur base SQLite dédiée : tous les discriminants `00..11` sont observés localement. Les gaps de matérialisation restants sont expliqués par decoded-only, transaction failed ou absence de catalogue/deltas exploitables.
|
||||
|
||||
`raydium_cpmm` remains closed. The final post-Launchpad cleanup removes the three legacy `raydium_cpmm.instruction_audit` rows for discriminator `40f4bc78a7e9690a` after they have been replaced by the local decoded-only `raydium_cpmm.anchor_idl_instruction` entry. This does not promote the discriminator to a trade, liquidity, fee, admin or lifecycle event.
|
||||
|
||||
@@ -170,19 +170,22 @@ Validation attendue après replay : aucune entrée CPMM/CLMM ne doit rester en `
|
||||
|
||||
Rapport associé : `docs/reports/RAYDIUM_CPMM_CLMM_RECHECK_REPORT_0_7_50_PRE_R2.md`.
|
||||
|
||||
## Note `0.7.50-final` — CPMM audit cleanup after Launchpad recheck
|
||||
## `0.7.51` — `raydium_amm_v4`
|
||||
|
||||
The `raydium_cpmm` recheck identified a legacy residual `raydium_cpmm.instruction_audit` row for discriminator `40f4bc78a7e9690a`. The discriminator is locally mapped as `raydium_cpmm.anchor_idl_instruction` and belongs to Anchor IDL management, not to AMM business activity.
|
||||
Sources inventoriées : Carbon `raydium-amm-v4-decoder`, Pinax `src/raydium/amm`, fnzero `raydium_amm_v4.json`, Solscan Program IDL. `raydium_pool_v4` est comparé mais non promu.
|
||||
|
||||
Final rule:
|
||||
Validation locale finale : tous les discriminants AMM v4 officiels `00..11` sont observés ; `instruction_audit`, fallback upstream, decoded sans coverage, observations 8 octets, non-swap trade, failed tx trade, gaps inexpliqués et multi-target materialization sont vides.
|
||||
|
||||
| Decoder | Entry | Family | DB target | Decision |
|
||||
| Famille | Entrées AMM v4 | Statut `0.7.51-final` | Cible DB | Règle |
|
||||
|---|---|---|---|---|
|
||||
| `raydium_cpmm` | `anchor_idl_instruction` / `40f4bc78a7e9690a` | `idl_management` | `k_sol_dex_decoded_events_only` | Keep decoded-only; remove legacy `raydium_cpmm.instruction_audit` duplicates after replay/coverage refresh. |
|
||||
|
||||
Expected residual checks after final replay:
|
||||
|
||||
```text
|
||||
raydium_cpmm.instruction_audit = 0
|
||||
raydium_cpmm decoded events missing coverage row = 0
|
||||
```
|
||||
| `swap` | `swap_base_in`, `swap_base_out`, `swap_base_in_v2`, `swap_base_out_v2` | observed/materialized partiel expliqué | `k_sol_trade_events` | Trade/candle seulement si tx successful + montants vault fiables ; sinon `skipTradeReason`. |
|
||||
| `pool_create` | `initialize`, `initialize2_pool` | observed/materialized | `k_sol_pool_lifecycle_events` | Alimente lifecycle et catalogue seulement quand les mints/pool sont prouvés. |
|
||||
| `pool_create` deprecated | `pre_initialize` | observed/materialized audit minimal | `k_sol_pool_lifecycle_events` | Lifecycle deprecated/partial ; ne crée pas de pair exploitable sans mints. |
|
||||
| `liquidity_add` | `deposit` | observed/materialized partiel expliqué | `k_sol_liquidity_events` | Jamais trade/candle ; pools absents du catalogue restent decoded-only expliqués. |
|
||||
| `liquidity_remove` | `withdraw` | observed/materialized partiel expliqué | `k_sol_liquidity_events` | Jamais trade/candle ; deltas/catalogue manquants doivent être explicités. |
|
||||
| `fee` | `withdraw_pnl`, `withdraw_srm` | observed/materialized partiel expliqué | `k_sol_fee_events` | Jamais trade/candle. |
|
||||
| `admin/config` | `set_params`, `create_config_account`, `update_config_account` | observed/materialized | `k_sol_pool_admin_events` | Preuve métier par corpus uniquement. |
|
||||
| `orderbook side effects` | `monitor_step`, `migrate_to_open_book`, `admin_cancel_orders` | observed/materialized | `k_sol_orderbook_events` | Side effects OpenBook/Serum ; pas de trade OpenBook autonome, pas de lifecycle en double. |
|
||||
| `cpi/informational` | `simulate_info` | observed decoded-only | `k_sol_dex_decoded_events_only` | Audit technique uniquement. |
|
||||
| `token side effects` | SPL Token / Token-2022 inner instructions | transversal | decoded-only actuellement | Ne pas promouvoir comme AMM v4 direct. |
|
||||
| `unknown/unmapped audit` | residual `raydium_amm_v4.instruction_audit` | vide | decoded-only si futur inconnu | Tout residual doit être expliqué avant promotion. |
|
||||
|
||||
42
docs/VALIDATION_STATUS_0_7_51.md
Normal file
42
docs/VALIDATION_STATUS_0_7_51.md
Normal file
@@ -0,0 +1,42 @@
|
||||
<!-- file: VALIDATION_STATUS_0_7_51.md -->
|
||||
|
||||
# Validation status — `0.7.51 raydium_amm_v4`
|
||||
|
||||
## Commandes demandées
|
||||
|
||||
```bash
|
||||
cargo fmt
|
||||
cargo test -p kb_lib
|
||||
cargo clippy -p kb_lib --all-targets -- -D warnings
|
||||
```
|
||||
|
||||
## Résultat dans le sandbox
|
||||
|
||||
Non exécuté : `cargo`, `rustc` et `rustfmt` ne sont pas disponibles dans l'environnement de génération.
|
||||
|
||||
```text
|
||||
cargo fmt -> cargo: command not found
|
||||
```
|
||||
|
||||
## Contrôles statiques effectués
|
||||
|
||||
- Extraction et modification de l'archive `0.7.50-raydium-launchpad-final`.
|
||||
- Vérification de l'équilibre basique `{}` et `()` sur les fichiers Rust modifiés.
|
||||
- Vérification des occurrences ajoutées : aucun `unwrap` / `expect` ajouté dans les nouveaux blocs AMM v4.
|
||||
- Création des livrables docs + SQL demandés.
|
||||
|
||||
## Validation locale requise
|
||||
|
||||
Appliquer le delta, puis exécuter localement :
|
||||
|
||||
```bash
|
||||
cargo fmt
|
||||
cargo test -p kb_lib
|
||||
cargo clippy -p kb_lib --all-targets -- -D warnings
|
||||
```
|
||||
|
||||
Ensuite créer une base SQLite vide dédiée `0.7.51`, constituer le corpus Demo3/Demo2 AMM v4, replay avec `forceDexDecode=yes`, puis exécuter :
|
||||
|
||||
```text
|
||||
validation_sql/SQL_VALIDATION_RAYDIUM_AMM_V4_0_7_51.sql
|
||||
```
|
||||
47
docs/VALIDATION_STATUS_0_7_51_FINAL.md
Normal file
47
docs/VALIDATION_STATUS_0_7_51_FINAL.md
Normal file
@@ -0,0 +1,47 @@
|
||||
<!-- file: docs/VALIDATION_STATUS_0_7_51_FINAL.md -->
|
||||
|
||||
# Validation Status — `0.7.51 raydium_amm_v4 final`
|
||||
|
||||
## Rust
|
||||
|
||||
```text
|
||||
cargo test -p kb_lib -> 405 passed / 0 failed
|
||||
cargo clippy -p kb_lib --all-targets -- -D warnings -> OK
|
||||
```
|
||||
|
||||
## Replay final
|
||||
|
||||
```text
|
||||
195 replayed
|
||||
0 decode skipped
|
||||
195 ledger upserts
|
||||
70 unsafe ledger rows
|
||||
168 trades
|
||||
7 liquidity
|
||||
15 lifecycle
|
||||
0 tokenAccount
|
||||
668 candle upserts
|
||||
instructionObservations = 2599
|
||||
resetDeleted = 1578
|
||||
catalog = 61 tokens / 65 pools / 65 pairs
|
||||
```
|
||||
|
||||
## SQL blocking checks
|
||||
|
||||
Résultat attendu et rapporté : `vide` pour les contrôles suivants.
|
||||
|
||||
- `raydium_amm_v4.swap` legacy ;
|
||||
- decoded events AMM v4 sans coverage entry ;
|
||||
- observations AMM v4 en discriminant plus long qu'un octet ;
|
||||
- non-swap AMM v4 avec trade ;
|
||||
- failed tx AMM v4 avec trade ;
|
||||
- successful non-materialized AMM v4 sans raison explicite ;
|
||||
- matérialisation multi-target AMM v4.
|
||||
|
||||
## Points validés
|
||||
|
||||
- Tous les discriminants officiels AMM v4 `00..11` sont observés localement.
|
||||
- `pre_initialize` : `decoded_success_count=7`, `lifecycle_count=7`.
|
||||
- `migrate_to_open_book` : orderbook-only (`lifecycle_count=0`, `orderbook_count=6`).
|
||||
- `simulate_info` : decoded-only.
|
||||
- `raydium_pool_v4` : audit-only / décision conditionnelle, sans decoder local.
|
||||
56
docs/VALIDATION_STATUS_0_7_51_MAX_DECODER.md
Normal file
56
docs/VALIDATION_STATUS_0_7_51_MAX_DECODER.md
Normal file
@@ -0,0 +1,56 @@
|
||||
# file: VALIDATION_STATUS_0_7_51_MAX_DECODER.md
|
||||
|
||||
# Validation status — `0.7.51 raydium_amm_v4 max-decoder`
|
||||
|
||||
## Scope
|
||||
|
||||
Delta incrémental après le premier patch `0.7.51 raydium_amm_v4`.
|
||||
|
||||
Objectifs couverts :
|
||||
|
||||
- correction du test `swap_base_in` avec une payload `0x09` ;
|
||||
- ajout d'un test dédié `swap_base_in_v2` avec une payload `0x10` ;
|
||||
- suppression de la route métier legacy `raydium_amm_v4.swap` ;
|
||||
- reconnaissance locale maximale des discriminants AMM v4 officiels `00..11` ;
|
||||
- conservation des instructions dépréciées comme events decoded-only ou non-trade matérialisables si corpus successful ;
|
||||
- reclassement orderbook/fee/admin/liquidity/lifecycle pour les non-swaps AMM v4 ;
|
||||
- reconstruction des observations techniques par transaction avant upsert ;
|
||||
- extension du SQL de validation AMM v4.
|
||||
|
||||
## Sandbox validation
|
||||
|
||||
Non exécutée dans l'environnement de génération : `cargo`, `rustc` et `rustfmt` ne sont pas disponibles.
|
||||
|
||||
## Validation locale obligatoire
|
||||
|
||||
```bash
|
||||
cargo fmt
|
||||
cargo test -p kb_lib
|
||||
cargo clippy -p kb_lib --all-targets -- -D warnings
|
||||
```
|
||||
|
||||
## Replay local attendu
|
||||
|
||||
Après application du delta, relancer le replay dédié `0.7.51` avec :
|
||||
|
||||
```text
|
||||
skipDexDecode = no
|
||||
forceDexDecode = yes
|
||||
deferInstructionObservations = yes
|
||||
```
|
||||
|
||||
Puis exécuter :
|
||||
|
||||
```text
|
||||
validation_sql/SQL_VALIDATION_RAYDIUM_AMM_V4_0_7_51.sql
|
||||
```
|
||||
|
||||
Les contrôles bloquants attendus vides sont :
|
||||
|
||||
- `raydium_amm_v4.instruction_audit` résiduel ;
|
||||
- `upstream_git.instruction_match` localement couvert ;
|
||||
- `raydium_amm_v4.swap` legacy ;
|
||||
- decoded AMM v4 sans coverage entry ;
|
||||
- observations AMM v4 avec `length(discriminator_hex) > 2` ;
|
||||
- non-swap AMM v4 avec `trade_count > 0` ;
|
||||
- failed tx matérialisée en trade.
|
||||
@@ -8,7 +8,9 @@ Reprise du projet `khadhroony-bobobot` après clôture de `0.7.50 raydium_launch
|
||||
|
||||
Utiliser la dernière archive complète du workspace intégrant les deltas validés jusqu'à :
|
||||
|
||||
```text
|
||||
0.7.50-raydium-launchpad-final
|
||||
```
|
||||
|
||||
Joindre aussi les docs et SQL de validation à jour :
|
||||
|
||||
@@ -20,6 +22,7 @@ docs/DEX_DECODER_MATRIX.md
|
||||
docs/DEX_EVENT_COVERAGE_MATRIX.md
|
||||
docs/DB_EVENT_MODEL_REVIEW.md
|
||||
docs/reports/RAYDIUM_LAUNCHPAD_EVENT_COVERAGE_REPORT.md
|
||||
docs/reports/RAYDIUM_CPMM_EVENT_COVERAGE_REPORT.md
|
||||
validation_sql/SQL_VALIDATION_RAYDIUM_LAUNCHPAD_0_7_50.sql
|
||||
validation_sql/SQL_VALIDATION_RAYDIUM_CPMM_AUDIT_CLEANUP_0_7_50_FINAL.sql
|
||||
validation_sql/SQL_VALIDATION_RAYDIUM_CPMM_0_7_50_RECHECK.sql
|
||||
@@ -30,20 +33,21 @@ validation_sql/SQL_VALIDATION_RAYDIUM_CLMM_0_7_50_RECHECK.sql
|
||||
|
||||
`0.7.50` a clôturé `raydium_launchpad` et consolidé les rechecks CPMM/CLMM.
|
||||
|
||||
Dernier replay local rapporté avant clôture :
|
||||
Dernier replay local rapporté après cleanup final CPMM :
|
||||
|
||||
```text
|
||||
1103 replayed
|
||||
1124 replayed
|
||||
0 decode skipped
|
||||
1124 ledger upserts
|
||||
542 unsafe ledger rows
|
||||
539 unsafe ledger rows
|
||||
561 trades
|
||||
50 liquidity
|
||||
13 lifecycle
|
||||
0 tokenAccount
|
||||
2224 candle upserts
|
||||
instructionObservations = 7013
|
||||
instructionObservations = 7010
|
||||
resetDeleted = 1182
|
||||
catalog = 37 tokens / 40 pools / 40 pairs
|
||||
```
|
||||
|
||||
Points de clôture à préserver :
|
||||
@@ -53,13 +57,16 @@ raydium_launchpad : surface canonique, program id LanMV9sAd7wArD4vJFi2qDdfnVhFxY
|
||||
Launchpad trade_event matérialisé seulement quand corpus + successful tx le prouvent
|
||||
Launchpad initialize* fournit le catalogue pool/pair, pas de faux trade/candle
|
||||
CPMM 40f4bc78a7e9690a est raydium_cpmm.anchor_idl_instruction decoded-only
|
||||
CPMM residual raydium_cpmm.instruction_audit 40f4bc78a7e9690a doit être nettoyé après replay final
|
||||
CPMM residual raydium_cpmm.instruction_audit 40f4bc78a7e9690a = vide après replay final
|
||||
CPMM decoded event without coverage entry = vide après replay final
|
||||
CPMM upstream_git.instruction_match fallback résiduel = vide
|
||||
CPMM non-swap materialization gap hors failed tx = vide
|
||||
CLMM residual instruction_audit / upstream fallback doivent rester vides
|
||||
k_sol_instruction_observations reste une table technique, pas une table métier
|
||||
Solscan instruction=<discriminator> est une aide de découverte, pas une preuve métier
|
||||
```
|
||||
|
||||
Requête CPMM post-fix obligatoire :
|
||||
Requêtes CPMM post-fix obligatoires avant d'ouvrir `0.7.51` :
|
||||
|
||||
```sql
|
||||
SELECT
|
||||
@@ -73,7 +80,38 @@ GROUP BY discriminator_hex
|
||||
ORDER BY audit_count DESC, discriminator_hex;
|
||||
```
|
||||
|
||||
Cette requête doit être vide après replay `forceDexDecode=yes`.
|
||||
```sql
|
||||
SELECT
|
||||
de.event_kind,
|
||||
COUNT(*) AS decoded_count
|
||||
FROM k_sol_dex_decoded_events de
|
||||
LEFT JOIN k_sol_dex_event_coverage_entries ce
|
||||
ON ce.decoder_code = 'raydium_cpmm'
|
||||
AND ce.local_event_kind = de.event_kind
|
||||
WHERE de.protocol_name = 'raydium_cpmm'
|
||||
AND ce.id IS NULL
|
||||
GROUP BY de.event_kind
|
||||
ORDER BY decoded_count DESC, de.event_kind;
|
||||
```
|
||||
|
||||
Ces deux requêtes doivent être vides après replay `forceDexDecode=yes`.
|
||||
|
||||
## Décision de reprise
|
||||
|
||||
Ouvrir une nouvelle tranche :
|
||||
|
||||
```text
|
||||
0.7.51 raydium_amm_v4
|
||||
```
|
||||
|
||||
Ne pas commencer par `raydium_pool_v4` comme nouveau decoder autonome tant que son program id et son rôle métier ne sont pas prouvés localement.
|
||||
|
||||
`raydium_pool_v4` doit être traité dans `0.7.51` comme une **source à auditer / comparer** avec `raydium_amm_v4`, pas comme version déjà décidée. La roadmap peut conserver une entrée de décision `raydium_pool_v4 audit / program-id decision`, mais cette entrée doit être reformulée comme décision conditionnelle :
|
||||
|
||||
```text
|
||||
si raydium_pool_v4 correspond au même program id AMM v4 ou à un layout alternatif -> intégrer à raydium_amm_v4
|
||||
si raydium_pool_v4 correspond à un autre program id / strategy / farm / pool wrapper -> créer une tranche dédiée seulement après corpus local
|
||||
```
|
||||
|
||||
## Objectif `0.7.51` — `raydium_amm_v4`
|
||||
|
||||
@@ -84,6 +122,7 @@ swaps
|
||||
pool lifecycle / pool_create
|
||||
add_liquidity / remove_liquidity
|
||||
fees / admin/config
|
||||
open_orders / target_orders / serum/openbook side effects documentés
|
||||
side effects SPL Token / Token-2022 documentés mais non promus comme raydium_amm_v4.* directs
|
||||
fallback instruction_audit nettoyé quand une entrée locale spécialisée couvre l'instruction
|
||||
coverage entries synchronisées et rafraîchies
|
||||
@@ -108,18 +147,75 @@ https://solscan.io/account/675kPX9MHTjS2zt1qfr1NYHuzeLXfQM9H24wFSUt1Mp8#programI
|
||||
https://solscan.io/account/675kPX9MHTjS2zt1qfr1NYHuzeLXfQM9H24wFSUt1Mp8?instruction=<DISCRIMINATOR>&hide_spam=true&hide_failed=true&show_related=false&sort=desc
|
||||
```
|
||||
|
||||
## Nouvelle base de travail
|
||||
|
||||
Démarrer `0.7.51` sur une base SQLite vide dédiée.
|
||||
|
||||
Avant le replay de validation complet, prévoir un corpus initial construit volontairement :
|
||||
|
||||
```text
|
||||
1. Demo3 program_id = 675kPX9MHTjS2zt1qfr1NYHuzeLXfQM9H24wFSUt1Mp8
|
||||
2. Solscan Program IDL + instruction=<DISCRIMINATOR>
|
||||
3. backfill Demo2 de signatures contenant des instructions AMM v4 variées
|
||||
4. backfill de pools AMM v4 quand Demo3/Solscan fournit un AMM/pool account fiable
|
||||
```
|
||||
|
||||
Ne pas interpréter l'absence de résultat Solscan comme absence on-chain définitive.
|
||||
|
||||
## Sources Git/IDL à utiliser systématiquement
|
||||
|
||||
Sources globales :
|
||||
|
||||
```text
|
||||
https://github.com/sevenlabs-hq/carbon/tree/main/decoders
|
||||
https://github.com/0xfnzero/solana-streamer
|
||||
https://github.com/0xfnzero/sol-parser-sdk/tree/main/idl
|
||||
https://github.com/0xfnzero/sol-parser-sdk/tree/main/idls
|
||||
https://github.com/pinax-network/substreams-solana-idls/tree/main/src
|
||||
https://github.com/hodlwarden/solana-tx-parser/tree/main/src
|
||||
https://docs.vybenetwork.com/docs/available-dexs-amms
|
||||
```
|
||||
|
||||
Pour AMM v4, vérifier aussi les IDL/JSON Raydium legacy présents dans fnzero, notamment les fichiers autour de `raydium_amm_v4` / `raydium_pool_v4`, sans promouvoir `raydium_pool_v4` tant que son program id et son rôle métier ne sont pas prouvés localement.
|
||||
Sources spécifiques `raydium_amm_v4` à vérifier en priorité :
|
||||
|
||||
```text
|
||||
https://github.com/sevenlabs-hq/carbon/tree/main/decoders/raydium-amm-v4-decoder
|
||||
https://github.com/pinax-network/substreams-solana-idls/tree/main/src/raydium/amm
|
||||
https://github.com/0xfnzero/sol-parser-sdk/blob/main/idl/raydium_amm_v4.json
|
||||
https://github.com/0xfnzero/sol-parser-sdk/blob/main/idls/raydium_amm_v4.json
|
||||
https://github.com/0xfnzero/sol-parser-sdk/blob/main/idl/raydium_pool_v4.json
|
||||
https://github.com/0xfnzero/sol-parser-sdk/blob/main/idls/raydium_pool_v4.json
|
||||
https://solscan.io/account/675kPX9MHTjS2zt1qfr1NYHuzeLXfQM9H24wFSUt1Mp8#programIdl
|
||||
```
|
||||
|
||||
## Vérification obligatoire `raydium_pool_v4`
|
||||
|
||||
Avant de coder une tranche séparée `raydium_pool_v4`, faire une vérification explicite :
|
||||
|
||||
```text
|
||||
1. comparer idl/raydium_pool_v4.json et idls/raydium_pool_v4.json
|
||||
2. comparer idl/raydium_amm_v4.json et idls/raydium_amm_v4.json
|
||||
3. chercher si raydium_pool_v4 contient un program id explicite
|
||||
4. comparer les instructions communes : initialize, initialize2, deposit, withdraw, swapBaseIn, swapBaseOut, monitorStep, admin/config
|
||||
5. vérifier si raydium_pool_v4 décrit :
|
||||
- le même Raydium AMM v4 program id 675kPX...
|
||||
- un layout alternatif d'instruction
|
||||
- un wrapper strategy / pool / farming / lending
|
||||
- une ancienne ABI non directement liée au program id 675kPX...
|
||||
6. ne pas promouvoir `raydium_pool_v4` sans corpus local :
|
||||
- k_sol_instruction_observations
|
||||
- decoded events locaux
|
||||
- coverage local_event_kind
|
||||
- absence de fallback upstream
|
||||
```
|
||||
|
||||
Décision attendue dans `0.7.51` :
|
||||
|
||||
```text
|
||||
Option A : raydium_pool_v4 = alias/source complémentaire de raydium_amm_v4 -> intégrer ses discriminants/layouts dans raydium_amm_v4 et supprimer la version roadmap autonome.
|
||||
Option B : raydium_pool_v4 = autre program id / autre surface -> conserver une future version dédiée avec program id prouvé.
|
||||
Option C : raydium_pool_v4 = IDL ambiguë / strategy wrapper sans corpus -> garder en audit roadmap, pas de decoder local.
|
||||
```
|
||||
|
||||
## Règles fixes
|
||||
|
||||
@@ -150,10 +246,11 @@ instruction_audit et upstream_git.instruction_match doivent être nettoyés quan
|
||||
|
||||
1. Créer une nouvelle base SQLite dédiée `0.7.51`.
|
||||
2. Inventorier Carbon/fnzero/Pinax/Solscan Program IDL pour `raydium_amm_v4`.
|
||||
3. Synchroniser `k_sol_dex_event_coverage_entries` avec `decoder_code = raydium_amm_v4`.
|
||||
4. Utiliser Solscan `instruction=<discriminator>` pour obtenir rapidement des signatures non failed.
|
||||
5. Backfill Demo2 signature/pool.
|
||||
6. Replay local avec :
|
||||
3. Auditer `raydium_pool_v4` avant de décider si la roadmap garde une tranche dédiée.
|
||||
4. Synchroniser `k_sol_dex_event_coverage_entries` avec `decoder_code = raydium_amm_v4`.
|
||||
5. Utiliser Solscan `instruction=<discriminator>` pour obtenir rapidement des signatures non failed.
|
||||
6. Backfill Demo2 signature/pool sur corpus varié.
|
||||
7. Replay local avec :
|
||||
|
||||
```text
|
||||
skipDexDecode = no
|
||||
@@ -161,7 +258,7 @@ forceDexDecode = yes
|
||||
deferInstructionObservations = yes
|
||||
```
|
||||
|
||||
7. Vérifier :
|
||||
8. Vérifier :
|
||||
|
||||
```text
|
||||
coverage listed/observed/materialized
|
||||
@@ -170,6 +267,101 @@ residual upstream_git.instruction_match
|
||||
failed tx materialization = 0
|
||||
non-trade trade_count = 0
|
||||
trade/candle only for swap events validés
|
||||
raydium_pool_v4 decision documented
|
||||
```
|
||||
|
||||
## SQL de contrôle minimal `0.7.51`
|
||||
|
||||
Coverage AMM v4 :
|
||||
|
||||
```sql
|
||||
SELECT
|
||||
entry_name,
|
||||
entry_kind,
|
||||
event_family,
|
||||
expected_db_target,
|
||||
proof_status,
|
||||
local_event_kind,
|
||||
discriminator_hex,
|
||||
observed_count,
|
||||
materialized_count,
|
||||
trade_count
|
||||
FROM k_sol_dex_event_coverage_entries
|
||||
WHERE decoder_code = 'raydium_amm_v4'
|
||||
ORDER BY entry_kind, entry_name, discriminator_hex;
|
||||
```
|
||||
|
||||
Instruction observations :
|
||||
|
||||
```sql
|
||||
SELECT
|
||||
instruction_name,
|
||||
discriminator_hex,
|
||||
COUNT(*) AS observed_count,
|
||||
COUNT(DISTINCT signature) AS tx_count
|
||||
FROM k_sol_instruction_observations
|
||||
WHERE decoder_code = 'raydium_amm_v4'
|
||||
GROUP BY instruction_name, discriminator_hex
|
||||
ORDER BY observed_count DESC, instruction_name, discriminator_hex;
|
||||
```
|
||||
|
||||
Residual audit :
|
||||
|
||||
```sql
|
||||
SELECT
|
||||
json_extract(payload_json, '$.discriminatorHex') AS discriminator_hex,
|
||||
COUNT(*) AS audit_count,
|
||||
COUNT(DISTINCT transaction_id) AS tx_count
|
||||
FROM k_sol_dex_decoded_events
|
||||
WHERE protocol_name = 'raydium_amm_v4'
|
||||
AND event_kind = 'raydium_amm_v4.instruction_audit'
|
||||
GROUP BY discriminator_hex
|
||||
ORDER BY audit_count DESC, discriminator_hex;
|
||||
```
|
||||
|
||||
Fallback upstream :
|
||||
|
||||
```sql
|
||||
SELECT
|
||||
json_extract(ug.payload_json, '$.upstreamDecoderCode') AS upstream_decoder_code,
|
||||
json_extract(ug.payload_json, '$.upstreamEntryName') AS entry_name,
|
||||
json_extract(ug.payload_json, '$.upstreamDiscriminatorHex') AS discriminator_hex,
|
||||
json_extract(ug.payload_json, '$.upstreamSourceRepo') AS source_repo,
|
||||
COUNT(*) AS fallback_count,
|
||||
COUNT(DISTINCT ug.transaction_id) AS tx_count
|
||||
FROM k_sol_dex_decoded_events ug
|
||||
JOIN k_sol_dex_event_coverage_entries ce
|
||||
ON ce.decoder_code = json_extract(ug.payload_json, '$.upstreamDecoderCode')
|
||||
AND ce.entry_name = json_extract(ug.payload_json, '$.upstreamEntryName')
|
||||
AND ce.discriminator_hex = json_extract(ug.payload_json, '$.upstreamDiscriminatorHex')
|
||||
AND ce.local_event_kind IS NOT NULL
|
||||
AND ce.local_event_kind <> ''
|
||||
WHERE ug.protocol_name = 'upstream_git'
|
||||
AND ug.event_kind = 'upstream_git.instruction_match'
|
||||
AND json_extract(ug.payload_json, '$.upstreamDecoderCode') = 'raydium_amm_v4'
|
||||
GROUP BY upstream_decoder_code, entry_name, discriminator_hex, source_repo
|
||||
ORDER BY fallback_count DESC, entry_name;
|
||||
```
|
||||
|
||||
Non-swap safety :
|
||||
|
||||
```sql
|
||||
SELECT
|
||||
de.event_kind,
|
||||
ce.event_family,
|
||||
COUNT(*) AS decoded_count,
|
||||
COUNT(te.id) AS trade_count
|
||||
FROM k_sol_dex_decoded_events de
|
||||
LEFT JOIN k_sol_dex_event_coverage_entries ce
|
||||
ON ce.decoder_code = 'raydium_amm_v4'
|
||||
AND ce.local_event_kind = de.event_kind
|
||||
LEFT JOIN k_sol_trade_events te
|
||||
ON te.decoded_event_id = de.id
|
||||
WHERE de.protocol_name = 'raydium_amm_v4'
|
||||
GROUP BY de.event_kind, ce.event_family
|
||||
HAVING ce.event_family <> 'swap'
|
||||
AND COUNT(te.id) > 0
|
||||
ORDER BY trade_count DESC, de.event_kind;
|
||||
```
|
||||
|
||||
## Livrables attendus
|
||||
@@ -181,6 +373,7 @@ docs/DEX_DECODER_MATRIX.md
|
||||
docs/DEX_EVENT_COVERAGE_MATRIX.md
|
||||
docs/DB_EVENT_MODEL_REVIEW.md
|
||||
docs/reports/RAYDIUM_AMM_V4_EVENT_COVERAGE_REPORT.md
|
||||
docs/reports/RAYDIUM_POOL_V4_DECISION_NOTE.md
|
||||
validation_sql/SQL_VALIDATION_RAYDIUM_AMM_V4_0_7_51.sql
|
||||
```
|
||||
|
||||
|
||||
@@ -0,0 +1,626 @@
|
||||
<!-- file: docs/prompts/PROMPT_REPRISE_khadhroony-bobobot_0.7.52-raydium-stable.md -->
|
||||
|
||||
# Prompt de reprise — `khadhroony-bobobot` — `0.7.52 raydium_stable_swap`
|
||||
|
||||
Reprise du projet `khadhroony-bobobot` après clôture de `0.7.51 raydium_amm_v4`.
|
||||
|
||||
## Archive de départ
|
||||
|
||||
Utiliser la dernière archive complète du workspace intégrant les deltas validés jusqu’à :
|
||||
|
||||
```text
|
||||
0.7.51-raydium-amm-v4-final
|
||||
```
|
||||
|
||||
Joindre aussi les docs et SQL de validation à jour :
|
||||
|
||||
```text
|
||||
README.md
|
||||
ROADMAP.md
|
||||
CHANGELOG.md
|
||||
docs/DEX_DECODER_MATRIX.md
|
||||
docs/DEX_EVENT_COVERAGE_MATRIX.md
|
||||
docs/DB_EVENT_MODEL_REVIEW.md
|
||||
docs/reports/RAYDIUM_AMM_V4_EVENT_COVERAGE_REPORT.md
|
||||
docs/reports/RAYDIUM_POOL_V4_DECISION_NOTE.md
|
||||
docs/VALIDATION_STATUS_0_7_51_FINAL.md
|
||||
validation_sql/SQL_VALIDATION_RAYDIUM_AMM_V4_0_7_51.sql
|
||||
```
|
||||
|
||||
## État validé avant reprise
|
||||
|
||||
`0.7.51` a clôturé `raydium_amm_v4`.
|
||||
|
||||
Validation locale finale rapportée :
|
||||
|
||||
```text
|
||||
cargo test -p kb_lib
|
||||
405 passed / 0 failed
|
||||
|
||||
cargo clippy -p kb_lib --all-targets -- -D warnings
|
||||
OK
|
||||
```
|
||||
|
||||
Dernier replay local `0.7.51` :
|
||||
|
||||
```text
|
||||
195 replayed
|
||||
0 decode skipped
|
||||
195 ledger upserts
|
||||
70 unsafe ledger rows
|
||||
168 trades
|
||||
7 liquidity
|
||||
15 lifecycle
|
||||
0 tokenAccount
|
||||
668 candle upserts
|
||||
instructionObservations = 2599
|
||||
resetDeleted = 1578
|
||||
catalog = 61 tokens / 65 pools / 65 pairs
|
||||
```
|
||||
|
||||
Points de clôture AMM v4 à préserver :
|
||||
|
||||
```text
|
||||
raydium_amm_v4.swap legacy = vide
|
||||
decoded without coverage entry = vide
|
||||
instruction_observations > 1 octet = vide
|
||||
non-swap -> trade = vide
|
||||
failed tx -> trade = vide
|
||||
unexplained successful non-materialized events = vide
|
||||
multi-target materialization = vide
|
||||
pre_initialize lifecycle audit = 7 / 7
|
||||
migrate_to_open_book = orderbook only
|
||||
simulate_info = decoded-only
|
||||
raydium_pool_v4 = audit-only / pas de decoder autonome
|
||||
```
|
||||
|
||||
## Décision de reprise
|
||||
|
||||
Ouvrir une nouvelle tranche :
|
||||
|
||||
```text
|
||||
0.7.52 raydium_stable_swap
|
||||
```
|
||||
|
||||
Code local canonique :
|
||||
|
||||
```text
|
||||
raydium_stable_swap
|
||||
```
|
||||
|
||||
Program id canonique à utiliser comme hypothèse de départ :
|
||||
|
||||
```text
|
||||
5quBtoiQqxF9Jv6KYKctB59NT3gtJD2Y65kdnB1Uev3h
|
||||
```
|
||||
|
||||
Important : upstream Git/IDL/Solscan est un indice, pas une preuve métier. Le program id doit être confirmé par corpus local via `k_sol_instruction_observations`, decoded events, coverage entries et absence de fallback upstream.
|
||||
|
||||
## Nouvelle base de travail
|
||||
|
||||
Démarrer `0.7.52` sur une base SQLite vide dédiée.
|
||||
|
||||
Avant le replay de validation complet, construire volontairement un corpus initial :
|
||||
|
||||
```text
|
||||
1. Demo3 program_id = 5quBtoiQqxF9Jv6KYKctB59NT3gtJD2Y65kdnB1Uev3h
|
||||
2. Solscan non filtré + essais instruction=<DISCRIMINATOR>
|
||||
3. backfill Demo2 de signatures contenant des instructions stable swap variées
|
||||
4. backfill de pools stable swap quand Demo3/Solscan fournit un AMM/pool account fiable
|
||||
```
|
||||
|
||||
Ne pas interpréter l’absence de résultat Solscan comme absence on-chain définitive.
|
||||
|
||||
## Note Solscan importante
|
||||
|
||||
Pour `raydium_stable_swap`, il semble que Solscan ne dispose pas d’un Program IDL exploitable sur :
|
||||
|
||||
```text
|
||||
https://solscan.io/account/5quBtoiQqxF9Jv6KYKctB59NT3gtJD2Y65kdnB1Uev3h#programIdl
|
||||
```
|
||||
|
||||
Donc le filtrage Solscan par instruction peut ne pas fonctionner avec les discriminants 8 octets Carbon/Pinax.
|
||||
|
||||
Il faut tester deux approches :
|
||||
|
||||
```text
|
||||
1. Liens exploratoires courts : instruction=00, 01, 02, ...
|
||||
2. Liens discriminants upstream 8 octets : instruction=<DISCRIMINATOR_HEX>
|
||||
```
|
||||
|
||||
Solscan est une aide de découverte uniquement. La preuve métier reste locale : signatures backfillées, decoded events, instruction observations et coverage DB.
|
||||
|
||||
## Sources Git/IDL à utiliser systématiquement
|
||||
|
||||
Sources globales :
|
||||
|
||||
```text
|
||||
https://github.com/sevenlabs-hq/carbon/tree/main/decoders
|
||||
https://github.com/0xfnzero/solana-streamer
|
||||
https://github.com/0xfnzero/sol-parser-sdk/tree/main/idl
|
||||
https://github.com/0xfnzero/sol-parser-sdk/tree/main/idls
|
||||
https://github.com/pinax-network/substreams-solana-idls/tree/main/src
|
||||
https://github.com/hodlwarden/solana-tx-parser/tree/main/src
|
||||
https://docs.vybenetwork.com/docs/available-dexs-amms
|
||||
```
|
||||
|
||||
Sources spécifiques `raydium_stable_swap` à vérifier en priorité :
|
||||
|
||||
```text
|
||||
https://github.com/sevenlabs-hq/carbon/tree/main/decoders/raydium-stable-swap-decoder
|
||||
https://github.com/pinax-network/substreams-solana-idls/tree/main/src/raydium/stable
|
||||
https://github.com/pinax-network/substreams-solana-idls/tree/main/src/raydium/stable/idl.json
|
||||
https://github.com/pinax-network/substreams-solana-idls/tree/main/src/raydium/stable/instructions.rs
|
||||
https://github.com/pinax-network/substreams-solana-idls/tree/main/src/raydium/stable/events.rs
|
||||
https://github.com/pinax-network/substreams-solana-idls/tree/main/src/raydium/stable/accounts.rs
|
||||
```
|
||||
|
||||
## Solscan — liens exploratoires
|
||||
|
||||
Base non filtrée :
|
||||
|
||||
```text
|
||||
https://solscan.io/account/5quBtoiQqxF9Jv6KYKctB59NT3gtJD2Y65kdnB1Uev3h?hide_spam=false&hide_failed=false&show_related=true&sort=desc
|
||||
```
|
||||
|
||||
Base non filtrée sans related :
|
||||
|
||||
```text
|
||||
https://solscan.io/account/5quBtoiQqxF9Jv6KYKctB59NT3gtJD2Y65kdnB1Uev3h?hide_spam=false&hide_failed=false&show_related=false&sort=desc
|
||||
```
|
||||
|
||||
### Essais courts `instruction=00..11`
|
||||
|
||||
Ces liens sont exploratoires. Ils ne prouvent pas que le program utilise des discriminants 1 octet ; ils servent seulement à tester le comportement Solscan quand aucun IDL n’est présent.
|
||||
|
||||
```text
|
||||
instruction=00
|
||||
https://solscan.io/account/5quBtoiQqxF9Jv6KYKctB59NT3gtJD2Y65kdnB1Uev3h?instruction=00&hide_spam=false&hide_failed=false&show_related=false&sort=desc
|
||||
|
||||
instruction=01
|
||||
https://solscan.io/account/5quBtoiQqxF9Jv6KYKctB59NT3gtJD2Y65kdnB1Uev3h?instruction=01&hide_spam=false&hide_failed=false&show_related=false&sort=desc
|
||||
|
||||
instruction=02
|
||||
https://solscan.io/account/5quBtoiQqxF9Jv6KYKctB59NT3gtJD2Y65kdnB1Uev3h?instruction=02&hide_spam=false&hide_failed=false&show_related=false&sort=desc
|
||||
|
||||
instruction=03
|
||||
https://solscan.io/account/5quBtoiQqxF9Jv6KYKctB59NT3gtJD2Y65kdnB1Uev3h?instruction=03&hide_spam=false&hide_failed=false&show_related=false&sort=desc
|
||||
|
||||
instruction=04
|
||||
https://solscan.io/account/5quBtoiQqxF9Jv6KYKctB59NT3gtJD2Y65kdnB1Uev3h?instruction=04&hide_spam=false&hide_failed=false&show_related=false&sort=desc
|
||||
|
||||
instruction=05
|
||||
https://solscan.io/account/5quBtoiQqxF9Jv6KYKctB59NT3gtJD2Y65kdnB1Uev3h?instruction=05&hide_spam=false&hide_failed=false&show_related=false&sort=desc
|
||||
|
||||
instruction=06
|
||||
https://solscan.io/account/5quBtoiQqxF9Jv6KYKctB59NT3gtJD2Y65kdnB1Uev3h?instruction=06&hide_spam=false&hide_failed=false&show_related=false&sort=desc
|
||||
|
||||
instruction=07
|
||||
https://solscan.io/account/5quBtoiQqxF9Jv6KYKctB59NT3gtJD2Y65kdnB1Uev3h?instruction=07&hide_spam=false&hide_failed=false&show_related=false&sort=desc
|
||||
|
||||
instruction=08
|
||||
https://solscan.io/account/5quBtoiQqxF9Jv6KYKctB59NT3gtJD2Y65kdnB1Uev3h?instruction=08&hide_spam=false&hide_failed=false&show_related=false&sort=desc
|
||||
|
||||
instruction=09
|
||||
https://solscan.io/account/5quBtoiQqxF9Jv6KYKctB59NT3gtJD2Y65kdnB1Uev3h?instruction=09&hide_spam=false&hide_failed=false&show_related=false&sort=desc
|
||||
|
||||
instruction=0a
|
||||
https://solscan.io/account/5quBtoiQqxF9Jv6KYKctB59NT3gtJD2Y65kdnB1Uev3h?instruction=0a&hide_spam=false&hide_failed=false&show_related=false&sort=desc
|
||||
|
||||
instruction=0b
|
||||
https://solscan.io/account/5quBtoiQqxF9Jv6KYKctB59NT3gtJD2Y65kdnB1Uev3h?instruction=0b&hide_spam=false&hide_failed=false&show_related=false&sort=desc
|
||||
|
||||
instruction=0c
|
||||
https://solscan.io/account/5quBtoiQqxF9Jv6KYKctB59NT3gtJD2Y65kdnB1Uev3h?instruction=0c&hide_spam=false&hide_failed=false&show_related=false&sort=desc
|
||||
|
||||
instruction=0d
|
||||
https://solscan.io/account/5quBtoiQqxF9Jv6KYKctB59NT3gtJD2Y65kdnB1Uev3h?instruction=0d&hide_spam=false&hide_failed=false&show_related=false&sort=desc
|
||||
|
||||
instruction=0e
|
||||
https://solscan.io/account/5quBtoiQqxF9Jv6KYKctB59NT3gtJD2Y65kdnB1Uev3h?instruction=0e&hide_spam=false&hide_failed=false&show_related=false&sort=desc
|
||||
|
||||
instruction=0f
|
||||
https://solscan.io/account/5quBtoiQqxF9Jv6KYKctB59NT3gtJD2Y65kdnB1Uev3h?instruction=0f&hide_spam=false&hide_failed=false&show_related=false&sort=desc
|
||||
|
||||
instruction=10
|
||||
https://solscan.io/account/5quBtoiQqxF9Jv6KYKctB59NT3gtJD2Y65kdnB1Uev3h?instruction=10&hide_spam=false&hide_failed=false&show_related=false&sort=desc
|
||||
|
||||
instruction=11
|
||||
https://solscan.io/account/5quBtoiQqxF9Jv6KYKctB59NT3gtJD2Y65kdnB1Uev3h?instruction=11&hide_spam=false&hide_failed=false&show_related=false&sort=desc
|
||||
```
|
||||
|
||||
### Essais discriminants 8 octets Carbon/Pinax
|
||||
|
||||
À tester aussi, mais ne pas bloquer si Solscan ne filtre rien.
|
||||
|
||||
```text
|
||||
initialize / afaf6d1f0d989bed
|
||||
https://solscan.io/account/5quBtoiQqxF9Jv6KYKctB59NT3gtJD2Y65kdnB1Uev3h?instruction=afaf6d1f0d989bed&hide_spam=false&hide_failed=false&show_related=false&sort=desc
|
||||
|
||||
pre_initialize / ff5c572dc6acec02
|
||||
https://solscan.io/account/5quBtoiQqxF9Jv6KYKctB59NT3gtJD2Y65kdnB1Uev3h?instruction=ff5c572dc6acec02&hide_spam=false&hide_failed=false&show_related=false&sort=desc
|
||||
|
||||
deposit / f223c68952e1f2b6
|
||||
https://solscan.io/account/5quBtoiQqxF9Jv6KYKctB59NT3gtJD2Y65kdnB1Uev3h?instruction=f223c68952e1f2b6&hide_spam=false&hide_failed=false&show_related=false&sort=desc
|
||||
|
||||
withdraw / b712469c946da122
|
||||
https://solscan.io/account/5quBtoiQqxF9Jv6KYKctB59NT3gtJD2Y65kdnB1Uev3h?instruction=b712469c946da122&hide_spam=false&hide_failed=false&show_related=false&sort=desc
|
||||
|
||||
swap_base_in / 2aec48a2f2182754
|
||||
https://solscan.io/account/5quBtoiQqxF9Jv6KYKctB59NT3gtJD2Y65kdnB1Uev3h?instruction=2aec48a2f2182754&hide_spam=false&hide_failed=false&show_related=false&sort=desc
|
||||
|
||||
swap_base_out / a3d29bd0af92d596
|
||||
https://solscan.io/account/5quBtoiQqxF9Jv6KYKctB59NT3gtJD2Y65kdnB1Uev3h?instruction=a3d29bd0af92d596&hide_spam=false&hide_failed=false&show_related=false&sort=desc
|
||||
```
|
||||
|
||||
## Instructions/discriminants de départ à couvrir
|
||||
|
||||
À partir de Carbon stable swap, à vérifier contre Pinax :
|
||||
|
||||
```text
|
||||
initialize afaf6d1f0d989bed pool_create / k_sol_pool_lifecycle_events
|
||||
pre_initialize ff5c572dc6acec02 pool_create deprecated/partial / k_sol_pool_lifecycle_events si pool context suffisant
|
||||
deposit f223c68952e1f2b6 liquidity_add / k_sol_liquidity_events
|
||||
withdraw b712469c946da122 liquidity_remove / k_sol_liquidity_events
|
||||
swap_base_in 2aec48a2f2182754 swap / k_sol_trade_events
|
||||
swap_base_out a3d29bd0af92d596 swap / k_sol_trade_events
|
||||
```
|
||||
|
||||
Si Pinax expose des discriminants numériques ou une ABI non Anchor, ne pas forcer les discriminants 8 octets. Le decoder local doit suivre le layout prouvé par corpus local.
|
||||
|
||||
## Objectif `0.7.52` — `raydium_stable_swap`
|
||||
|
||||
Reprendre Raydium Stable Swap au même niveau de couverture que CPMM/CLMM/AMM v4 :
|
||||
|
||||
```text
|
||||
initialize / pre_initialize
|
||||
pool lifecycle / pool_create
|
||||
deposit / withdraw
|
||||
swap_base_in / swap_base_out
|
||||
fees / admin/config si présents dans IDL/events/accounts
|
||||
OpenBook/Serum side effects documentés si présents
|
||||
side effects SPL Token / Token-2022 documentés mais non promus comme raydium_stable_swap.* directs
|
||||
fallback instruction_audit nettoyé quand une entrée locale spécialisée couvre l’instruction
|
||||
coverage entries synchronisées et rafraîchies
|
||||
decoded-only explicitement expliqué quand la matérialisation métier est impossible
|
||||
```
|
||||
|
||||
## Règles fixes
|
||||
|
||||
```text
|
||||
Rust 2024
|
||||
pas de mod.rs
|
||||
fichiers Rust avec // file: ...
|
||||
pas de anyhow
|
||||
pas de thiserror
|
||||
pas de ? / unwrap / expect dans kb_lib applicatif
|
||||
match / if let Err / let Err = ... else
|
||||
rustdoc sur API publique
|
||||
re-exports db.rs puis lib.rs si DB modifiée
|
||||
```
|
||||
|
||||
## Invariants métier
|
||||
|
||||
```text
|
||||
non-trade event = jamais trade/candle
|
||||
failed transaction = audit-only / jamais matérialisée métier
|
||||
upstream Git/IDL/Solscan = indice, pas preuve métier
|
||||
program id upstream non promu sans corpus local
|
||||
side effects SPL Token / Token-2022 restent transversaux sauf preuve multi-DEX et décision DB
|
||||
instruction_audit et upstream_git.instruction_match doivent être nettoyés quand une entrée locale spécialisée couvre le discriminant
|
||||
observed_count ne doit pas obligatoirement égaler materialized_count
|
||||
règle de clôture : observed_count = materialized_count + decoded_only_explained_count + failed_count
|
||||
```
|
||||
|
||||
## Workflow conseillé
|
||||
|
||||
1. Créer une nouvelle base SQLite dédiée `0.7.52`.
|
||||
2. Inventorier Carbon + Pinax pour `raydium_stable_swap`.
|
||||
3. Vérifier explicitement le program id `5quBtoiQqxF9Jv6KYKctB59NT3gtJD2Y65kdnB1Uev3h`.
|
||||
4. Vérifier si les discriminants sont 8 octets Anchor-like, 1 octet, ou autre layout.
|
||||
5. Synchroniser `k_sol_dex_event_coverage_entries` avec `decoder_code = raydium_stable_swap`.
|
||||
6. Utiliser Solscan seulement comme aide exploratoire ; si le filtre instruction échoue, utiliser Demo3 program_id + signatures récentes/non filtrées.
|
||||
7. Backfill Demo2 signature/pool sur corpus varié.
|
||||
8. Replay local avec :
|
||||
|
||||
```text
|
||||
skipDexDecode = no
|
||||
forceDexDecode = yes
|
||||
deferInstructionObservations = yes
|
||||
```
|
||||
|
||||
9. Vérifier :
|
||||
|
||||
```text
|
||||
coverage listed/observed/materialized
|
||||
residual instruction_audit
|
||||
residual upstream_git.instruction_match
|
||||
decoded without coverage entry
|
||||
failed tx materialization = 0
|
||||
non-trade trade_count = 0
|
||||
single-target materialization
|
||||
trade/candle only for swap events validés
|
||||
decoded-only explanations
|
||||
```
|
||||
|
||||
## SQL de contrôle minimal `0.7.52`
|
||||
|
||||
Coverage stable swap :
|
||||
|
||||
```sql
|
||||
SELECT
|
||||
entry_name,
|
||||
entry_kind,
|
||||
event_family,
|
||||
expected_db_target,
|
||||
proof_status,
|
||||
local_event_kind,
|
||||
discriminator_hex,
|
||||
observed_count,
|
||||
materialized_count,
|
||||
trade_count
|
||||
FROM k_sol_dex_event_coverage_entries
|
||||
WHERE decoder_code = 'raydium_stable_swap'
|
||||
ORDER BY entry_kind, entry_name, discriminator_hex;
|
||||
```
|
||||
|
||||
Instruction observations :
|
||||
|
||||
```sql
|
||||
SELECT
|
||||
instruction_name,
|
||||
discriminator_hex,
|
||||
COUNT(*) AS observed_count,
|
||||
COUNT(DISTINCT signature) AS tx_count
|
||||
FROM k_sol_instruction_observations
|
||||
WHERE decoder_code = 'raydium_stable_swap'
|
||||
GROUP BY instruction_name, discriminator_hex
|
||||
ORDER BY observed_count DESC, instruction_name, discriminator_hex;
|
||||
```
|
||||
|
||||
Residual audit :
|
||||
|
||||
```sql
|
||||
SELECT
|
||||
json_extract(payload_json, '$.discriminatorHex') AS discriminator_hex,
|
||||
COUNT(*) AS audit_count,
|
||||
COUNT(DISTINCT transaction_id) AS tx_count
|
||||
FROM k_sol_dex_decoded_events
|
||||
WHERE protocol_name = 'raydium_stable_swap'
|
||||
AND event_kind = 'raydium_stable_swap.instruction_audit'
|
||||
GROUP BY discriminator_hex
|
||||
ORDER BY audit_count DESC, discriminator_hex;
|
||||
```
|
||||
|
||||
Fallback upstream :
|
||||
|
||||
```sql
|
||||
SELECT
|
||||
json_extract(ug.payload_json, '$.upstreamDecoderCode') AS upstream_decoder_code,
|
||||
json_extract(ug.payload_json, '$.upstreamEntryName') AS entry_name,
|
||||
json_extract(ug.payload_json, '$.upstreamDiscriminatorHex') AS discriminator_hex,
|
||||
json_extract(ug.payload_json, '$.upstreamSourceRepo') AS source_repo,
|
||||
COUNT(*) AS fallback_count,
|
||||
COUNT(DISTINCT ug.transaction_id) AS tx_count
|
||||
FROM k_sol_dex_decoded_events ug
|
||||
JOIN k_sol_dex_event_coverage_entries ce
|
||||
ON ce.decoder_code = json_extract(ug.payload_json, '$.upstreamDecoderCode')
|
||||
AND ce.entry_name = json_extract(ug.payload_json, '$.upstreamEntryName')
|
||||
AND ce.discriminator_hex = json_extract(ug.payload_json, '$.upstreamDiscriminatorHex')
|
||||
AND ce.local_event_kind IS NOT NULL
|
||||
AND ce.local_event_kind <> ''
|
||||
WHERE ug.protocol_name = 'upstream_git'
|
||||
AND ug.event_kind = 'upstream_git.instruction_match'
|
||||
AND json_extract(ug.payload_json, '$.upstreamDecoderCode') = 'raydium_stable_swap'
|
||||
GROUP BY upstream_decoder_code, entry_name, discriminator_hex, source_repo
|
||||
ORDER BY fallback_count DESC, entry_name;
|
||||
```
|
||||
|
||||
Non-swap safety :
|
||||
|
||||
```sql
|
||||
SELECT
|
||||
de.event_kind,
|
||||
ce.event_family,
|
||||
COUNT(*) AS decoded_count,
|
||||
COUNT(te.id) AS trade_count
|
||||
FROM k_sol_dex_decoded_events de
|
||||
LEFT JOIN k_sol_dex_event_coverage_entries ce
|
||||
ON ce.decoder_code = 'raydium_stable_swap'
|
||||
AND ce.local_event_kind = de.event_kind
|
||||
LEFT JOIN k_sol_trade_events te
|
||||
ON te.decoded_event_id = de.id
|
||||
WHERE de.protocol_name = 'raydium_stable_swap'
|
||||
GROUP BY de.event_kind, ce.event_family
|
||||
HAVING ce.event_family <> 'swap'
|
||||
AND COUNT(te.id) > 0
|
||||
ORDER BY trade_count DESC, de.event_kind;
|
||||
```
|
||||
|
||||
Failed tx safety :
|
||||
|
||||
```sql
|
||||
SELECT
|
||||
de.event_kind,
|
||||
COUNT(*) AS decoded_failed_count,
|
||||
COUNT(te.id) AS trade_count
|
||||
FROM k_sol_dex_decoded_events de
|
||||
JOIN k_sol_chain_transactions tx
|
||||
ON tx.id = de.transaction_id
|
||||
LEFT JOIN k_sol_trade_events te
|
||||
ON te.decoded_event_id = de.id
|
||||
WHERE de.protocol_name = 'raydium_stable_swap'
|
||||
AND tx.err_json IS NOT NULL
|
||||
AND tx.err_json <> ''
|
||||
AND tx.err_json <> 'null'
|
||||
GROUP BY de.event_kind
|
||||
HAVING COUNT(te.id) > 0
|
||||
ORDER BY trade_count DESC, de.event_kind;
|
||||
```
|
||||
|
||||
Decoded without coverage :
|
||||
|
||||
```sql
|
||||
SELECT
|
||||
de.event_kind,
|
||||
COUNT(*) AS decoded_count
|
||||
FROM k_sol_dex_decoded_events de
|
||||
LEFT JOIN k_sol_dex_event_coverage_entries ce
|
||||
ON ce.decoder_code = 'raydium_stable_swap'
|
||||
AND ce.local_event_kind = de.event_kind
|
||||
WHERE de.protocol_name = 'raydium_stable_swap'
|
||||
AND ce.id IS NULL
|
||||
GROUP BY de.event_kind
|
||||
ORDER BY decoded_count DESC, de.event_kind;
|
||||
```
|
||||
|
||||
Multi-target materialization :
|
||||
|
||||
```sql
|
||||
SELECT
|
||||
de.event_kind,
|
||||
COUNT(DISTINCT de.id) AS decoded_count,
|
||||
COUNT(DISTINCT te.id) AS trade_count,
|
||||
COUNT(DISTINCT le.id) AS liquidity_count,
|
||||
COUNT(DISTINCT pe.id) AS lifecycle_count,
|
||||
COUNT(DISTINCT fe.id) AS fee_count,
|
||||
COUNT(DISTINCT ae.id) AS admin_count,
|
||||
COUNT(DISTINCT oe.id) AS orderbook_count,
|
||||
(
|
||||
CASE WHEN COUNT(DISTINCT te.id) > 0 THEN 1 ELSE 0 END
|
||||
+ CASE WHEN COUNT(DISTINCT le.id) > 0 THEN 1 ELSE 0 END
|
||||
+ CASE WHEN COUNT(DISTINCT pe.id) > 0 THEN 1 ELSE 0 END
|
||||
+ CASE WHEN COUNT(DISTINCT fe.id) > 0 THEN 1 ELSE 0 END
|
||||
+ CASE WHEN COUNT(DISTINCT ae.id) > 0 THEN 1 ELSE 0 END
|
||||
+ CASE WHEN COUNT(DISTINCT oe.id) > 0 THEN 1 ELSE 0 END
|
||||
) AS materialized_target_count
|
||||
FROM k_sol_dex_decoded_events de
|
||||
LEFT JOIN k_sol_trade_events te
|
||||
ON te.decoded_event_id = de.id
|
||||
LEFT JOIN k_sol_liquidity_events le
|
||||
ON le.decoded_event_id = de.id
|
||||
LEFT JOIN k_sol_pool_lifecycle_events pe
|
||||
ON pe.decoded_event_id = de.id
|
||||
LEFT JOIN k_sol_fee_events fe
|
||||
ON fe.decoded_event_id = de.id
|
||||
LEFT JOIN k_sol_pool_admin_events ae
|
||||
ON ae.decoded_event_id = de.id
|
||||
LEFT JOIN k_sol_orderbook_events oe
|
||||
ON oe.decoded_event_id = de.id
|
||||
WHERE de.protocol_name = 'raydium_stable_swap'
|
||||
GROUP BY de.event_kind
|
||||
HAVING materialized_target_count > 1
|
||||
ORDER BY materialized_target_count DESC, de.event_kind;
|
||||
```
|
||||
|
||||
Unexplained successful non-materialized events :
|
||||
|
||||
```sql
|
||||
SELECT
|
||||
de.event_kind,
|
||||
COUNT(*) AS unexplained_count
|
||||
FROM k_sol_dex_decoded_events de
|
||||
JOIN k_sol_chain_transactions tx
|
||||
ON tx.id = de.transaction_id
|
||||
LEFT JOIN k_sol_trade_events te
|
||||
ON te.decoded_event_id = de.id
|
||||
LEFT JOIN k_sol_liquidity_events le
|
||||
ON le.decoded_event_id = de.id
|
||||
LEFT JOIN k_sol_pool_lifecycle_events pe
|
||||
ON pe.decoded_event_id = de.id
|
||||
LEFT JOIN k_sol_fee_events fe
|
||||
ON fe.decoded_event_id = de.id
|
||||
LEFT JOIN k_sol_pool_admin_events ae
|
||||
ON ae.decoded_event_id = de.id
|
||||
LEFT JOIN k_sol_orderbook_events oe
|
||||
ON oe.decoded_event_id = de.id
|
||||
LEFT JOIN k_sol_token_account_events tae
|
||||
ON tae.decoded_event_id = de.id
|
||||
WHERE de.protocol_name = 'raydium_stable_swap'
|
||||
AND (
|
||||
tx.err_json IS NULL
|
||||
OR tx.err_json = ''
|
||||
OR tx.err_json = 'null'
|
||||
)
|
||||
AND te.id IS NULL
|
||||
AND le.id IS NULL
|
||||
AND pe.id IS NULL
|
||||
AND fe.id IS NULL
|
||||
AND ae.id IS NULL
|
||||
AND oe.id IS NULL
|
||||
AND tae.id IS NULL
|
||||
AND COALESCE(TRIM(json_extract(de.payload_json, '$.skipTradeReason')), '') = ''
|
||||
AND COALESCE(TRIM(json_extract(de.payload_json, '$.skipLiquidityReason')), '') = ''
|
||||
AND COALESCE(TRIM(json_extract(de.payload_json, '$.skipLifecycleReason')), '') = ''
|
||||
AND COALESCE(TRIM(json_extract(de.payload_json, '$.skipCatalogReason')), '') = ''
|
||||
GROUP BY de.event_kind
|
||||
ORDER BY unexplained_count DESC, de.event_kind;
|
||||
```
|
||||
|
||||
Materialization summary :
|
||||
|
||||
```sql
|
||||
SELECT
|
||||
de.event_kind,
|
||||
COUNT(DISTINCT de.id) AS decoded_count,
|
||||
COUNT(DISTINCT te.id) AS trade_count,
|
||||
COUNT(DISTINCT le.id) AS liquidity_count,
|
||||
COUNT(DISTINCT pe.id) AS lifecycle_count,
|
||||
COUNT(DISTINCT fe.id) AS fee_count,
|
||||
COUNT(DISTINCT ae.id) AS admin_count,
|
||||
COUNT(DISTINCT oe.id) AS orderbook_count
|
||||
FROM k_sol_dex_decoded_events de
|
||||
LEFT JOIN k_sol_trade_events te
|
||||
ON te.decoded_event_id = de.id
|
||||
LEFT JOIN k_sol_liquidity_events le
|
||||
ON le.decoded_event_id = de.id
|
||||
LEFT JOIN k_sol_pool_lifecycle_events pe
|
||||
ON pe.decoded_event_id = de.id
|
||||
LEFT JOIN k_sol_fee_events fe
|
||||
ON fe.decoded_event_id = de.id
|
||||
LEFT JOIN k_sol_pool_admin_events ae
|
||||
ON ae.decoded_event_id = de.id
|
||||
LEFT JOIN k_sol_orderbook_events oe
|
||||
ON oe.decoded_event_id = de.id
|
||||
WHERE de.protocol_name = 'raydium_stable_swap'
|
||||
GROUP BY de.event_kind
|
||||
ORDER BY de.event_kind;
|
||||
```
|
||||
|
||||
## Livrables attendus
|
||||
|
||||
```text
|
||||
archive delta fichiers modifiés/ajoutés
|
||||
README.md / ROADMAP.md / CHANGELOG.md mis à jour
|
||||
docs/DEX_DECODER_MATRIX.md
|
||||
docs/DEX_EVENT_COVERAGE_MATRIX.md
|
||||
docs/DB_EVENT_MODEL_REVIEW.md
|
||||
docs/reports/RAYDIUM_STABLE_SWAP_EVENT_COVERAGE_REPORT.md
|
||||
validation_sql/SQL_VALIDATION_RAYDIUM_STABLE_SWAP_0_7_52.sql
|
||||
```
|
||||
|
||||
Validation finale locale :
|
||||
|
||||
```bash
|
||||
cargo fmt
|
||||
cargo test -p kb_lib
|
||||
cargo clippy -p kb_lib --all-targets -- -D warnings
|
||||
```
|
||||
|
||||
## Critères de clôture `0.7.52`
|
||||
|
||||
```text
|
||||
tous les discriminants stable swap connus sont listés en coverage
|
||||
tous les discriminants stable swap connus sont observés localement ou explicitement marqués mapped_unverified
|
||||
instruction_audit résiduel vide pour les discriminants couverts
|
||||
fallback upstream_git.instruction_match résiduel vide pour les discriminants couverts
|
||||
decoded without coverage vide
|
||||
non-swap -> trade vide
|
||||
failed tx -> trade vide
|
||||
multi-target materialization vide
|
||||
successful decoded-only events expliqués par skip*Reason
|
||||
trade/candle uniquement pour swaps avec montants fiables
|
||||
deposit/withdraw uniquement vers liquidity
|
||||
initialize/pre_initialize uniquement vers lifecycle
|
||||
simulate/transport éventuel reste decoded-only sauf preuve métier
|
||||
```
|
||||
141
docs/reports/RAYDIUM_AMM_V4_EVENT_COVERAGE_REPORT.md
Normal file
141
docs/reports/RAYDIUM_AMM_V4_EVENT_COVERAGE_REPORT.md
Normal file
@@ -0,0 +1,141 @@
|
||||
<!-- file: docs/reports/RAYDIUM_AMM_V4_EVENT_COVERAGE_REPORT.md -->
|
||||
|
||||
# Raydium AMM v4 Event Coverage Report — `0.7.51-final`
|
||||
|
||||
## Scope
|
||||
|
||||
Tranche : `0.7.51 raydium_amm_v4`.
|
||||
|
||||
Program id canonique local :
|
||||
|
||||
```text
|
||||
675kPX9MHTjS2zt1qfr1NYHuzeLXfQM9H24wFSUt1Mp8
|
||||
```
|
||||
|
||||
Code local canonique :
|
||||
|
||||
```text
|
||||
raydium_amm_v4
|
||||
```
|
||||
|
||||
Cette tranche reprend AMM v4 legacy après `0.7.50 raydium_launchpad` et les rechecks CPMM/CLMM. Les sources Git/IDL/Solscan restent des indices ; les statuts observé/matérialisé proviennent du corpus local et du replay forcé.
|
||||
|
||||
## Sources inventoriées
|
||||
|
||||
Sources utilisées comme indices de coverage :
|
||||
|
||||
- Carbon : `decoders/raydium-amm-v4-decoder` ;
|
||||
- Pinax : `src/raydium/amm` ;
|
||||
- fnzero `sol-parser-sdk` : `idl/raydium_amm_v4.json` et `idls/raydium_amm_v4.json` ;
|
||||
- fnzero `sol-parser-sdk` : `idl/raydium_pool_v4.json` et `idls/raydium_pool_v4.json`, audit comparatif uniquement ;
|
||||
- Solscan Program IDL et recherche `instruction=<discriminator>` pour `675kPX9MHTjS2zt1qfr1NYHuzeLXfQM9H24wFSUt1Mp8`.
|
||||
|
||||
## Validation Rust et replay final
|
||||
|
||||
Validation locale rapportée :
|
||||
|
||||
```text
|
||||
cargo test -p kb_lib -> 405 passed / 0 failed
|
||||
cargo clippy -p kb_lib --all-targets -- -D warnings -> OK
|
||||
```
|
||||
|
||||
Replay local final :
|
||||
|
||||
```text
|
||||
195 replayed
|
||||
0 decode skipped
|
||||
195 ledger upserts
|
||||
70 unsafe ledger rows
|
||||
168 trades
|
||||
7 liquidity
|
||||
15 lifecycle
|
||||
0 tokenAccount
|
||||
668 candle upserts
|
||||
instructionObservations = 2599
|
||||
resetDeleted = 1578
|
||||
catalog = 61 tokens / 65 pools / 65 pairs
|
||||
```
|
||||
|
||||
## Coverage finale par discriminant
|
||||
|
||||
| Discriminant | Entrée | Famille | Local event kind | Cible DB | Observed | Materialized | Trade |
|
||||
|---|---|---|---|---|---:|---:|---:|
|
||||
| `00` | `initialize` | `pool_create` | `raydium_amm_v4.initialize` | `k_sol_pool_lifecycle_events` | 4 | 4 | 0 |
|
||||
| `01` | `initialize2` | `pool_create` | `raydium_amm_v4.initialize2_pool` | `k_sol_pool_lifecycle_events` | 8 | 8 | 0 |
|
||||
| `02` | `monitor_step` | `order_place` | `raydium_amm_v4.monitor_step` | `k_sol_orderbook_events` | 20 | 20 | 0 |
|
||||
| `03` | `deposit` | `liquidity_add` | `raydium_amm_v4.deposit` | `k_sol_liquidity_events` | 10 | 5 | 0 |
|
||||
| `04` | `withdraw` | `liquidity_remove` | `raydium_amm_v4.withdraw` | `k_sol_liquidity_events` | 3 | 2 | 0 |
|
||||
| `05` | `migrate_to_open_book` | `order_place` | `raydium_amm_v4.migrate_to_open_book` | `k_sol_orderbook_events` | 6 | 6 | 0 |
|
||||
| `06` | `set_params` | `admin_config` | `raydium_amm_v4.set_params` | `k_sol_pool_admin_events` | 1 | 1 | 0 |
|
||||
| `07` | `withdraw_pnl` | `fee` | `raydium_amm_v4.withdraw_pnl` | `k_sol_fee_events` | 1 | 1 | 0 |
|
||||
| `08` | `withdraw_srm` | `fee` | `raydium_amm_v4.withdraw_srm` | `k_sol_fee_events` | 2 | 1 | 0 |
|
||||
| `09` | `swap_base_in` | `swap` | `raydium_amm_v4.swap_base_in` | `k_sol_trade_events` | 76 | 66 | 66 |
|
||||
| `0a` | `pre_initialize` | `pool_create` | `raydium_amm_v4.pre_initialize` | `k_sol_pool_lifecycle_events` | 8 | 7 | 0 |
|
||||
| `0b` | `swap_base_out` | `swap` | `raydium_amm_v4.swap_base_out` | `k_sol_trade_events` | 3 | 1 | 1 |
|
||||
| `0c` | `simulate_info` | `cpi_transport` | `raydium_amm_v4.simulate_info` | `k_sol_dex_decoded_events_only` | 6 | 0 | 0 |
|
||||
| `0d` | `admin_cancel_orders` | `order_cancel` | `raydium_amm_v4.admin_cancel_orders` | `k_sol_orderbook_events` | 22 | 22 | 0 |
|
||||
| `0e` | `create_config_account` | `admin_config` | `raydium_amm_v4.create_config_account` | `k_sol_pool_admin_events` | 50 | 50 | 0 |
|
||||
| `0f` | `update_config_account` | `admin_config` | `raydium_amm_v4.update_config_account` | `k_sol_pool_admin_events` | 6 | 6 | 0 |
|
||||
| `10` | `swap_base_in_v2` | `swap` | `raydium_amm_v4.swap_base_in_v2` | `k_sol_trade_events` | 35 | 35 | 35 |
|
||||
| `11` | `swap_base_out_v2` | `swap` | `raydium_amm_v4.swap_base_out_v2` | `k_sol_trade_events` | 7 | 7 | 7 |
|
||||
|
||||
Toutes les entrées ont `proof_status=upstream_git_local_corpus_materialized`, sauf `simulate_info`, qui reste volontairement `upstream_git_local_corpus_observed` / decoded-only.
|
||||
|
||||
## Matérialisation métier finale
|
||||
|
||||
| Event kind | Decoded | Trade | Liquidity | Lifecycle | Fee | Admin | Orderbook |
|
||||
|---|---:|---:|---:|---:|---:|---:|---:|
|
||||
| `raydium_amm_v4.admin_cancel_orders` | 22 | 0 | 0 | 0 | 0 | 0 | 22 |
|
||||
| `raydium_amm_v4.create_config_account` | 50 | 0 | 0 | 0 | 0 | 50 | 0 |
|
||||
| `raydium_amm_v4.deposit` | 10 | 0 | 5 | 0 | 0 | 0 | 0 |
|
||||
| `raydium_amm_v4.initialize2_pool` | 8 | 0 | 0 | 8 | 0 | 0 | 0 |
|
||||
| `raydium_amm_v4.migrate_to_open_book` | 6 | 0 | 0 | 0 | 0 | 0 | 6 |
|
||||
| `raydium_amm_v4.monitor_step` | 20 | 0 | 0 | 0 | 0 | 0 | 20 |
|
||||
| `raydium_amm_v4.pre_initialize` | 8 | 0 | 0 | 7 | 0 | 0 | 0 |
|
||||
| `raydium_amm_v4.set_params` | 1 | 0 | 0 | 0 | 0 | 1 | 0 |
|
||||
| `raydium_amm_v4.simulate_info` | 6 | 0 | 0 | 0 | 0 | 0 | 0 |
|
||||
| `raydium_amm_v4.swap_base_in` | 76 | 66 | 0 | 0 | 0 | 0 | 0 |
|
||||
| `raydium_amm_v4.swap_base_in_v2` | 35 | 35 | 0 | 0 | 0 | 0 | 0 |
|
||||
| `raydium_amm_v4.swap_base_out` | 3 | 1 | 0 | 0 | 0 | 0 | 0 |
|
||||
| `raydium_amm_v4.swap_base_out_v2` | 7 | 7 | 0 | 0 | 0 | 0 | 0 |
|
||||
| `raydium_amm_v4.update_config_account` | 6 | 0 | 0 | 0 | 0 | 6 | 0 |
|
||||
| `raydium_amm_v4.withdraw` | 3 | 0 | 2 | 0 | 0 | 0 | 0 |
|
||||
| `raydium_amm_v4.withdraw_pnl` | 1 | 0 | 0 | 0 | 1 | 0 | 0 |
|
||||
| `raydium_amm_v4.withdraw_srm` | 2 | 0 | 0 | 0 | 1 | 0 | 0 |
|
||||
|
||||
## Invariants validés
|
||||
|
||||
Les requêtes finales donnent `vide` pour :
|
||||
|
||||
- `raydium_amm_v4.swap` legacy ;
|
||||
- decoded AMM v4 sans coverage entry ;
|
||||
- observations AMM v4 dont `length(discriminator_hex) > 2` ;
|
||||
- non-swap AMM v4 avec trade ;
|
||||
- transaction failed AMM v4 avec trade ;
|
||||
- event successful non matérialisé sans raison explicite ;
|
||||
- event AMM v4 matérialisé vers plus d'une table métier principale.
|
||||
|
||||
## Gaps expliqués
|
||||
|
||||
Les écarts `observed_count > materialized_count` sont acceptés uniquement s'ils sont expliqués :
|
||||
|
||||
- `swap_base_in` / `swap_base_out` : decoded-only lorsque les deltas vault ou montants exploitables sont absents ;
|
||||
- `deposit` / `withdraw` : non matérialisés lorsque le pool/pair catalogue ou les deltas nécessaires sont absents ;
|
||||
- `withdraw_srm` : non matérialisé si le contexte fee exploitable est absent ;
|
||||
- `pre_initialize` : 1 transaction failed ; les 7 transactions successful sont matérialisées en lifecycle audit minimal ;
|
||||
- `simulate_info` : decoded-only assumé.
|
||||
|
||||
Pour `deposit`, le corpus final montre 5 événements matérialisés sur le pool catalogué `2dRNngAm729NzLbb1pzgHtfHvPqR4XHFmFyYK78EfEeX` / pair `FIDA/RAY`, et 5 événements decoded-only sur des pools absents du catalogue local.
|
||||
|
||||
## Décisions spécifiques
|
||||
|
||||
- `raydium_amm_v4.swap` est définitivement interdit : les swaps doivent rester spécialisés.
|
||||
- `pre_initialize` est conservé pour les scans historiques, matérialisé comme lifecycle audit deprecated/partial, sans pair exploitable.
|
||||
- `migrate_to_open_book`, `monitor_step` et `admin_cancel_orders` sont des side effects orderbook AMM v4, pas des trades OpenBook autonomes.
|
||||
- `simulate_info` reste `k_sol_dex_decoded_events_only`.
|
||||
- Les side effects SPL Token / Token-2022 restent transversaux.
|
||||
- `raydium_pool_v4` n'est pas promu en decoder autonome dans `0.7.51`.
|
||||
|
||||
## Clôture
|
||||
|
||||
`0.7.51 raydium_amm_v4` est clôturable côté `kb_lib` sous réserve de conserver les rechecks CPMM/CLMM/Launchpad dans la validation globale de workspace lorsque la base utilisée les contient.
|
||||
56
docs/reports/RAYDIUM_POOL_V4_DECISION_NOTE.md
Normal file
56
docs/reports/RAYDIUM_POOL_V4_DECISION_NOTE.md
Normal file
@@ -0,0 +1,56 @@
|
||||
<!-- file: docs/reports/RAYDIUM_POOL_V4_DECISION_NOTE.md -->
|
||||
|
||||
# Raydium Pool v4 Decision Note — `0.7.51`
|
||||
|
||||
## Décision courte
|
||||
|
||||
`raydium_pool_v4` ne doit pas être ouvert comme decoder autonome dans `0.7.51`.
|
||||
|
||||
Statut retenu :
|
||||
|
||||
```text
|
||||
Option C — IDL ambiguë / strategy-pool wrapper sans corpus local suffisant.
|
||||
```
|
||||
|
||||
Conséquence : `raydium_pool_v4` reste une source d'audit/comparaison pour `raydium_amm_v4`. Toute promotion en tranche dédiée exige un program id prouvé localement, des observations dans `k_sol_instruction_observations`, des decoded events locaux et une absence de fallback upstream inexpliqué.
|
||||
|
||||
## Comparaison synthétique
|
||||
|
||||
| Source | Nom / rôle constaté | Indices structurants | Décision locale |
|
||||
|---|---|---|---|
|
||||
| `idl/raydium_amm_v4.json` | `raydium_amm` | Instructions AMM v4 legacy : `initialize`, `initialize2`, `deposit`, `withdraw`, `swapBaseIn`, `swapBaseOut`, `monitorStep`, `setParams`. | Source principale pour `raydium_amm_v4`. |
|
||||
| `idls/raydium_amm_v4.json` | `raydium_amm` | Variante parallèle à comparer ligne à ligne avec `idl/`. | Source principale complémentaire. |
|
||||
| `idl/raydium_pool_v4.json` | `Raydium Liquidity Pool V4` | Entrées orientées stratégie/pool wrapper : `initializeStrategy`, comptes `strategyState`, `strategyAuthority`, `lendingProgramId`; contient aussi des noms comme `swapBaseIn`. | Audit uniquement. Ne pas promouvoir. |
|
||||
| `idls/raydium_pool_v4.json` | `Raydium Liquidity Pool V4` | Même famille de signaux que `idl/raydium_pool_v4.json` à vérifier localement. | Audit uniquement. |
|
||||
|
||||
## Raisons de non-promotion
|
||||
|
||||
1. `raydium_pool_v4` ne prouve pas encore un program id local autonome dans le workspace.
|
||||
2. La présence de noms communs (`swapBaseIn`, comptes OpenBook) ne suffit pas à conclure que la surface est le program id AMM v4 canonique `675kPX...`.
|
||||
3. Les entrées `initializeStrategy`, `strategyState`, `strategyAuthority` et `lendingProgramId` indiquent un rôle potentiellement distinct : strategy, wrapper, pool manager, lending ou ancienne ABI composite.
|
||||
4. Aucune ligne locale `k_sol_instruction_observations` / `k_sol_dex_decoded_events` / `k_sol_dex_event_coverage_entries.local_event_kind` ne justifie une tranche autonome au moment de l'ouverture `0.7.51`.
|
||||
|
||||
## Règle de décision future
|
||||
|
||||
- Si `raydium_pool_v4` correspond finalement au même program id AMM v4 ou à un layout alternatif compatible, intégrer les discriminants/layouts validés dans `raydium_amm_v4`.
|
||||
- Si `raydium_pool_v4` correspond à un autre program id / wrapper / strategy / lending surface, créer une tranche dédiée seulement après corpus local.
|
||||
- Si l'IDL reste ambiguë, conserver l'entrée en roadmap comme audit conditionnel sans decoder runtime.
|
||||
|
||||
## SQL local attendu avant toute promotion
|
||||
|
||||
Une future promotion doit au minimum montrer :
|
||||
|
||||
```sql
|
||||
SELECT
|
||||
decoder_code,
|
||||
instruction_name,
|
||||
discriminator_hex,
|
||||
COUNT(*) AS observed_count,
|
||||
COUNT(DISTINCT signature) AS tx_count
|
||||
FROM k_sol_instruction_observations
|
||||
WHERE decoder_code IN ('raydium_amm_v4', 'raydium_pool_v4')
|
||||
GROUP BY decoder_code, instruction_name, discriminator_hex
|
||||
ORDER BY decoder_code, observed_count DESC;
|
||||
```
|
||||
|
||||
Puis une preuve de decoded events locaux, de coverage entries mappées et d'absence de fallback upstream résiduel.
|
||||
Reference in New Issue
Block a user