v0.2.11-pre.002-fix.001

This commit is contained in:
2026-08-25 20:17:31 +02:00
parent 4f92fb03f1
commit 3fd540a9db
18 changed files with 358 additions and 67 deletions

View File

@@ -6,7 +6,7 @@ resolver = "3"
members = ["crates/ksp-app-config-desk", "crates/ksp-app-wallet-desk", "crates/ksp-config-lib", "crates/ksp-core-lib", "crates/ksp-logging-lib", "crates/ksp-offchain-transport-lib", "crates/ksp-onchain-transport-lib", "crates/ksp-wallet-lib"]
[workspace.package]
version = "0.2.11-pre.2"
version = "0.2.11-pre.2.fix.1"
edition = "2024"
license = "MIT"
repository = "https://git.sasedev.com/Sasedev/khadhroony-solana-project"

View File

@@ -1,5 +1,5 @@
# file: crates/ksp-offchain-transport-lib/Cargo.toml
# version: 1
# version: 2
[package]
name = "ksp-offchain-transport-lib"
@@ -9,6 +9,7 @@ repository.workspace = true
[dependencies]
ksp-core-lib = { path = "../ksp-core-lib" }
ksp-logging-lib = { path = "../ksp-logging-lib" }
serde = { workspace = true, features = ["derive"] }
[dev-dependencies]

View File

@@ -0,0 +1,7 @@
// file: crates/ksp-offchain-transport-lib/src/constants.rs
// version: 1
//! Off-chain Transport-owned tracing constants.
/// Owning tracing target for events emitted by the off-chain transport crate.
pub(crate) const TRACING_TARGET: &str = "ksp-offchain-transport-lib";

View File

@@ -1,13 +1,13 @@
// file: crates/ksp-offchain-transport-lib/src/error.rs
// version: 1
// version: 2
/// Stable off-chain transport error for an invalid exact decimal price.
pub const ERROR_CODE_PRICE_DECIMAL_INVALID: ksp_core_lib::ErrorCode = ksp_core_lib::ErrorCode::new("offchain_transport", "price_decimal_invalid");
/// Stable off-chain transport error for an invalid provider descriptor.
/// Stable off-chain transport error for an invalid market-price provider descriptor.
pub const ERROR_CODE_PROVIDER_DESCRIPTOR_INVALID: ksp_core_lib::ErrorCode = ksp_core_lib::ErrorCode::new("offchain_transport", "provider_descriptor_invalid");
/// Stable off-chain transport error for an invalid provider identifier.
/// Stable off-chain transport error for an invalid market-price provider identifier.
pub const ERROR_CODE_PROVIDER_ID_INVALID: ksp_core_lib::ErrorCode = ksp_core_lib::ErrorCode::new("offchain_transport", "provider_id_invalid");
/// Stable off-chain transport error for an invalid normalized observation.
/// Stable off-chain transport error for an invalid normalized market-price observation.
pub const ERROR_CODE_PROVIDER_OBSERVATION_INVALID: ksp_core_lib::ErrorCode = ksp_core_lib::ErrorCode::new("offchain_transport", "provider_observation_invalid");
/// Stable off-chain transport error for invalid common provider settings.
/// Stable off-chain transport error for invalid common market-price provider settings.
pub const ERROR_CODE_PROVIDER_SETTINGS_INVALID: ksp_core_lib::ErrorCode = ksp_core_lib::ErrorCode::new("offchain_transport", "provider_settings_invalid");

View File

