511 lines
26 KiB
Rust
511 lines
26 KiB
Rust
// file: crates/ksp-app-wallet-desk/tests/desktop_contract.rs
|
|
// version: 33
|
|
|
|
//! Desktop build, shell and Config-status contract audits for Wallet Desk.
|
|
|
|
fn app_root() -> std::path::PathBuf {
|
|
return std::path::PathBuf::from(env!("CARGO_MANIFEST_DIR"));
|
|
}
|
|
|
|
fn read_text(path: &std::path::Path) -> String {
|
|
let source = std::fs::read_to_string(path);
|
|
assert!(source.is_ok(), "unable to read {}", path.display());
|
|
return match source {
|
|
std::result::Result::Ok(value) => value,
|
|
std::result::Result::Err(_) => String::new(),
|
|
};
|
|
}
|
|
|
|
fn read_source(relative_path: &str) -> String {
|
|
let root = app_root();
|
|
return read_text(root.join(relative_path).as_path());
|
|
}
|
|
|
|
fn read_json(path: &std::path::Path) -> serde_json::Value {
|
|
let source = read_text(path);
|
|
let parsed = serde_json::from_str::<serde_json::Value>(source.as_str());
|
|
assert!(parsed.is_ok(), "unable to parse {}", path.display());
|
|
return match parsed {
|
|
std::result::Result::Ok(value) => value,
|
|
std::result::Result::Err(_) => serde_json::Value::Null,
|
|
};
|
|
}
|
|
|
|
#[test]
|
|
fn tauri_shell_uses_reserved_wallet_desk_ports_and_template_windows() {
|
|
let root = app_root();
|
|
let tauri = read_json(root.join("tauri.conf.json").as_path());
|
|
assert_eq!(tauri.pointer("/build/devUrl").and_then(serde_json::Value::as_str), std::option::Option::Some("http://localhost:1432"));
|
|
assert_eq!(tauri.pointer("/build/beforeDevCommand/script").and_then(serde_json::Value::as_str), std::option::Option::Some("npm run dev"));
|
|
assert_eq!(tauri.pointer("/build/beforeDevCommand/cwd").and_then(serde_json::Value::as_str), std::option::Option::Some("."));
|
|
assert_eq!(tauri.pointer("/build/beforeBuildCommand/script").and_then(serde_json::Value::as_str), std::option::Option::Some("npm run build"));
|
|
assert_eq!(tauri.pointer("/build/beforeBuildCommand/cwd").and_then(serde_json::Value::as_str), std::option::Option::Some("."));
|
|
assert_eq!(
|
|
tauri.pointer("/build/frontendDist").and_then(serde_json::Value::as_str),
|
|
std::option::Option::Some("../../../builds/khadhroony-solana-project/ksp-app-wallet-desk/dist"),
|
|
);
|
|
assert_eq!(tauri.pointer("/app/security/csp"), std::option::Option::Some(&serde_json::Value::Null));
|
|
let manifest = read_text(root.join("Cargo.toml").as_path());
|
|
assert!(manifest.contains("name = \"ksp-app-wallet-desk\""));
|
|
let windows = tauri.pointer("/app/windows").and_then(serde_json::Value::as_array);
|
|
assert!(windows.is_some());
|
|
let windows = match windows {
|
|
std::option::Option::Some(value) => value,
|
|
std::option::Option::None => return,
|
|
};
|
|
let labels = windows.iter().filter_map(|window| return window.get("label").and_then(serde_json::Value::as_str)).collect::<std::vec::Vec<_>>();
|
|
assert_eq!(labels, ["splash", "main"]);
|
|
}
|
|
|
|
#[test]
|
|
fn package_reuses_config_desk_frontend_baseline_without_standalone_check_script() {
|
|
let root = app_root();
|
|
let package = read_json(root.join("package.json").as_path());
|
|
assert!(package.pointer("/scripts/check").is_none());
|
|
let dependencies = package.get("dependencies").and_then(serde_json::Value::as_object);
|
|
assert!(dependencies.is_some());
|
|
let dependencies = match dependencies {
|
|
std::option::Option::Some(value) => value,
|
|
std::option::Option::None => return,
|
|
};
|
|
for dependency in [
|
|
"@fltsci/tauri-plugin-tracing",
|
|
"@fortawesome/fontawesome-free",
|
|
"@tauri-apps/api",
|
|
"bootstrap",
|
|
"datatables.net-bs5",
|
|
"datatables.net-select-bs5",
|
|
"resize-observer-polyfill",
|
|
"simplebar",
|
|
] {
|
|
assert!(dependencies.contains_key(dependency), "missing dependency {dependency}");
|
|
}
|
|
}
|
|
|
|
#[test]
|
|
fn shell_contains_wallet_navigation_datatable_and_lock_state_icons() {
|
|
let root = app_root();
|
|
let html = read_text(root.join("frontend/main.html").as_path());
|
|
let main = read_text(root.join("frontend/ts/main.ts").as_path());
|
|
assert!(html.contains("id=\"walletInventoryTable\""));
|
|
assert!(html.contains("fa-lock"));
|
|
assert!(html.contains("fa-lock-open"));
|
|
assert!(html.contains("data-view=\"wallets\""));
|
|
assert!(html.contains("id=\"runtimeCompositeProfile\""));
|
|
assert!(html.contains("id=\"runtimeEffectiveWalletsDirectory\""));
|
|
assert!(main.contains("new DataTable"));
|
|
assert!(main.contains("datatables.net-select-bs5"));
|
|
assert!(main.contains("ResizeObserver"));
|
|
assert!(main.contains("simplebar"));
|
|
}
|
|
|
|
#[test]
|
|
fn pre_004_inventory_uses_wallet_library_and_exposes_only_locked_safe_fields() {
|
|
let root = app_root();
|
|
let manifest = read_text(root.join("Cargo.toml").as_path());
|
|
let tauri = read_text(root.join("src/tauri.rs").as_path());
|
|
let inventory = read_text(root.join("src/wallet_inventory.rs").as_path());
|
|
let main = read_text(root.join("frontend/ts/main.ts").as_path());
|
|
assert!(manifest.contains("ksp-wallet-lib = { path = \"../ksp-wallet-lib\" }"));
|
|
assert!(inventory.contains("ksp_wallet_lib::inspect_locked_wallet_file"));
|
|
assert!(inventory.contains("symlink_metadata"));
|
|
assert!(inventory.contains("WALLET_FILE_SUFFIX"));
|
|
assert!(tauri.contains("list_wallets"));
|
|
assert!(tauri.contains("refresh_wallets"));
|
|
assert!(tauri.contains("select_wallet"));
|
|
assert!(main.contains("WalletInventoryEntryDto"));
|
|
assert!(main.contains("LockedWalletDto"));
|
|
assert!(main.contains("refresh_wallets"));
|
|
assert!(!inventory.contains("pubkey"));
|
|
assert!(!inventory.contains("alias"));
|
|
assert!(!inventory.contains("notes"));
|
|
}
|
|
|
|
#[test]
|
|
fn frontend_control_interactions_are_trace_logged_without_control_values() {
|
|
let root = app_root();
|
|
let main = read_text(root.join("frontend/ts/main.ts").as_path());
|
|
assert!(main.contains("bindFrontendInteractions"));
|
|
assert!(main.contains("Frontend control clicked"));
|
|
assert!(main.contains("[role=\"tab\"]"));
|
|
assert!(main.contains("shellAction: control.dataset.shellAction"));
|
|
assert!(main.contains("viewId: control.dataset.view"));
|
|
assert!(!main.contains("control.value"));
|
|
}
|
|
|
|
#[test]
|
|
fn pre_005_create_and_session_lifecycle_are_backend_owned() {
|
|
let root = app_root();
|
|
let state = read_text(root.join("src/app_state.rs").as_path());
|
|
let session = read_text(root.join("src/wallet_session.rs").as_path());
|
|
let tauri = read_text(root.join("src/tauri.rs").as_path());
|
|
let html = read_text(root.join("frontend/main.html").as_path());
|
|
let main = read_text(root.join("frontend/ts/main.ts").as_path());
|
|
assert!(state.contains("ksp_wallet_lib::create_wallet_file"));
|
|
assert!(state.contains("WalletSession::Owner"));
|
|
assert!(state.contains("WalletSession::Locked"));
|
|
assert!(state.contains("std::mem::replace"));
|
|
assert!(session.contains("WalletCreateRequestDto"));
|
|
assert!(session.contains("WalletAuthorizedDto"));
|
|
assert!(tauri.contains("create_wallet"));
|
|
assert!(tauri.contains("deselect_wallet"));
|
|
assert!(tauri.contains("lock_wallet"));
|
|
assert!(html.contains("id=\"createWalletForm\""));
|
|
assert!(html.contains("id=\"createWalletOwnerPassword\""));
|
|
assert!(html.contains("id=\"createWalletViewPassword\""));
|
|
assert!(main.contains("clearCreateFormSensitiveInputs"));
|
|
assert!(main.contains("Authorized Wallet session rendered"));
|
|
}
|
|
|
|
#[test]
|
|
fn pre_006_unlock_surface_is_explicit_backend_owned_and_supports_view_owner() {
|
|
let root = app_root();
|
|
let state = read_text(root.join("src/app_state.rs").as_path());
|
|
let secrets = read_text(root.join("src/wallet_secrets.rs").as_path());
|
|
let session = read_text(root.join("src/wallet_session.rs").as_path());
|
|
let tauri = read_text(root.join("src/tauri.rs").as_path());
|
|
let html = read_text(root.join("frontend/main.html").as_path());
|
|
let main = read_text(root.join("frontend/ts/main.ts").as_path());
|
|
assert!(state.contains("open_wallet_view_file"));
|
|
assert!(state.contains("open_wallet_owner_file"));
|
|
assert!(state.contains("WalletSession::PrivilegedOperation"));
|
|
assert!(state.contains("WalletSession::View"));
|
|
assert!(secrets.contains("environment_report"));
|
|
assert!(secrets.contains("reveal_effective_environment_value"));
|
|
assert!(secrets.contains("normalize_wallet_secret_label"));
|
|
assert!(session.contains("WalletUnlockRequestDto"));
|
|
assert!(tauri.contains("unlock_wallet_view_manual"));
|
|
assert!(tauri.contains("unlock_wallet_owner_manual"));
|
|
assert!(tauri.contains("unlock_wallet_view_configured"));
|
|
assert!(tauri.contains("unlock_wallet_owner_configured"));
|
|
assert!(html.contains("id=\"unlockViewManual\""));
|
|
assert!(html.contains("id=\"unlockOwnerManual\""));
|
|
assert!(html.contains("id=\"unlockViewConfigured\""));
|
|
assert!(html.contains("id=\"unlockOwnerConfigured\""));
|
|
assert!(main.contains("beginFrontendUnlock"));
|
|
assert!(main.contains("configuredSecretCandidateCount"));
|
|
}
|
|
|
|
#[test]
|
|
fn pre_007_balance_uses_authorized_pubkey_and_composite_transport() {
|
|
let root = app_root();
|
|
let manifest = read_text(root.join("Cargo.toml").as_path());
|
|
let state = read_text(root.join("src/app_state.rs").as_path());
|
|
let transport = read_text(root.join("src/transport_runtime.rs").as_path());
|
|
let balance = read_text(root.join("src/wallet_balance.rs").as_path());
|
|
let tauri = read_text(root.join("src/tauri.rs").as_path());
|
|
let html = read_text(root.join("frontend/main.html").as_path());
|
|
let main = read_text(root.join("frontend/ts/main.ts").as_path());
|
|
assert!(manifest.contains("ksp-onchain-transport-lib = { path = \"../ksp-onchain-transport-lib\" }"));
|
|
assert!(transport.contains("resolve_transport_config_profile"));
|
|
assert!(transport.contains("HttpTransportPool::new"));
|
|
assert!(transport.contains("getBalance"));
|
|
assert!(state.contains("get_balance"));
|
|
assert!(state.contains("SolanaCommitment::Confirmed"));
|
|
assert!(state.contains("wallet.pubkey()"));
|
|
assert!(balance.contains("WalletBalanceDto"));
|
|
assert!(balance.contains("format_lamports_as_sol"));
|
|
assert!(tauri.contains("refresh_wallet_balance"));
|
|
assert!(html.contains("id=\"refreshWalletBalance\""));
|
|
assert!(html.contains("id=\"detailsBalanceLamports\""));
|
|
assert!(main.contains("renderWalletBalance"));
|
|
assert!(main.contains("refresh_wallet_balance"));
|
|
}
|
|
|
|
#[test]
|
|
fn pre_008_import_uses_rust_native_picker_and_wallet_transfer_adapters() {
|
|
let root = app_root();
|
|
let manifest = read_text(root.join("Cargo.toml").as_path());
|
|
let state = read_text(root.join("src/app_state.rs").as_path());
|
|
let import = read_text(root.join("src/wallet_import.rs").as_path());
|
|
let tauri = read_text(root.join("src/tauri.rs").as_path());
|
|
let html = read_text(root.join("frontend/main.html").as_path());
|
|
let main = read_text(root.join("frontend/ts/main.ts").as_path());
|
|
assert!(manifest.contains("tauri-plugin-dialog.workspace = true"));
|
|
assert!(manifest.contains("zeroize.workspace = true"));
|
|
assert!(tauri.contains("tauri_plugin_dialog::init()"));
|
|
assert!(tauri.contains("blocking_pick_file"));
|
|
assert!(tauri.contains("inspect_import_source"));
|
|
assert!(tauri.contains("import_wallet"));
|
|
assert!(import.contains("ksp_wallet_lib::inspect_wallet_transfer"));
|
|
assert!(import.contains("zeroize::Zeroizing"));
|
|
assert!(state.contains("ksp_wallet_lib::import_wallet_transfer"));
|
|
assert!(html.contains("id=\"inspectImportSource\""));
|
|
assert!(html.contains("id=\"importWalletForm\""));
|
|
assert!(html.contains("id=\"importSourcePubkey\""));
|
|
assert!(main.contains("WalletTransferInspectionDto"));
|
|
assert!(main.contains("bindImportWalletForm"));
|
|
}
|
|
|
|
#[test]
|
|
fn pre_009_owner_metadata_administration_uses_wallet_owner_and_refreshes_projection() {
|
|
let root = app_root();
|
|
let state = read_text(root.join("src/app_state.rs").as_path());
|
|
let metadata = read_text(root.join("src/wallet_metadata.rs").as_path());
|
|
let session = read_text(root.join("src/wallet_session.rs").as_path());
|
|
let tauri = read_text(root.join("src/tauri.rs").as_path());
|
|
let html = read_text(root.join("frontend/main.html").as_path());
|
|
let main = read_text(root.join("frontend/ts/main.ts").as_path());
|
|
assert!(state.contains("owner.update_alias"));
|
|
assert!(state.contains("owner.add_note"));
|
|
assert!(state.contains("owner.update_note"));
|
|
assert!(state.contains("owner.delete_note"));
|
|
assert!(state.contains("ERROR_CODE_STATE_CONFLICT"));
|
|
assert!(session.contains("OwnerOperation"));
|
|
assert!(metadata.contains("WalletAliasUpdateRequestDto"));
|
|
assert!(metadata.contains("WalletNoteAddRequestDto"));
|
|
assert!(metadata.contains("WalletNoteUpdateRequestDto"));
|
|
assert!(metadata.contains("WalletNoteDeleteRequestDto"));
|
|
assert!(tauri.contains("update_wallet_alias"));
|
|
assert!(tauri.contains("add_wallet_note"));
|
|
assert!(tauri.contains("update_wallet_note"));
|
|
assert!(tauri.contains("delete_wallet_note"));
|
|
assert!(html.contains("id=\"ownerWalletAlias\""));
|
|
assert!(html.contains("id=\"ownerNotesList\""));
|
|
assert!(html.contains("id=\"deleteWalletNoteModal\""));
|
|
assert!(main.contains("runOwnerMetadataMutation"));
|
|
assert!(main.contains("recoverOwnerStateConflict"));
|
|
}
|
|
|
|
#[test]
|
|
fn pre_010_owner_and_view_authorized_credential_rotations_preserve_session_projection() {
|
|
let root = app_root();
|
|
let security = read_text(root.join("src/wallet_security.rs").as_path());
|
|
let state = read_text(root.join("src/app_state.rs").as_path());
|
|
let tauri = read_text(root.join("src/tauri.rs").as_path());
|
|
let html = read_text(root.join("frontend/main.html").as_path());
|
|
let main = read_text(root.join("frontend/ts/main.ts").as_path());
|
|
assert!(security.contains("WalletPasswordRotationRequestDto"));
|
|
assert!(state.contains("owner.rotate_owner_password"));
|
|
assert!(state.contains("owner.rotate_view_password"));
|
|
assert!(state.contains("view.rotate_view_password"));
|
|
assert!(state.contains("begin_view_operation"));
|
|
assert!(state.contains("finish_view_operation"));
|
|
assert!(state.contains("begin_owner_operation"));
|
|
assert!(state.contains("finish_owner_operation"));
|
|
assert!(tauri.contains("rotate_owner_password"));
|
|
assert!(tauri.contains("rotate_view_password"));
|
|
assert!(html.contains("id=\"rotateOwnerPasswordSubmit\""));
|
|
assert!(html.contains("id=\"rotateViewPasswordSubmit\""));
|
|
assert!(main.contains("rotateWalletPassword"));
|
|
assert!(main.contains("bindRotationActions"));
|
|
assert!(main.contains("viewAuthorized"));
|
|
assert!(main.contains("Les secrets Config"));
|
|
}
|
|
|
|
#[test]
|
|
fn pre_011_strong_view_administration_is_owner_only_and_refreshes_safe_status() {
|
|
let root = app_root();
|
|
let security = read_text(root.join("src/wallet_security.rs").as_path());
|
|
let state = read_text(root.join("src/app_state.rs").as_path());
|
|
let tauri = read_text(root.join("src/tauri.rs").as_path());
|
|
let html = read_text(root.join("frontend/main.html").as_path());
|
|
let main = read_text(root.join("frontend/ts/main.ts").as_path());
|
|
assert!(security.contains("WalletViewSecurityStatusDto"));
|
|
assert!(state.contains("owner.disable_view"));
|
|
assert!(state.contains("owner.recreate_view"));
|
|
assert!(state.contains("result_view_enabled = false"));
|
|
assert!(state.contains("result_view_enabled = true"));
|
|
assert!(tauri.contains("disable_wallet_view"));
|
|
assert!(tauri.contains("recreate_wallet_view"));
|
|
assert!(html.contains("id=\"disableWalletViewModal\""));
|
|
assert!(html.contains("id=\"recreateWalletViewModal\""));
|
|
assert!(html.contains("id=\"disableWalletView\""));
|
|
assert!(html.contains("id=\"recreateWalletView\""));
|
|
assert!(main.contains("runStrongViewDisable"));
|
|
assert!(main.contains("runStrongViewRecreate"));
|
|
assert!(main.contains("applyViewSecurityStatus"));
|
|
assert!(main.contains("bindStrongViewSecurityActions"));
|
|
}
|
|
|
|
#[test]
|
|
fn pre_012_owner_export_uses_rust_native_save_picker_and_wallet_file_adapter() {
|
|
let root = app_root();
|
|
let state = read_text(root.join("src/app_state.rs").as_path());
|
|
let export = read_text(root.join("src/wallet_export.rs").as_path());
|
|
let transfer = read_text(root.join("src/wallet_transfer.rs").as_path());
|
|
let tauri = read_text(root.join("src/tauri.rs").as_path());
|
|
let html = read_text(root.join("frontend/main.html").as_path());
|
|
let main = read_text(root.join("frontend/ts/main.ts").as_path());
|
|
assert!(export.contains("WalletExportRequestDto"));
|
|
assert!(export.contains("WalletExportResultDto"));
|
|
assert!(transfer.contains("WalletTransferFormatDto"));
|
|
assert!(transfer.contains("solana_cli_json"));
|
|
assert!(transfer.contains("solana_keypair_base58"));
|
|
assert!(state.contains("wallet_export_picker_filename"));
|
|
assert!(state.contains("begin_owner_operation(\"keypair_export\")"));
|
|
assert!(state.contains("owner.export_transfer_file"));
|
|
assert!(tauri.contains("blocking_save_file"));
|
|
assert!(tauri.contains("export_wallet_transfer"));
|
|
assert!(html.contains("id=\"walletExportFormat\""));
|
|
assert!(html.contains("id=\"exportWalletKeypair\""));
|
|
assert!(html.contains("id=\"exportWalletKeypairModal\""));
|
|
assert!(main.contains("bindWalletExportActions"));
|
|
assert!(main.contains("export_wallet_transfer"));
|
|
}
|
|
|
|
#[test]
|
|
fn pre_013_integration_compliance_and_devnet_smoke_are_durable_release_gates() {
|
|
let root = app_root();
|
|
let compliance = read_text(root.join("tests/release_compliance.rs").as_path());
|
|
let smoke = read_text(root.join("tests/wallet_desk_devnet_smoke.rs").as_path());
|
|
let validation = read_text(root.join("../../docs/validation/009-V0_2_6_WALLET_DESK_COMPLIANCE.md").as_path());
|
|
assert!(compliance.contains("wallet_desk_dependency_firewall_and_tauri_capabilities_are_minimal"));
|
|
assert!(compliance.contains("frontend_has_no_direct_filesystem_network_or_secret_persistence_surface"));
|
|
assert!(smoke.contains("committed_wallet_desk_composite_creates_wallet_and_reaches_devnet_balance"));
|
|
assert!(smoke.contains("#[ignore"));
|
|
assert!(validation.contains("Config -> Wallet -> Transport -> Devnet getBalance"));
|
|
}
|
|
|
|
#[test]
|
|
fn pre_014_template_has_normalized_html_headers_light_header_and_kbot_style_splash_contract() {
|
|
let root = app_root();
|
|
let main = read_text(root.join("frontend/main.html").as_path());
|
|
let splash = read_text(root.join("frontend/splash.html").as_path());
|
|
let app_style = read_text(root.join("frontend/sass/_app.scss").as_path());
|
|
let main_ts = read_text(root.join("frontend/ts/main.ts").as_path());
|
|
let state = read_text(root.join("src/app_state.rs").as_path());
|
|
let splash_style = read_text(root.join("frontend/sass/splash.scss").as_path());
|
|
let splash_ts = read_text(root.join("frontend/ts/splash.ts").as_path());
|
|
assert!(main.starts_with("<!-- file: crates/ksp-app-wallet-desk/frontend/main.html -->"));
|
|
assert!(main.contains("navbar h-100 py-0 bg-light text-dark"));
|
|
assert!(main.contains("ps-2 fs-4 fw-semibold text-primary text-nowrap\">Wallet Desk"));
|
|
assert!(main.contains("row g-0 h-100 flex-nowrap"));
|
|
assert!(main.contains("col app-content app-scrollable h-100"));
|
|
assert!(main.contains("card app-shell-card mx-auto shadow-sm border-0"));
|
|
assert!(main.contains("card-body p-4"));
|
|
assert!(main.contains("© 2026 SASEDEV"));
|
|
assert!(!main.contains("id=\"shellStatus\""));
|
|
assert!(app_style.contains("flex-wrap: nowrap"));
|
|
assert!(app_style.contains("min-width: 0"));
|
|
assert!(state.contains("pre.014-desktop-polish"));
|
|
assert!(main_ts.contains("pre.014-desktop-polish"));
|
|
assert!(!main_ts.contains("#shellStatus"));
|
|
assert!(main.contains("app-sidebar"));
|
|
assert!(splash.starts_with("<!-- file: crates/ksp-app-wallet-desk/frontend/splash.html -->"));
|
|
assert!(splash.contains("id=\"debug-info\""));
|
|
assert!(splash.contains("id=\"messages-container\""));
|
|
assert!(splash.contains("sass/splash.scss"));
|
|
assert!(splash_style.contains("overflow: hidden"));
|
|
assert!(splash_style.contains("width: 100%"));
|
|
assert!(splash_style.contains("user-select: none"));
|
|
assert!(splash_ts.contains("add_debug"));
|
|
assert!(splash_ts.contains("add_message"));
|
|
assert!(!splash_ts.contains("../sass/splash.scss"));
|
|
}
|
|
|
|
#[test]
|
|
fn pre_016_wallet_desk_uses_version_neutral_wallet_dispatch() {
|
|
let state = read_source("src/app_state.rs");
|
|
let inventory = read_source("src/wallet_inventory.rs");
|
|
assert!(state.contains("ksp_wallet_lib::create_wallet_file"));
|
|
assert!(state.contains("ksp_wallet_lib::import_wallet_transfer"));
|
|
assert!(state.contains("ksp_wallet_lib::open_wallet_view_file"));
|
|
assert!(state.contains("ksp_wallet_lib::open_wallet_owner_file"));
|
|
assert!(inventory.contains("ksp_wallet_lib::inspect_locked_wallet_file"));
|
|
assert!(!state.contains("create_wallet_file_v1"));
|
|
assert!(!state.contains("import_wallet_transfer_v1"));
|
|
assert!(!state.contains("open_wallet_view_file_v1"));
|
|
assert!(!state.contains("open_wallet_owner_file_v1"));
|
|
assert!(!inventory.contains("inspect_locked_wallet_file_v1"));
|
|
}
|
|
|
|
#[test]
|
|
fn pre_017_wallet_desk_open_paths_remain_non_migrating() {
|
|
let state = read_source("src/app_state.rs");
|
|
let inventory = read_source("src/wallet_inventory.rs");
|
|
assert!(!state.contains("migrate_wallet_v1_to_v2"));
|
|
assert!(!state.contains("migrate_wallet_file_v1_to_v2"));
|
|
assert!(!inventory.contains("migrate_wallet_v1_to_v2"));
|
|
assert!(state.contains("ksp_wallet_lib::open_wallet_view_file"));
|
|
assert!(state.contains("ksp_wallet_lib::open_wallet_owner_file"));
|
|
assert!(inventory.contains("ksp_wallet_lib::inspect_locked_wallet_file"));
|
|
}
|
|
|
|
#[test]
|
|
fn pre_018_packaged_runtime_bundles_config_resources_and_keeps_wallet_desk_version_coherent() {
|
|
let root = app_root();
|
|
let tauri = read_json(root.join("tauri.conf.json").as_path());
|
|
assert!(tauri.pointer("/version").is_none(), "Wallet Desk must let Tauri derive the bundle version from Cargo");
|
|
let package = read_json(root.join("package.json").as_path());
|
|
assert_eq!(package.pointer("/private").and_then(serde_json::Value::as_bool), std::option::Option::Some(true));
|
|
let resources = tauri.pointer("/bundle/resources").and_then(serde_json::Value::as_object);
|
|
assert!(resources.is_some(), "packaged Wallet Desk Config resources map must exist");
|
|
if let std::option::Option::Some(resources) = resources {
|
|
assert_eq!(resources.len(), 15);
|
|
assert_eq!(
|
|
resources.get("../../config/composite.ksp-app-backfill-desk.json").and_then(serde_json::Value::as_str),
|
|
std::option::Option::Some("config/composite.ksp-app-backfill-desk.json"),
|
|
);
|
|
assert_eq!(
|
|
resources.get("../../config/composite.ksp-app-solprices-desk.json").and_then(serde_json::Value::as_str),
|
|
std::option::Option::Some("config/composite.ksp-app-solprices-desk.json"),
|
|
);
|
|
assert_eq!(
|
|
resources.get("../../config/composite.ksp-app-store-desk.json").and_then(serde_json::Value::as_str),
|
|
std::option::Option::Some("config/composite.ksp-app-store-desk.json"),
|
|
);
|
|
assert_eq!(
|
|
resources.get("../../config/composite.ksp-app-wallet-desk.json").and_then(serde_json::Value::as_str),
|
|
std::option::Option::Some("config/composite.ksp-app-wallet-desk.json"),
|
|
);
|
|
assert_eq!(
|
|
resources.get("../../config/schemas/composite.schema.json").and_then(serde_json::Value::as_str),
|
|
std::option::Option::Some("config/schemas/composite.schema.json"),
|
|
);
|
|
assert_eq!(
|
|
resources.get("../../config/std.offchain_transport.json").and_then(serde_json::Value::as_str),
|
|
std::option::Option::Some("config/std.offchain_transport.json"),
|
|
);
|
|
assert_eq!(resources.get("../../config/std.store.json").and_then(serde_json::Value::as_str), std::option::Option::Some("config/std.store.json"),);
|
|
assert_eq!(
|
|
resources.get("../../config/schemas/std.store.schema.json").and_then(serde_json::Value::as_str),
|
|
std::option::Option::Some("config/schemas/std.store.schema.json"),
|
|
);
|
|
assert_eq!(
|
|
resources.get("../../config/schemas/std.offchain_transport.schema.json").and_then(serde_json::Value::as_str),
|
|
std::option::Option::Some("config/schemas/std.offchain_transport.schema.json"),
|
|
);
|
|
}
|
|
let main = read_text(root.join("frontend/main.html").as_path());
|
|
let main_ts = read_text(root.join("frontend/ts/main.ts").as_path());
|
|
assert!(main.contains(r#"id="appVersionBadge""#));
|
|
assert!(main_ts.contains("setText(\"#appVersionBadge\", status.applicationVersion);"));
|
|
let tauri_source = read_text(root.join("src/tauri.rs").as_path());
|
|
assert!(tauri_source.contains("ksp_config_lib::prepare_packaged_runtime"));
|
|
assert!(tauri_source.contains("tauri::utils::platform::resource_dir"));
|
|
assert!(tauri_source.contains("std::env::set_current_dir(layout.runtime_root())"));
|
|
}
|
|
|
|
#[test]
|
|
fn v0_2_12_pre_008_wallet_balance_refresh_adds_average_and_exact_usd_equivalent() {
|
|
let root = app_root();
|
|
let manifest = read_text(root.join("Cargo.toml").as_path());
|
|
let composite = read_text(root.join("../../config/composite.ksp-app-wallet-desk.json").as_path());
|
|
let state = read_text(root.join("src/app_state.rs").as_path());
|
|
let balance = read_text(root.join("src/wallet_balance.rs").as_path());
|
|
let main = read_text(root.join("frontend/ts/main.ts").as_path());
|
|
let html = read_text(root.join("frontend/main.html").as_path());
|
|
assert!(manifest.contains(r#"ksp-offchain-transport-lib = { path = "../ksp-offchain-transport-lib" }"#));
|
|
assert!(composite.contains(r#""component_id": "offchain_transport""#));
|
|
assert!(composite.contains(r#""profile_id": "public_keyless""#));
|
|
assert!(state.contains("initialize_offchain_transport"));
|
|
assert!(state.contains("refresh_sol_usd_average"));
|
|
assert!(state.contains("tokio::join!"));
|
|
assert!(state.contains("refresh_all().await"));
|
|
assert!(balance.contains("sol_usd_average"));
|
|
assert!(balance.contains("sol_usd_equivalent"));
|
|
assert!(balance.contains("average_sol_usd_prices"));
|
|
assert!(html.contains(r#"id="currentWalletSolUsdAverage""#));
|
|
assert!(html.contains(r#"id="currentWalletSolUsdEquivalent""#));
|
|
assert!(html.contains(r#"id="detailsSolUsdAverage""#));
|
|
assert!(html.contains(r#"id="detailsSolUsdEquivalent""#));
|
|
assert!(main.contains(r#"balance.solUsdAverage ? `${balance.solUsdAverage} USD/SOL` : "N.A.""#));
|
|
assert!(main.contains(r#"balance.solUsdEquivalent ? `${balance.solUsdEquivalent} USD` : "N.A.""#));
|
|
assert!(!main.contains("parseFloat("));
|
|
assert!(!main.contains("Number(balance.sol"));
|
|
assert!(!main.contains("refresh_market_price"));
|
|
assert!(!main.contains("refresh_all_market_prices"));
|
|
assert!(!main.contains("fetch("));
|
|
}
|