# Delta `0.2.5-pre.002` — foundation crate/capabilities/passwords/errors/logging ## Base requise ```text release : 0.2.5 prerelease : pre.002 identifiant de commit attendu : v0.2.5-pre.002 workspace.package.version : 0.2.5-pre.2 base : v0.2.5-pre.001-fix.001 ``` Le delta `pre.001-fix.001` est appliqué avant cette tranche. Les deltas historiques `pre.001.md` et `pre.001-fix.001.md` restent inchangés. ## Objectif Créer la foundation Rust de `ksp-wallet-lib` sans commencer encore le codec `.kspwallet`, le KDF/AEAD, la persistence, la keypair Solana ou la signature. Cette tranche matérialise uniquement : ```text crate + frontières Cargo WalletCapability WalletView / WalletOwner opaques LockedWalletInfo / WalletInfo / WalletNote ViewPassword / OwnerPassword codes d'erreur Wallet contrat de logging KSP canaries public API / dependency firewall ``` Les opérations `create/open/rotate/sign/import/export` restent volontairement absentes tant que leurs invariants cryptographiques/persistence ne sont pas implémentés dans les tranches prévues. ## Version Cargo Conformément à `VER-ID-009` : ```text 0.2.5-pre.1 -> 0.2.5-pre.2 ``` Toutes les crates membres continuent d'hériter `version.workspace = true`. ## Workspace et dépendances Nouveau membre : ```text crates/ksp-wallet-lib ``` Dépendances directes : ```text ksp-core-lib ksp-logging-lib zeroize.workspace = true ``` `zeroize` est centralisé dans `[workspace.dependencies]` : ```toml zeroize = { version = "^1.9" } ``` La génération courante `zeroize 1.9.0` a été réauditée avant insertion. La crate est utilisée immédiatement pour nettoyer au `Drop` les buffers `String` possédés par les wrappers de passwords. Aucun `secrecy`, Argon2, AEAD, CSPRNG, Solana keypair/signer/signature ou codec supplémentaire n'est ajouté par anticipation. Interdictions confirmées dans le manifest Wallet : ```text ksp-config-lib ksp-onchain-transport-lib ksp-execution-policy-api ksp-store-api / ksp-store-lib Tauri tracing direct solana-pubkey direct ``` ### Ownership de `Pubkey` `ksp-wallet-lib` ne dépend pas directement de `solana-pubkey`. Toute surface Wallet utilise : ```text ksp_core_lib::Pubkey ``` qui est le re-export possédé par `ksp-core-lib`. Les futures crates `solana-keypair`/`solana-signer` ne seront ajoutées que lorsqu'un chemin de compilation les consommera réellement ; leur compatibilité avec la génération de `Pubkey` possédée par Core sera alors contrôlée par compilation et `cargo tree`. ### Aucun ownership Config Wallet n'a aucune configuration runtime propre et ne lit ni document Config, ni `.env`, ni environnement processus. Le futur chemin/répertoire de destination d'une création/import sera fourni explicitement par le caller. Une application pourra faire résoudre son propre défaut par Config puis transmettre ce chemin à Wallet sans créer de dépendance inverse Wallet -> Config. ## Capabilities publiques ### `WalletCapability` Deux rôles uniquement : ```text View Owner ``` `View` signifie metadata autorisées plus future rotation de **son propre password VIEW uniquement**. `Owner` signifie metadata autorisées plus futures capacités de signature/export explicite/administration. Aucun rôle recovery/hardware/automation n'est ajouté en V1. ### `WalletView` Handle opaque exposant actuellement uniquement la projection metadata : ```text capability() -> View pubkey() alias() notes() info() ``` Il n'expose aucun constructeur public, aucune signature, aucun export secret, aucune mutation alias/notes et aucune administration OWNER. La future méthode de rotation de son propre password sera ajoutée lorsque le slot VIEW réel et sa persistence existent ; `pre.002` ne simule pas cette opération. ### `WalletOwner` Handle opaque exposant actuellement la même lecture metadata autorisée : ```text capability() -> Owner pubkey() alias() notes() info() ``` Il n'expose encore ni secret ni signature ni méthode d'administration. Les opérations OWNER réelles sont ajoutées avec les matériaux cryptographiques/persistence correspondants dans les tranches suivantes. ### Projections metadata `LockedWalletInfo` contient uniquement : ```text format_version view_enabled ``` Il ne contient aucune Pubkey, alias ou note. `WalletInfo` contient après autorisation : ```text format_version capability ksp_core_lib::Pubkey alias optionnel notes ``` `WalletNote` expose un identifiant stable et un texte protégé après autorisation. Les constructors de ces projections ne sont pas publics : elles sont destinées à être produites par Wallet, pas à fabriquer une capability. Les `Debug` de `WalletInfo`/`WalletNote` ne rendent pas alias, identifiant de note ou contenu de note. La Pubkey peut apparaître dans `WalletInfo::Debug` car cette projection n'existe qu'après autorisation et la Pubkey n'est pas un secret blockchain ; Wallet verrouillé ne possède pas cette projection. ## Password wrappers Deux types distincts : ```text ViewPassword OwnerPassword ``` Ils : - prennent ownership d'un `String` ; - n'implémentent ni `Clone` ni `Copy` ; - n'implémentent pas `Display` ; - exposent un `Debug` strictement redacted ; - implémentent un `Drop` appelant `zeroize::Zeroize` sur le buffer possédé ; - n'exposent aucun getter public du password en clair. Deux doctests `compile_fail` canaris interdisent la régression vers `Clone`. Cette zeroization reste une hygiène best-effort sur le buffer possédé et ne prétend pas effacer des copies antérieures conservées par le caller, l'allocateur, les registres ou d'autres couches du runtime. ## Erreurs Le domaine stable est : ```text wallet ``` Les 13 codes réservés/stabilisés dans cette foundation sont : ```text format_invalid format_version_unsupported crypto_parameters_invalid authentication_failed view_unlock_failed owner_unlock_failed capability_insufficient io_failed destination_exists atomic_persistence_failed transfer_format_unsupported key_material_invalid signature_failed ``` Ils utilisent exclusivement `ksp_core_lib::ErrorCode`. Aucun type d'erreur parallèle n'est créé. Les codes de déverrouillage restent volontairement orientés rôle/opération afin que l'implémentation crypto future puisse éviter de distinguer publiquement password incorrect, unwrap incorrect et tag AEAD incorrect lorsqu'une telle distinction créerait un oracle inutile. ## Logging Le target Wallet est possédé explicitement par : ```text crates/ksp-wallet-lib/src/constants.rs ``` avec : ```text pub(crate) const TRACING_TARGET: &str = "ksp-wallet-lib"; ``` Les émissions utilisent exclusivement `ksp_logging_lib::*` et jamais `tracing` directement ni `env!("CARGO_PKG_NAME")` comme target. La foundation instrumente seulement la demande explicite de projection `info()` au niveau `trace`, avec : ```text operation=wallet_info_projection capability=view|owner ``` Aucun alias, note, password, secret, payload arbitraire ou path n'est loggé. ## Tests ajoutés La tranche définit **13 tests Rust déterministes** plus **2 doctests `compile_fail`** : - variants `WalletCapability` ; - redaction `Debug` des deux password wrappers ; - présence d'un `Drop` pour les wrappers secrets ; - projection metadata autorisée ; - redaction alias/note dans `Debug` ; - projection locked sans identité/metadata ; - canary crate-root pour `WalletView`/`WalletOwner`/`WalletCapability` ; - canary crate-root pour les wrappers de password ; - signatures de méthodes Pubkey typées en `ksp_core_lib::Pubkey` ; - disponibilité des 13 codes d'erreur depuis le crate root ; - manifest firewall Wallet ; - source ownership canary Core Pubkey / Logging facade / absence env direct. Les tests d'intégration de firewall restent spécifiques à `ksp-wallet-lib`; aucun nouveau canary général du workspace n'est déplacé arbitrairement dans cette crate. ## Documentation synchronisée Le plan Wallet est passé en version 5 pour : - figer `ksp_core_lib::Pubkey` comme seule frontière Pubkey de Wallet ; - corriger le target de logging vers `ksp-wallet-lib` dans `src/constants.rs` conformément à `DEP-LOG-010` ; - enregistrer `zeroize ^1.9` comme seul ajout tiers de `pre.002` ; - repousser les crates Solana directes à leur premier usage réel ; - confirmer qu'aucun répertoire par défaut n'appartient à Wallet et que le path sera fourni par le caller ; - pointer la suite immédiate sur `pre.003`. `ROADMAP.md` et `docs/plans/002-FUNCTIONAL_RELEASE_SEQUENCE.md` enregistrent la matérialisation de la foundation sans recopier le détail des futures prereleases. ## Fichiers ajoutés ```text crates/ksp-wallet-lib/Cargo.toml crates/ksp-wallet-lib/src/capability.rs crates/ksp-wallet-lib/src/constants.rs crates/ksp-wallet-lib/src/error.rs crates/ksp-wallet-lib/src/lib.rs crates/ksp-wallet-lib/src/metadata.rs crates/ksp-wallet-lib/src/owner.rs crates/ksp-wallet-lib/src/password.rs crates/ksp-wallet-lib/src/view.rs crates/ksp-wallet-lib/unit_tests/capability.rs crates/ksp-wallet-lib/unit_tests/metadata.rs crates/ksp-wallet-lib/unit_tests/password.rs crates/ksp-wallet-lib/tests/dependency_boundary.rs crates/ksp-wallet-lib/tests/public_api.rs deltas/0.2.5/pre.002.md ``` ## Fichiers modifiés ```text Cargo.toml ROADMAP.md docs/plans/002-FUNCTIONAL_RELEASE_SEQUENCE.md docs/plans/012-V0_2_5_WALLET_FOUNDATION_PLAN.md ``` ## Fichiers supprimés Aucun. ## Validations exécutées dans l'environnement de préparation Contrôles statiques réellement exécutés : - parsing TOML du `Cargo.toml` racine et du manifest Wallet ; - comparaison de l'arbre avec la base `pre.001-fix.001` ; - inventaire exact des fichiers ajoutés/modifiés ; - scan des sources Wallet : aucun `use` statement ; - scan production : aucun `unwrap`, `expect`, `panic`, opérateur `?` ou bloc `unsafe` ajouté ; - manifest firewall : absence Config/Transport/ExecutionPolicy/Store/Tauri/tracing/solana-pubkey directs ; - source ownership : `ksp_core_lib::Pubkey`, `ksp_logging_lib::trace!`, target explicite `ksp-wallet-lib`, aucun `solana_pubkey::`, `tracing::` ou `std::env::` ; - contrôle des headers `file:` / `version:` des fichiers ajoutés/modifiés ; - contrôle de l'archive d'échange contre `VER-ARCHIVE-004` avant livraison. ## Validations non exécutées L'environnement de préparation ne fournit pas la toolchain Rust/Cargo. Les validations suivantes doivent donc être exécutées par l'opérateur après application du delta : ```bash cargo fmt --all cargo check --workspace cargo clippy --workspace --all-targets cargo test -p ksp-wallet-lib ``` Un `cargo tree` complet des primitives Solana/crypto n'est pas encore pertinent : aucune primitive Solana/keypair/KDF/AEAD nouvelle n'est ajoutée en `pre.002`. `zeroize` doit néanmoins apparaître sans duplication injustifiée lors du contrôle Cargo opérateur. ## Décisions prises - `Pubkey` Wallet est exclusivement `ksp_core_lib::Pubkey`; aucune dépendance directe `solana-pubkey` dans Wallet. - Logging Wallet utilise exclusivement `ksp-logging-lib` et `TRACING_TARGET = "ksp-wallet-lib"` dans `src/constants.rs`. - Wallet ne dépend pas de Config et ne choisira pas lui-même un répertoire par défaut ; le caller fournit le path. - `zeroize ^1.9` est le seul nouveau tiers de `pre.002`. - Les password wrappers sont distincts OWNER/VIEW, owned, redacted, non-Clone et zeroized au drop. - Les handles VIEW/OWNER restent opaques et ne simulent aucune opération cryptographique non encore implémentée. - VIEW conserve comme contrat futur la seule mutation de son propre password ; OWNER conserve les futures rotations OWNER/VIEW et l'administration complète. ## Questions ouvertes Aucune question bloquante pour `pre.003`. Restent volontairement à décider/figer dans leurs tranches prévues : - wire exact JSON/key slots/transcript/AAD (`pre.003`) ; - paramètres Argon2 benchmarkés et crypto effective (`pre.004`) ; - matériaux owner-control/metadata/secret et state signature (`pre.005`) ; - persistence async/atomique/no-clobber (`pre.006`) ; - keypair/signature et rotations réelles (`pre.007`) ; - adapters import/export (`pre.008`).