@@ -1,5 +1,5 @@
// file: crates/ksp-offchain-transport-lib/src/lib.rs
// version: 1
// version: 2
#![warn(missing_docs)]
#![deny(unreachable_pub)]
@@ -7,22 +7,19 @@
//! KSP-owned off-chain transport foundation.
//!
//! `0.2.11-pre.002` opens the first deliberately narrow public surface: exact SOL/USD price values, provider-neutral observations, provider descriptors,
//! common provider settings and generic availability/rate-limit metadata. No provider wire type, HTTP client, provider SDK, Config dependency or active
//! `0.2.11-pre.002` opens the first deliberately narrow capability family: `market_price`, currently limited to exact SOL/USD values, provider-neutral
//! observations, provider descriptors, common provider settings and generic availability/rate-limit metadata. The crate itself is deliberately broader than
//! market prices: future off-chain capabilities such as amount-specific swap quotes belong to separate capability families instead of extending the
//! `market_price_*` modules. Shared transport/runtime concerns stay crate-wide. No provider wire type, HTTP client, provider SDK, Config dependency or active
//! rate limiter is introduced by this tranche.
mod decimal;
mod constants;
mod error;
mod observation;
mod provider;
mod settings;
mod market_price_decimal;
mod market_price_observation;
mod market_price_provider;
mod market_price_settings;
/// Maximum accepted byte length for one textual decimal input.
pub use self::decimal::PRICE_DECIMAL_MAX_INPUT_BYTES;
/// Maximum decimal scale retained by the canonical SOL/USD price representation.
pub use self::decimal::PRICE_DECIMAL_MAX_SCALE;
/// Exact positive decimal value used by the public off-chain price contract.
pub use self::decimal::PriceDecimal;
/// Stable error code for an invalid exact decimal price.
pub use self::error::ERROR_CODE_PRICE_DECIMAL_INVALID;
/// Stable error code for an invalid provider descriptor.
@@ -33,43 +30,52 @@ pub use self::error::ERROR_CODE_PROVIDER_ID_INVALID;
pub use self::error::ERROR_CODE_PROVIDER_OBSERVATION_INVALID;
/// Stable error code for invalid common provider settings.
pub use self::error::ERROR_CODE_PROVIDER_SETTINGS_INVALID;
/// Maximum accepted byte length for one textual decimal input.
pub use self::market_price_decimal::PRICE_DECIMAL_MAX_INPUT_BYTES;
/// Maximum decimal scale retained by the canonical SOL/USD price representation.
pub use self::market_price_decimal::PRICE_DECIMAL_MAX_SCALE;
/// Exact positive decimal value used by the public off-chain price contract.
pub use self::market_price_decimal::PriceDecimal;
/// Maximum safe provenance length attached to one normalized observation.
pub use self::observation::PRICE_PROVENANCE_MAX_BYTES;
pub use self::market_price_observation::PRICE_PROVENANCE_MAX_BYTES;
/// Safe bounded provenance supplied by one provider adapter.
pub use self::observation::PriceProvenance;
pub use self::market_price_observation::PriceProvenance;
/// Millisecond UTC timestamp used for request, receipt, provider and cooldown projections.
pub use self::observation::PriceTimestamp;
pub use self::market_price_observation::PriceTimestamp;
/// Public V1 SOL/USD observation normalized by Off-chain Transport.
pub use self::observation::SolUsdPriceObservation;
pub use self::market_price_observation::SolUsdPriceObservation;
/// Maximum provider display-name length accepted by descriptors.
pub use self::provider::PRICE_PROVIDER_DISPLAY_NAME_MAX_BYTES;
pub use self::market_price_provider::PRICE_PROVIDER_DISPLAY_NAME_MAX_BYTES;
/// Maximum opaque provider identifier length accepted by the public contract.
pub use self::provider::PRICE_PROVIDER_ID_MAX_BYTES;
pub use self::market_price_provider::PRICE_PROVIDER_ID_MAX_BYTES;
/// Only price pair exposed by the `0.2.11` V1 public contract.
pub use self::provider::PricePair;
pub use self::market_price_provider::PricePair;
/// Generic authentication capability exposed by a configured provider descriptor.
pub use self::provider::PriceProviderAuthMode;
pub use self::market_price_provider::PriceProviderAuthMode;
/// Generic runtime availability state exposed without provider-specific error parsing.
pub use self::provider::PriceProviderAvailability;
pub use self::market_price_provider::PriceProviderAvailability;
/// Provider capability and presentation descriptor consumed by provider-agnostic callers.
pub use self::provider::PriceProviderDescriptor;
pub use self::market_price_provider::PriceProviderDescriptor;
/// Opaque validated provider identifier owned by Off-chain Transport.
pub use self::provider::PriceProviderId;
pub use self::market_price_provider::PriceProviderId;
/// Long-term provider quota descriptor that is informational rather than an authoritative local counter.
pub use self::provider::PriceProviderLongTermQuota;
pub use self::market_price_provider::PriceProviderLongTermQuota;
/// Period used by a documented long-term provider quota.
pub use self::provider::PriceProviderQuotaPeriod;
pub use self::market_price_provider::PriceProviderQuotaPeriod;
/// Unit used by a documented long-term provider quota.
pub use self::provider::PriceProviderQuotaUnit;
pub use self::market_price_provider::PriceProviderQuotaUnit;
/// Generic provider request-limit capability.
pub use self::provider::PriceProviderRateLimit;
pub use self::market_price_provider::PriceProviderRateLimit;
/// Shape of one generic provider request-limit capability.
pub use self::provider::PriceProviderRateLimitKind;
pub use self::market_price_provider::PriceProviderRateLimitKind;
/// Scope to which a provider documents one request limit.
pub use self::provider::PriceProviderRateLimitScope;
pub use self::market_price_provider::PriceProviderRateLimitScope;
/// Current provider-neutral runtime state projection.
pub use self::provider::PriceProviderState;
pub use self::market_price_provider::PriceProviderState;
/// Price semantics retained so consumers never assume all providers report equivalent market values.
pub use self::provider::PriceSemantics;
pub use self::market_price_provider::PriceSemantics;
/// Common provider settings shared by provider-specific runtime settings.
pub use self::settings::PriceProviderCommonSettings;
pub use self::market_price_settings::PriceProviderCommonSettings;
/// Owning tracing target for events emitted by Off-chain Transport.
pub(crate) use self::constants::TRACING_TARGET;

