radrootsd

JSON-RPC bridge for Radroots event publishing
git clone https://radroots.dev/git/radrootsd.git
Log | Files | Refs | README | LICENSE

commit 30b7eb3ff07dc3c1f7c302c2959e56ec793dbb07
parent 7774f24d1bdcff4c23d83d41e822c8ec9180fdd9
Author: triesap <tyson@radroots.org>
Date:   Fri,  3 Jul 2026 06:40:17 +0000

runtime: remove migration startup report

- drop runtime migration contract fields from startup reporting
- remove legacy path inspection from path contract output
- replace migration tests with canonical path contract coverage
- keep daemon startup logging on active runtime paths only

Diffstat:
Msrc/app/paths.rs | 101+++++++++++++++++++++----------------------------------------------------------
Msrc/app/runtime.rs | 26+++-----------------------
2 files changed, 29 insertions(+), 98 deletions(-)

diff --git a/src/app/paths.rs b/src/app/paths.rs @@ -1,12 +1,10 @@ use std::path::{Path, PathBuf}; -use anyhow::{Context, Result}; +use anyhow::Result; use radroots_runtime_paths::{ - DEFAULT_CONFIG_FILE_NAME, DEFAULT_SERVICE_IDENTITY_FILE_NAME, RadrootsLegacyPathCandidate, - RadrootsMigrationReport, RadrootsPathProfile, RadrootsPathResolver, - RadrootsRuntimeMigrationContract, RadrootsRuntimePathSelection, - RadrootsRuntimeSelectionContract, RadrootsRuntimeSelectionOverrideContract, - inspect_legacy_paths, runtime_migration_contract, + DEFAULT_CONFIG_FILE_NAME, DEFAULT_SERVICE_IDENTITY_FILE_NAME, RadrootsPathProfile, + RadrootsPathResolver, RadrootsRuntimePathSelection, RadrootsRuntimeSelectionContract, + RadrootsRuntimeSelectionOverrideContract, }; use serde::Serialize; @@ -22,7 +20,6 @@ const SUBORDINATE_PATH_OVERRIDE_KEYS: [&str; 2] = [ "config.service.logs_dir", "config.publish_proxy.database_path", ]; -const MIGRATION_IMPORT_HINT: &str = "stop the runtime, inspect this legacy path, then perform an explicit import or manual copy into the canonical destination; radrootsd will not move it on startup"; #[derive(Debug, Clone, PartialEq, Eq)] pub(crate) struct RadrootsdRuntimePaths { @@ -39,14 +36,12 @@ pub struct RadrootsdRuntimeContractOutput { pub path_overrides: RadrootsdRuntimePathOverrideContractOutput, pub default_shared_secret_backend: String, pub allowed_shared_secret_backends: Vec<String>, - pub migration: RadrootsdRuntimeMigrationContractOutput, pub canonical_config_path: PathBuf, pub canonical_logs_dir: PathBuf, pub canonical_identity_path: PathBuf, pub canonical_publish_proxy_database_path: PathBuf, } -pub type RadrootsdRuntimeMigrationContractOutput = RadrootsRuntimeMigrationContract; pub type RadrootsdRuntimePathOverrideContractOutput = RadrootsRuntimeSelectionOverrideContract; pub(crate) fn process_path_selection() -> Result<(RadrootsPathProfile, Option<PathBuf>)> { @@ -149,7 +144,6 @@ fn runtime_contract_with_selection( .into_iter() .map(str::to_owned) .collect(), - migration: runtime_migration_contract(RadrootsMigrationReport::empty()), canonical_config_path: paths.config_path, canonical_logs_dir: paths.logs_dir, canonical_identity_path: paths.identity_path, @@ -157,53 +151,6 @@ fn runtime_contract_with_selection( }) } -#[allow(dead_code)] -pub(crate) fn runtime_migration_for_process( - contract: &RadrootsdRuntimeContractOutput, -) -> Result<RadrootsdRuntimeMigrationContractOutput> { - let current_dir = std::env::current_dir().context("resolve current directory")?; - Ok(runtime_migration_for_current_dir( - contract, - current_dir.as_path(), - )) -} - -pub(crate) fn runtime_migration_for_current_dir( - contract: &RadrootsdRuntimeContractOutput, - current_dir: &Path, -) -> RadrootsdRuntimeMigrationContractOutput { - let report = inspect_legacy_paths(legacy_path_candidates(contract, current_dir)); - migration_contract_output(report) -} - -fn legacy_path_candidates( - contract: &RadrootsdRuntimeContractOutput, - current_dir: &Path, -) -> Vec<RadrootsLegacyPathCandidate> { - vec![ - RadrootsLegacyPathCandidate::new( - "radrootsd_repo_config_v0", - "legacy radrootsd repo-relative config", - current_dir.join(DEFAULT_CONFIG_FILE_NAME), - Some(contract.canonical_config_path.clone()), - MIGRATION_IMPORT_HINT, - ), - RadrootsLegacyPathCandidate::new( - "radrootsd_repo_logs_v0", - "legacy radrootsd repo-relative logs directory", - current_dir.join("logs"), - Some(contract.canonical_logs_dir.clone()), - MIGRATION_IMPORT_HINT, - ), - ] -} - -fn migration_contract_output( - report: RadrootsMigrationReport, -) -> RadrootsdRuntimeMigrationContractOutput { - runtime_migration_contract(report) -} - #[cfg(test)] mod tests { use std::path::PathBuf; @@ -212,7 +159,7 @@ mod tests { RadrootsHostEnvironment, RadrootsPathProfile, RadrootsPathResolver, RadrootsPlatform, }; - use super::{runtime_contract_with_resolver, runtime_migration_for_current_dir}; + use super::runtime_contract_with_resolver; fn linux_resolver() -> RadrootsPathResolver { RadrootsPathResolver::new( @@ -225,13 +172,7 @@ mod tests { } #[test] - fn runtime_migration_detects_legacy_repo_relative_state_without_moving_it() { - let temp = tempfile::tempdir().expect("tempdir"); - std::fs::write( - temp.path().join("config.toml"), - "[metadata]\nname = \"old\"\n", - ) - .expect("write old config"); + fn runtime_contract_output_contains_canonical_runtime_paths() { let contract = runtime_contract_with_resolver( &linux_resolver(), RadrootsPathProfile::InteractiveUser, @@ -239,19 +180,29 @@ mod tests { ) .expect("contract"); - let report = runtime_migration_for_current_dir(&contract, temp.path()); - - assert_eq!(report.posture, "explicit_operator_import_required"); - assert_eq!(report.state, "legacy_state_detected"); - assert!(!report.silent_startup_relocation); - assert_eq!(report.detected_legacy_paths.len(), 1); + assert_eq!(contract.active_profile, "interactive_user"); + assert_eq!( + contract.allowed_profiles, + ["interactive_user", "service_host", "repo_local"] + ); + assert_eq!(contract.path_overrides.root_source, "host_defaults"); + assert_eq!( + contract.canonical_config_path, + PathBuf::from("/home/treesap/.radroots/config/services/radrootsd/config.toml") + ); + assert_eq!( + contract.canonical_logs_dir, + PathBuf::from("/home/treesap/.radroots/logs/services/radrootsd") + ); assert_eq!( - report.detected_legacy_paths[0].id, - "radrootsd_repo_config_v0" + contract.canonical_identity_path, + PathBuf::from( + "/home/treesap/.radroots/secrets/services/radrootsd/identity.secret.json" + ) ); assert_eq!( - report.detected_legacy_paths[0].destination, - Some(contract.canonical_config_path) + contract.canonical_publish_proxy_database_path, + PathBuf::from("/home/treesap/.radroots/data/services/radrootsd/publish_proxy.sqlite") ); } } diff --git a/src/app/runtime.rs b/src/app/runtime.rs @@ -61,7 +61,6 @@ struct RadrootsdRuntimeStartupReport { publish_proxy_database_path_source: String, canonical_publish_proxy_database_path: PathBuf, path_overrides: paths::RadrootsdRuntimePathOverrideContractOutput, - migration: paths::RadrootsdRuntimeMigrationContractOutput, default_shared_secret_backend: String, allowed_shared_secret_backends: Vec<String>, } @@ -156,7 +155,6 @@ fn runtime_startup_report( args: &cli::Args, settings: &config::Settings, contract: &paths::RadrootsdRuntimeContractOutput, - migration: paths::RadrootsdRuntimeMigrationContractOutput, ) -> RadrootsdRuntimeStartupReport { RadrootsdRuntimeStartupReport { active_profile: contract.active_profile.clone(), @@ -205,7 +203,6 @@ fn runtime_startup_report( .canonical_publish_proxy_database_path .clone(), path_overrides: contract.path_overrides.clone(), - migration, default_shared_secret_backend: contract.default_shared_secret_backend.clone(), allowed_shared_secret_backends: contract.allowed_shared_secret_backends.clone(), } @@ -240,10 +237,6 @@ fn log_runtime_startup_report(report: &RadrootsdRuntimeStartupReport) { repo_local_root = ?report.path_overrides.repo_local_root, repo_local_root_source = ?report.path_overrides.repo_local_root_source, subordinate_path_override_source = report.path_overrides.subordinate_path_override_source.as_str(), - migration_posture = report.migration.posture.as_str(), - migration_state = report.migration.state.as_str(), - migration_detected_legacy_paths = report.migration.detected_legacy_paths.len(), - silent_startup_relocation = report.migration.silent_startup_relocation, config_path = %report.config_path.display(), config_path_source = report.config_path_source.as_str(), canonical_config_path = %report.canonical_config_path.display(), @@ -440,9 +433,7 @@ pub async fn run() -> Result<()> { #[cfg(not(test))] { let contract = paths::runtime_contract_for_process().context("resolve runtime contract")?; - let migration = - paths::runtime_migration_for_process(&contract).context("inspect runtime migration")?; - let report = runtime_startup_report(&args, &settings, &contract, migration); + let report = runtime_startup_report(&args, &settings, &contract); log_runtime_startup_report(&report); } @@ -613,13 +604,6 @@ mod tests { }, default_shared_secret_backend: "encrypted_file".to_string(), allowed_shared_secret_backends: vec!["encrypted_file".to_string()], - migration: paths::RadrootsdRuntimeMigrationContractOutput { - posture: "explicit_operator_import_required".to_string(), - state: "ready".to_string(), - silent_startup_relocation: false, - compatibility_window: "detect_and_report_only".to_string(), - detected_legacy_paths: Vec::new(), - }, canonical_config_path: PathBuf::from( "/home/treesap/.radroots/config/services/radrootsd/config.toml", ), @@ -854,8 +838,7 @@ mod tests { PathBuf::from("/tmp/radrootsd/publish_proxy.sqlite"); let contract = sample_runtime_contract(); - let report = - runtime_startup_report(&args, &settings, &contract, contract.migration.clone()); + let report = runtime_startup_report(&args, &settings, &contract); assert_eq!( report, @@ -882,7 +865,6 @@ mod tests { "/home/treesap/.radroots/data/services/radrootsd/publish_proxy.sqlite" ), path_overrides: sample_runtime_contract().path_overrides, - migration: sample_runtime_contract().migration, default_shared_secret_backend: "encrypted_file".to_string(), allowed_shared_secret_backends: vec!["encrypted_file".to_string()], } @@ -905,8 +887,7 @@ mod tests { settings.config.publish_proxy.database_path = contract.canonical_publish_proxy_database_path.clone(); - let report = - runtime_startup_report(&args, &settings, &contract, contract.migration.clone()); + let report = runtime_startup_report(&args, &settings, &contract); assert_eq!(report.config_path, contract.canonical_config_path); assert_eq!(report.config_path_source, "profile_default"); @@ -920,7 +901,6 @@ mod tests { ); assert_eq!(report.publish_proxy_database_path_source, "profile_default"); assert_eq!(report.path_overrides, contract.path_overrides); - assert_eq!(report.migration, contract.migration); assert_eq!(report.default_shared_secret_backend, "encrypted_file"); assert_eq!( report.allowed_shared_secret_backends,