280 lines
8.5 KiB
Markdown
280 lines
8.5 KiB
Markdown
<!-- file: deltas/0.3.10/pre.004.md -->
|
||
<!-- version: 1 -->
|
||
|
||
# Delta `0.3.10-pre.004` — HTTP observed block + matériau RAW block
|
||
|
||
## Base requise
|
||
|
||
```text
|
||
0.3.10-pre.003
|
||
workspace.package.version = 0.3.10-pre.3
|
||
```
|
||
|
||
Le gate opérateur communiqué le 2026-09-06 ferme intégralement `pre.003` : audits statiques propres, `cargo check --workspace` PASS, Clippy workspace `--all-targets --all-features -- -D warnings` PASS, tests de `ksp-raw-transaction-lib` PASS, tests de `ksp-job-backfill-lib` PASS avec 51 tests unitaires et 20 tests d’intégration, arbres normal/features conformes.
|
||
|
||
## Objectif
|
||
|
||
Fermer `TR-B` et la preuve HTTP block de `TR-C` sans ouvrir le Worker :
|
||
|
||
```text
|
||
getBlock pool HTTP
|
||
-> valeur observée + provider/endpoint winner
|
||
-> SolanaConfirmedBlock
|
||
-> N SolanaBlockTransaction full Base64
|
||
-> matériau RAW source-neutral
|
||
```
|
||
|
||
La tranche ne crée aucun adapter productif Transport -> common. Conformément à `TR-C2`, cet adapter reste producer-owned et sera matérialisé dans le futur `ksp-worker-raw-transaction-ingest-lib`.
|
||
|
||
## Version
|
||
|
||
```text
|
||
workspace.package.version = 0.3.10-pre.4
|
||
```
|
||
|
||
Le header du `Cargo.toml` racine passe de `493` à `494`. Le nombre de membres workspace reste `20`.
|
||
|
||
## `get_block_observed`
|
||
|
||
`ksp-onchain-transport-lib` ajoute :
|
||
|
||
```text
|
||
HttpTransportPool::get_block_observed(...)
|
||
```
|
||
|
||
Le wrapper :
|
||
|
||
```text
|
||
réutilise exactement la validation/config moderne de get_block
|
||
utilise le routing/admission/timeout/retry standard du pool
|
||
retourne HttpObservedValue<Option<SolanaConfirmedBlock>>
|
||
conserve endpoint_name + provider du winner réel après retry/reroute
|
||
préserve result = null comme None
|
||
n’expose ni URL, ni headers, ni raw HTTP body
|
||
réutilise le décodage typé SolanaConfirmedBlock
|
||
```
|
||
|
||
`get_block(...)` et `get_block_observed(...)` partagent désormais le même helper privé de paramètres et la même validation du commitment `processed`.
|
||
|
||
## Provenance winner déterministe
|
||
|
||
Le canari Transport configure deux endpoints :
|
||
|
||
```text
|
||
endpoint 1 -> HTTP 429
|
||
endpoint 2 -> getBlock success
|
||
```
|
||
|
||
La valeur observée doit reporter exclusivement :
|
||
|
||
```text
|
||
endpoint_name = winner-endpoint
|
||
provider = winner-provider
|
||
```
|
||
|
||
Le Debug conserve uniquement la projection sûre et ne rend pas le transaction wire Base64.
|
||
|
||
## Matériau Base64 source-neutral
|
||
|
||
`ksp-raw-transaction-lib` ajoute `base64` à son graphe common et expose :
|
||
|
||
```text
|
||
extract_raw_transaction_signature_from_binary_base64(...)
|
||
RawTransactionMaterial::binary_base64_with_embedded_signature(...)
|
||
```
|
||
|
||
L’extracteur lit directement le wire transaction Solana Base64 sans dépendance à une crate transaction runtime :
|
||
|
||
```text
|
||
borne la représentation textuelle avant décodage
|
||
exige Base64 STANDARD canonique
|
||
lit un short_vec de signature count borné et canonique
|
||
refuse count = 0
|
||
refuse short_vec tronqué/non canonique
|
||
refuse tableau de signatures tronqué
|
||
exige au moins un byte de message après les signatures déclarées
|
||
retourne uniquement la première signature exacte de 64 octets
|
||
ne copie jamais le transaction wire dans erreur/Debug
|
||
```
|
||
|
||
Le constructeur common réutilise cette signature puis conserve les dimensions RAW v1 existantes :
|
||
|
||
```text
|
||
network
|
||
slot
|
||
block_time
|
||
transaction Base64
|
||
meta omitted/null/value
|
||
version omitted/null/legacy/number
|
||
transaction_index
|
||
```
|
||
|
||
Le format canonique reste strictement `ksp.solana.raw_transaction` v1.
|
||
|
||
## Preuve cross-layer sans nouveau couplage de production
|
||
|
||
Le nouveau canari test-only :
|
||
|
||
```text
|
||
crates/ksp-job-backfill-lib/tests/http_block_material.rs
|
||
```
|
||
|
||
utilise une crate qui dépend déjà de Transport et de common pour prouver la composition future sans créer d’edge architectural supplémentaire :
|
||
|
||
```text
|
||
get_block_observed
|
||
-> SolanaConfirmedBlock
|
||
-> 2 SolanaBlockTransaction distinctes
|
||
-> full Base64 + meta + version + transactionIndex 0/1
|
||
-> RawTransactionMaterial::binary_base64_with_embedded_signature
|
||
-> canonicalize_raw_transaction
|
||
```
|
||
|
||
Les deux transaction wires minimales font `66` octets chacune et utilisent des signatures distinctes :
|
||
|
||
```text
|
||
transaction 0 -> signature [0; 64]
|
||
transaction 1 -> signature [1; 64]
|
||
```
|
||
|
||
Le canari vérifie que ces signatures et les index 0/1 restent associés à la bonne transaction, avec le slot et le block time communs du bloc.
|
||
|
||
Cette preuve reste strictement test-only. Aucun symbole `ksp_raw_transaction_lib` n’est ajouté aux sources de production de `ksp-onchain-transport-lib`.
|
||
|
||
## Dépendances common
|
||
|
||
Le graphe runtime direct de `ksp-raw-transaction-lib` devient exactement :
|
||
|
||
```text
|
||
base64
|
||
ksp-core-lib
|
||
ksp-store-api
|
||
serde_json
|
||
sha2
|
||
```
|
||
|
||
Restent interdits :
|
||
|
||
```text
|
||
ksp-store-lib
|
||
ksp-onchain-transport-lib
|
||
ksp-config-lib
|
||
ksp-job-api
|
||
ksp-job-backfill-lib
|
||
ksp-worker-api
|
||
tokio
|
||
futures
|
||
```
|
||
|
||
La règle `DEP-PIPE-006` reste donc respectée.
|
||
|
||
## Documentation durable
|
||
|
||
`crates/ksp-onchain-transport-lib/USAGE.md` documente la différence entre :
|
||
|
||
```text
|
||
get_block(...)
|
||
get_block_observed(...)
|
||
```
|
||
|
||
sans transformer le guide en journal de prerelease.
|
||
|
||
`docs/architecture/011-RAW_TRANSACTION_ACQUISITION.md` ferme `TR-B`, conserve `TR-C2` producer-owned et corrige le graphe common vers `ksp-store-api`.
|
||
|
||
Le plan `031` et la validation `027` enregistrent également la fermeture opérateur de `pre.003` et le périmètre exact de `pre.004`.
|
||
|
||
## Fichiers ajoutés
|
||
|
||
```text
|
||
crates/ksp-job-backfill-lib/tests/http_block_material.rs
|
||
crates/ksp-onchain-transport-lib/fixtures/http/get_block.observed_material.success.json
|
||
deltas/0.3.10/pre.004.md
|
||
```
|
||
|
||
## Fichiers modifiés
|
||
|
||
```text
|
||
Cargo.toml
|
||
crates/ksp-onchain-transport-lib/USAGE.md
|
||
crates/ksp-onchain-transport-lib/src/rpc_blocks.rs
|
||
crates/ksp-onchain-transport-lib/tests/public_api.rs
|
||
crates/ksp-onchain-transport-lib/unit_tests/rpc_blocks.rs
|
||
crates/ksp-raw-transaction-lib/Cargo.toml
|
||
crates/ksp-raw-transaction-lib/src/canonical.rs
|
||
crates/ksp-raw-transaction-lib/src/error.rs
|
||
crates/ksp-raw-transaction-lib/src/lib.rs
|
||
crates/ksp-raw-transaction-lib/src/signature.rs
|
||
crates/ksp-raw-transaction-lib/tests/dependency_boundary.rs
|
||
crates/ksp-raw-transaction-lib/tests/public_api.rs
|
||
crates/ksp-raw-transaction-lib/unit_tests/canonical.rs
|
||
crates/ksp-raw-transaction-lib/unit_tests/signature.rs
|
||
docs/architecture/011-RAW_TRANSACTION_ACQUISITION.md
|
||
docs/plans/031-V0_3_10_RAW_TRANSACTION_INGEST_PLAN.md
|
||
docs/validation/027-V0_3_10_RAW_TRANSACTION_INGEST.md
|
||
```
|
||
|
||
## Fichiers supprimés
|
||
|
||
Aucun.
|
||
|
||
## Validations exécutées dans l’environnement d’assemblage
|
||
|
||
```text
|
||
python3 scripts/audit_rust_workspace_rules.py
|
||
General Rust rule audit: clean
|
||
Rust export completeness audit: 0 candidate(s)
|
||
KSP workspace Rust rule audit: clean
|
||
|
||
python3 scripts/audit_markdown_tables.py README.md RULES.md ROADMAP.md CHANGELOG.md docs prompts crates deltas
|
||
Markdown table audit: clean (339 table(s), 757 file(s))
|
||
```
|
||
|
||
L’environnement d’assemblage ne fournit ni `cargo`, ni `rustc`, ni `rustfmt`.
|
||
|
||
## Gate opérateur demandé
|
||
|
||
```bash
|
||
cargo fmt --all
|
||
python3 scripts/audit_rust_workspace_rules.py
|
||
python3 scripts/audit_markdown_tables.py README.md RULES.md ROADMAP.md CHANGELOG.md docs prompts crates deltas
|
||
cargo check --workspace
|
||
cargo clippy --workspace --all-targets --all-features -- -D warnings
|
||
cargo test -p ksp-raw-transaction-lib
|
||
cargo test -p ksp-onchain-transport-lib
|
||
cargo test -p ksp-job-backfill-lib --test http_block_material
|
||
cargo tree -p ksp-raw-transaction-lib --edges normal
|
||
cargo tree -p ksp-onchain-transport-lib --edges normal
|
||
```
|
||
|
||
## Validations non exécutées localement
|
||
|
||
```text
|
||
cargo fmt --all
|
||
cargo check --workspace
|
||
cargo clippy --workspace --all-targets --all-features -- -D warnings
|
||
cargo test -p ksp-raw-transaction-lib
|
||
cargo test -p ksp-onchain-transport-lib
|
||
cargo test -p ksp-job-backfill-lib --test http_block_material
|
||
cargo tree -p ksp-raw-transaction-lib --edges normal
|
||
cargo tree -p ksp-onchain-transport-lib --edges normal
|
||
smokes live : non requis pour cette tranche déterministe
|
||
```
|
||
|
||
## Décisions prises
|
||
|
||
```text
|
||
TR-B est fermé par get_block_observed
|
||
get_block et get_block_observed partagent validation + décodage
|
||
la common extrait la signature d’un transaction wire Base64 complet
|
||
aucune dépendance Solana transaction runtime n’est ajoutée à la common
|
||
aucun adapter productif Transport -> common dans Transport
|
||
TR-C2 reste Worker-owned
|
||
la preuve block -> common est cross-layer et test-only
|
||
RAW v1 reste inchangé
|
||
aucun Worker live n’est ouvert dans pre.004
|
||
```
|
||
|
||
## Questions ouvertes
|
||
|
||
Aucune question ne bloque le gate de `pre.004`. `pre.005` reste dédiée à la parité WS `blockSubscribe` + Helius `transactionSubscribe`, avec golden parity ou fallback hydration explicitement qualifié selon la représentation réellement disponible.
|