View File

@@ -1,5 +1,5 @@
// file: crates/ksp-offchain-transport-lib/src/decimal.rs
// version: 1
// file: crates/ksp-offchain-transport-lib/src/market_price_decimal.rs
// version: 2
/// Maximum accepted UTF-8 byte length for one textual decimal input.
pub const PRICE_DECIMAL_MAX_INPUT_BYTES: usize = 96;
@@ -221,5 +221,5 @@ fn split_exponent(source: &str) -> std::result::Result<(&str, i32), ()> {
}
#[cfg(test)]
#[path = "../unit_tests/decimal.rs"]
#[path = "../unit_tests/market_price_decimal.rs"]
mod tests;

View File

@@ -1,5 +1,5 @@
// file: crates/ksp-offchain-transport-lib/src/observation.rs
// version: 1
// file: crates/ksp-offchain-transport-lib/src/market_price_observation.rs
// version: 2
/// Maximum UTF-8 byte length accepted for safe provider provenance.
pub const PRICE_PROVENANCE_MAX_BYTES: usize = 256;
@@ -165,5 +165,5 @@ fn valid_provenance(value: &str) -> bool {
}
#[cfg(test)]
#[path = "../unit_tests/observation.rs"]
#[path = "../unit_tests/market_price_observation.rs"]
mod tests;

View File

@@ -1,5 +1,5 @@
// file: crates/ksp-offchain-transport-lib/src/provider.rs
// version: 1
// file: crates/ksp-offchain-transport-lib/src/market_price_provider.rs
// version: 2
/// Maximum UTF-8 byte length of one provider display name.
pub const PRICE_PROVIDER_DISPLAY_NAME_MAX_BYTES: usize = 96;
@@ -208,9 +208,14 @@ pub struct PriceProviderId(std::string::String);
impl PriceProviderId {
/// Creates one bounded stable provider identifier.
pub fn new(value: impl std::convert::Into<std::string::String>) -> ksp_core_lib::Result<Self> {
ksp_logging_lib::trace!(target: crate::TRACING_TARGET, "validating market-price provider identifier");
let value = value.into();
if !valid_provider_id(value.as_str()) {
return std::result::Result::Err(ksp_core_lib::Error::new(crate::ERROR_CODE_PROVIDER_ID_INVALID, "invalid off-chain provider identifier"));
ksp_logging_lib::warn!(target: crate::TRACING_TARGET, field = "provider_id", "rejected invalid market-price provider identifier");
return std::result::Result::Err(ksp_core_lib::Error::new(
crate::ERROR_CODE_PROVIDER_ID_INVALID,
"invalid off-chain market-price provider identifier",
));
}
return std::result::Result::Ok(Self(value));
}
@@ -265,8 +270,10 @@ impl PriceProviderDescriptor {
long_term_quota: std::option::Option<crate::PriceProviderLongTermQuota>,
supports_sol_usd: bool,
) -> ksp_core_lib::Result<Self> {
ksp_logging_lib::trace!(target: crate::TRACING_TARGET, "validating market-price provider descriptor");
let display_name = display_name.into();
if !valid_display_name(display_name.as_str()) {
ksp_logging_lib::warn!(target: crate::TRACING_TARGET, field = "display_name", "rejected invalid market-price provider descriptor");
return std::result::Result::Err(provider_descriptor_error());
}
return std::result::Result::Ok(Self { auth_mode, display_name, id, long_term_quota, rate_limit, semantics, supports_sol_usd });
@@ -369,7 +376,7 @@ impl PriceProviderState {
}
fn provider_descriptor_error() -> ksp_core_lib::Error {
return ksp_core_lib::Error::new(crate::ERROR_CODE_PROVIDER_DESCRIPTOR_INVALID, "invalid off-chain provider descriptor");
return ksp_core_lib::Error::new(crate::ERROR_CODE_PROVIDER_DESCRIPTOR_INVALID, "invalid off-chain market-price provider descriptor");
}
fn valid_display_name(value: &str) -> bool {
@@ -397,5 +404,5 @@ fn valid_provider_id(value: &str) -> bool {
}
#[cfg(test)]
#[path = "../unit_tests/provider.rs"]
#[path = "../unit_tests/market_price_provider.rs"]
mod tests;

View File

@@ -1,5 +1,5 @@
// file: crates/ksp-offchain-transport-lib/src/settings.rs
// version: 1
// file: crates/ksp-offchain-transport-lib/src/market_price_settings.rs
// version: 2
/// Common provider settings embedded by future provider-specific runtime settings.
///
@@ -15,6 +15,7 @@ impl PriceProviderCommonSettings {
/// Creates common settings for one uniquely identified runtime provider instance.
#[must_use]
pub fn new(provider_id: crate::PriceProviderId, enabled: bool) -> Self {
ksp_logging_lib::trace!(target: crate::TRACING_TARGET, enabled = enabled, "constructed common market-price provider settings");
return Self { enabled, provider_id };
}
@@ -32,5 +33,5 @@ impl PriceProviderCommonSettings {
}
#[cfg(test)]
#[path = "../unit_tests/settings.rs"]
#[path = "../unit_tests/market_price_settings.rs"]
mod tests;

View File

@@ -1,14 +1,17 @@
// file: crates/ksp-offchain-transport-lib/tests/dependency_boundary.rs
// version: 1
// version: 2
#![warn(missing_docs)]
#![deny(unreachable_pub)]
#![forbid(unsafe_code)]
//! Dependency, observability and module-taxonomy canaries for the Off-chain Transport foundation.
#[test]
fn pre_002_manifest_keeps_foundation_provider_and_config_independent() {
let manifest = include_str!("../Cargo.toml");
assert!(manifest.contains("ksp-core-lib"));
assert!(manifest.contains("ksp-logging-lib"));
assert!(manifest.contains("serde"));
assert!(!manifest.contains("ksp-config-lib"));
assert!(!manifest.contains("reqwest"));
@@ -17,4 +20,17 @@ fn pre_002_manifest_keeps_foundation_provider_and_config_independent() {
assert!(!manifest.contains("jupiter"));
assert!(!manifest.contains("birdeye"));
assert!(!manifest.contains("dexscreener"));
assert!(!manifest.lines().any(|line| line.trim_start().starts_with("tracing =")));
let crate_root = include_str!("../src/lib.rs");
assert!(crate_root.contains("mod constants;"));
assert!(crate_root.contains("mod market_price_decimal;"));
assert!(crate_root.contains("mod market_price_observation;"));
assert!(crate_root.contains("mod market_price_provider;"));
assert!(crate_root.contains("mod market_price_settings;"));
assert!(!crate_root.contains("mod decimal;"));
assert!(!crate_root.contains("mod observation;"));
assert!(!crate_root.contains("mod provider;"));
assert!(!crate_root.contains("mod settings;"));
let constants = include_str!("../src/constants.rs");
assert!(constants.contains("pub(crate) const TRACING_TARGET: &str = \"ksp-offchain-transport-lib\";"));
}

View File

@@ -1,10 +1,12 @@
// file: crates/ksp-offchain-transport-lib/tests/public_api.rs
// version: 1
// version: 2
#![warn(missing_docs)]
#![deny(unreachable_pub)]
#![forbid(unsafe_code)]
//! Public API canaries for the first Off-chain Transport market-price capability family.
#[test]
fn public_pre_002_price_foundation_is_available_from_crate_root() -> ksp_core_lib::Result<()> {
assert_eq!(ksp_offchain_transport_lib::PricePair::SolUsd.code(), "SOL/USD");

View File

@@ -1,5 +1,5 @@
// file: crates/ksp-offchain-transport-lib/unit_tests/decimal.rs
// version: 1
// file: crates/ksp-offchain-transport-lib/unit_tests/market_price_decimal.rs
// version: 2
#[test]
fn decimal_normalizes_fractional_and_scientific_forms_without_f64() -> ksp_core_lib::Result<()> {

View File

@@ -1,5 +1,5 @@
// file: crates/ksp-offchain-transport-lib/unit_tests/observation.rs
// version: 1
// file: crates/ksp-offchain-transport-lib/unit_tests/market_price_observation.rs
// version: 2
#[test]
fn observation_preserves_pair_exact_price_semantics_timestamps_and_safe_provenance() -> ksp_core_lib::Result<()> {

View File

@@ -1,5 +1,5 @@
// file: crates/ksp-offchain-transport-lib/unit_tests/provider.rs
// version: 1
// file: crates/ksp-offchain-transport-lib/unit_tests/market_price_provider.rs
// version: 2
#[test]
fn provider_id_is_opaque_bounded_and_stable() -> ksp_core_lib::Result<()> {

View File

@@ -1,5 +1,5 @@
// file: crates/ksp-offchain-transport-lib/unit_tests/settings.rs
// version: 1
// file: crates/ksp-offchain-transport-lib/unit_tests/market_price_settings.rs
// version: 2
#[test]
fn common_settings_contain_only_generic_identity_and_enablement() -> ksp_core_lib::Result<()> {

View File

@@ -0,0 +1,193 @@
<!-- file: deltas/0.2.11/pre.002-fix.001.md -->
<!-- version: 1 -->
# Delta `0.2.11-pre.002-fix.001` — Rustdoc, Logging et taxonomie Off-chain
## 1. Base requise
Ce correctif s'applique exclusivement après :
```text
v0.2.10
+ 0.2.11-pre.001
+ 0.2.11-pre.001-fix.001
+ 0.2.11-pre.002
```
Conformément à `VER-ID-007` et `VER-ID-010`, la version Cargo devient `0.2.11-pre.2.fix.1` car ce correctif modifie du code Rust et un manifeste de crate.
## 2. Motifs du correctif
La validation opérateur de `pre.002` a montré que `cargo check` et les tests passaient, mais que `cargo clippy --workspace --all-targets` émettait deux warnings `missing_docs` sur les crates d'intégration :
```text
crates/ksp-offchain-transport-lib/tests/dependency_boundary.rs
crates/ksp-offchain-transport-lib/tests/public_api.rs
```
Le gate n'était donc pas propre malgré le succès fonctionnel. Les résultats opérateur complets de `pre.002` restent l'autorité sur cette constatation.
Une relecture des règles a également confirmé les contrats suivants :
```text
RUST-DOC-001/003 rustdocs utiles sur les surfaces concernées
DEP-LOG-004 runtime KSP instrumenté via ksp-logging-lib
DEP-LOG-010 target explicite dans src/constants.rs
DEP-LOG-011 pas de target dérivé implicitement de Cargo
FILE_CONTRACTS modules séparés selon responsabilités/invariants
```
Enfin, la fondation initiale utilisait des noms internes trop génériques (`decimal.rs`, `observation.rs`, `provider.rs`, `settings.rs`) alors que `ksp-offchain-transport-lib` est destinée à porter plusieurs familles off-chain hétérogènes.
## 3. Corrections Rustdoc
Les deux tests d'intégration possèdent désormais une rustdoc de crate explicite, ce qui supprime les warnings `missing_docs` attendus sous `#![warn(missing_docs)]`.
Aucun lint n'est désactivé ou abaissé.
## 4. Logging KSP
`ksp-offchain-transport-lib` dépend désormais réellement de `ksp-logging-lib`.
Le fichier suivant est ajouté :
```text
crates/ksp-offchain-transport-lib/src/constants.rs
```
avec le target propriétaire :
```text
ksp-offchain-transport-lib
```
Les validations/constructions comportementales de la fondation émettent uniquement via les macros `ksp-logging-lib` et `crate::TRACING_TARGET`. Aucune dépendance directe à `tracing`, `tracing-subscriber` ou `tracing-appender` n'est ajoutée.
Les logs de validation ne recopient ni identifiant rejeté, ni display name rejeté, ni futur credential.
## 5. Taxonomie de modules
La crate est explicitement traitée comme un transport off-chain hétérogène et non comme une crate dédiée exclusivement aux prix.
Les modules V1 de prix sont renommés :
```text
decimal.rs -> market_price_decimal.rs
observation.rs -> market_price_observation.rs
provider.rs -> market_price_provider.rs
settings.rs -> market_price_settings.rs
```
Les tests unitaires en miroir suivent la même convention.
La façade publique reste au crate-root ; aucun `pub mod` n'est introduit. Les noms publics `Price*` restent ceux du contrat V1, tandis que le classement physique privé rend explicite leur appartenance à la famille `market_price`.
La taxonomie durable prévue est :
```text
constants.rs / error.rs partagé crate-wide
http_* mécanique HTTP partageable lorsqu'elle existe réellement
market_price_* prix de marché / spot
swap_quote_* futures quotes montant/route
autres familles ajoutées seulement avec un scope réel
```
Cette organisation suit le précédent KSP des familles `http_*`, `ws_*`, `grpc_*` et `rpc_*` de On-chain Transport.
## 6. Lecture/écriture
`market_price` V1 reste strictement read-only. La crate n'est pas déclarée définitivement read-only pour toute évolution future : la sémantique métier décide de l'ownership, pas le simple verbe HTTP.
Une future quote Jupiter appartient à une famille distincte `swap_quote`; une soumission ou signature de transaction Solana reste hors de cette crate. Toute vraie mutation d'un service distant demandera un contrat explicite avant implémentation.
## 7. Tests et canaries modifiés
`dependency_boundary.rs` vérifie désormais au minimum :
```text
ksp-logging-lib présent
aucune dépendance tracing directe
constants.rs et TRACING_TARGET explicites
modules V1 préfixés market_price_*
anciens modules internes génériques absents
Config, reqwest et SDK providers toujours absents de pre.002
```
`public_api.rs` conserve les canaries de façade de `pre.002` avec sa rustdoc de crate.
## 8. Validations demandées après application
```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/0.2.11
cargo check --workspace
cargo clippy --workspace --all-targets
cargo test -p ksp-offchain-transport-lib
cargo test --workspace
```
Le résultat attendu de Clippy est **sans warning rustdoc** pour `ksp-offchain-transport-lib`.
## 9. Scope inchangé
Le correctif n'ajoute aucun client HTTP, limiter actif, adapter provider, credential Config, quote Jupiter ou nouvelle paire. `pre.003` reste propriétaire du premier runtime HTTP commun.
## 10. Validation opérateur de `pre.002` ayant déclenché le fix
La validation fournie par l'opérateur avant ce correctif donne :
```text
cargo fmt --all exécuté
python3 scripts/audit_rust_workspace_rules.py clean
python3 scripts/audit_markdown_tables.py clean, 115 tables / 102 files
cargo check --workspace PASS
cargo clippy --workspace --all-targets PASS fonctionnel avec 2 warnings missing_docs
cargo test -p ksp-offchain-transport-lib PASS, 10 unit + 1 boundary + 2 public API
cargo test --workspace PASS, ignored opt-in/diagnostic inchangés
```
Les deux warnings Clippy sont précisément la raison rustdoc du présent fix ; ils ne sont pas requalifiés en PASS propre.
## 11. Fichiers ajoutés
```text
crates/ksp-offchain-transport-lib/src/constants.rs
crates/ksp-offchain-transport-lib/src/market_price_decimal.rs
crates/ksp-offchain-transport-lib/src/market_price_observation.rs
crates/ksp-offchain-transport-lib/src/market_price_provider.rs
crates/ksp-offchain-transport-lib/src/market_price_settings.rs
crates/ksp-offchain-transport-lib/unit_tests/market_price_decimal.rs
crates/ksp-offchain-transport-lib/unit_tests/market_price_observation.rs
crates/ksp-offchain-transport-lib/unit_tests/market_price_provider.rs
crates/ksp-offchain-transport-lib/unit_tests/market_price_settings.rs
deltas/0.2.11/pre.002-fix.001.md
```
## 12. Fichiers modifiés
```text
Cargo.toml
crates/ksp-offchain-transport-lib/Cargo.toml
crates/ksp-offchain-transport-lib/src/error.rs
crates/ksp-offchain-transport-lib/src/lib.rs
crates/ksp-offchain-transport-lib/tests/dependency_boundary.rs
crates/ksp-offchain-transport-lib/tests/public_api.rs
docs/plans/018-V0_2_11_OFFCHAIN_PRICE_TRANSPORT_PLAN.md
docs/validation/014-V0_2_11_OFFCHAIN_PRICE_TRANSPORT.md
```
## 13. Fichiers supprimés par renommage
```text
crates/ksp-offchain-transport-lib/src/decimal.rs
crates/ksp-offchain-transport-lib/src/observation.rs
crates/ksp-offchain-transport-lib/src/provider.rs
crates/ksp-offchain-transport-lib/src/settings.rs
crates/ksp-offchain-transport-lib/unit_tests/decimal.rs
crates/ksp-offchain-transport-lib/unit_tests/observation.rs
crates/ksp-offchain-transport-lib/unit_tests/provider.rs
crates/ksp-offchain-transport-lib/unit_tests/settings.rs
```
Ces suppressions font partie du correctif : les anciens fichiers génériques ne doivent pas coexister avec les fichiers `market_price_*` après application.

View File

@@ -1,9 +1,9 @@
<!-- file: docs/plans/018-V0_2_11_OFFCHAIN_PRICE_TRANSPORT_PLAN.md -->
<!-- version: 3 -->
<!-- version: 4 -->
# Plan `0.2.11` — Off-chain price transport SOL/USD multi-provider
**Statut courant : `0.2.11-pre.002` matérialise la fondation de `ksp-offchain-transport-lib` sans encore ajouter de client HTTP ou d'adapter provider. Le contrat public V1 possède désormais un décimal exact SOL/USD, des observations/provenances/timestamps sûrs, des identifiants/descriptors provider opaques, des capacités auth/rate-limit/quota descriptives, des settings communs minimaux et des états d'availability provider-neutral.**
**Statut courant : `0.2.11-pre.002-fix.001` corrige la fondation de `ksp-offchain-transport-lib` avant `pre.003` : rustdocs d'intégration complètes, façade Logging KSP avec target explicite, et classement de la capacité actuelle sous la famille interne `market_price_*`. Le contrat V1 reste limité à SOL/USD et aucun client HTTP/provider n'est encore ajouté.**
## 1. Base et autorité
@@ -93,6 +93,41 @@ forme JSON wire provider
mapping de status HTTP provider
```
### 3.1 Taxonomie interne durable de `ksp-offchain-transport-lib`
`ksp-offchain-transport-lib` est une crate de transport **off-chain hétérogène**. `0.2.11` n'en définit que la première famille fonctionnelle ; la crate elle-même ne doit pas être structurée comme si toutes ses responsabilités futures étaient des prix.
La convention retenue à partir de `pre.002-fix.001` est :
```text
constants.rs préoccupations partagées à toute la crate
error.rs erreurs partagées / codes crate-wide
http_* mécanique HTTP réutilisable entre familles lorsqu'elle sera matérialisée
market_price_* prix de marché / spot et observations normalisées
swap_quote_* réservé aux futures quotes montant/route, uniquement lorsqu'elles seront réellement implémentées
<future_capability>_* nouvelle famille uniquement lorsqu'un scope réel l'exige
```
Les fichiers génériques `decimal.rs`, `observation.rs`, `provider.rs` et `settings.rs` introduits initialement par `pre.002` sont donc corrigés avant toute extension runtime : la fonctionnalité actuelle est préfixée `market_price_*`. Les futurs domaines ne doivent pas être ajoutés dans ces modules uniquement parce qu'ils utilisent eux aussi un provider HTTP.
La règle est **responsabilité avant taille** : un module commun n'est promu au niveau crate-wide que lorsqu'au moins deux familles réelles partagent le même invariant. Ainsi, le HTTP, le scheduling ou une identité provider pourront être factorisés plus tard si leur partage est effectivement démontré ; aucune abstraction générique n'est créée aujourd'hui uniquement pour anticiper Jupiter Quotes.
### 3.2 Lecture, écriture et verbes HTTP
La capacité `market_price` de `0.2.11` est strictement read-only. La crate n'est toutefois pas déclarée architecturalement read-only pour toutes ses versions futures.
L'ownership dépend de la sémantique métier, pas du verbe HTTP :
```text
GET/POST qui récupère ou calcule une donnée off-chain peut appartenir à Off-chain Transport
quote de swap dépendante d'un montant et d'une route future famille swap_quote, pas market_price
construction distante d'un payload sans soumission à auditer selon le contrat futur
soumission/signature d'une transaction Solana reste hors d'Off-chain Transport
écriture distante ayant un effet métier externe nécessite un scope/contrat explicite avant ajout
```
Un futur endpoint Jupiter utilisant `POST` ne devient donc pas automatiquement une « écriture » KSP. Inversement, aucune opération mutante distante n'est autorisée implicitement sous prétexte qu'elle passe par `reqwest`.
## 4. Frontière avec la future `ksp-app-solprices-desk`
La release suivante doit créer :
@@ -629,6 +664,12 @@ Remplacement du forecast tabulaire par des sous-sections éditables, clarificati
Création de la crate et de sa façade publique initiale : `PriceDecimal`, paire SOL/USD, observation/provenance/timestamps, identifiants/descriptors provider, capacités auth/rate-limit/quota, settings communs minimaux et états d'availability provider-neutral. Aucun HTTP, limiter actif, credential provider ou adapter wire n'est avancé depuis `pre.003+`.
#### `pre.002-fix.001` — Rustdoc, Logging et taxonomie Off-chain
**Statut : réalisé.**
Correction des deux warnings `missing_docs` des tests d'intégration, ajout de `ksp-logging-lib` avec `src/constants.rs` et `TRACING_TARGET = "ksp-offchain-transport-lib"`, instrumentation KSP des validations/constructions comportementales, et renommage des modules actuels en `market_price_*` pour préparer les futures familles hétérogènes telles que `swap_quote_*` sans transformer la crate entière en module de prix.
### `pre.003` — HTTP REST commun et rate limiting
**Statut : planifié.**

View File

@@ -1,5 +1,5 @@
<!-- file: docs/validation/014-V0_2_11_OFFCHAIN_PRICE_TRANSPORT.md -->
<!-- version: 2 -->
<!-- version: 3 -->
# Validation `0.2.11` — Off-chain price transport SOL/USD
@@ -60,6 +60,23 @@ Les statuts `PLANNED` restent non validés tant que la tranche correspondante n'
| availability provider-neutral représentable | PASS | `PriceProviderAvailability` + `PriceProviderState` |
| HTTP actif ou adapter provider ajouté | N/A | explicitement réservé à `pre.003+` |
## 3.1 Taxonomie Off-chain et observabilité
| Invariant | Statut |
|--------------------------------------------------------------------------|--------|
| crate `ksp-offchain-transport-lib` non assimilée à une crate price-only | PASS |
| capacité V1 classée sous modules privés `market_price_*` | PASS |
| modules partagés `constants.rs` et `error.rs` restent crate-wide | PASS |
| futures quotes prévues sous famille distincte `swap_quote_*` | PASS |
| aucune abstraction future créée sans responsabilité réellement partagée | PASS |
| `market_price` V1 strictement read-only | PASS |
| verbe HTTP distinct de la sémantique métier read/write | PASS |
| soumission/signature Solana reste hors d'Off-chain Transport | PASS |
| `ksp-logging-lib` utilisé pour les événements KSP de la crate | PASS |
| `src/constants.rs` possède `TRACING_TARGET = ksp-offchain-transport-lib` | PASS |
| aucune dépendance directe à `tracing` | PASS |
| crate-rustdocs présentes dans les tests d'intégration | PASS |
## 4. Matrice provider prévue
| Provider | SOL/USD V1 | Gratuit V1 | Mode auth prévu | Test déterministe | Smoke live | Statut courant |