{"record":{"id":"94319bc303071e7e","repo":"astrid-runtime/astrid","slug":"astrid-durable-media-is-redirected-or-not-a-regula","errorCode":null,"errorMessage":"Astrid durable media is redirected or not a regular file: {}","messagePattern":"Astrid durable media is redirected or not a regular file: (.+?)","errorType":"exception","errorClass":"io::Error","httpStatus":null,"severity":"error","filePath":"crates/astrid-core/src/dirs.rs","lineNumber":514,"sourceCode":"                        \"Astrid durable media is redirected or not a regular file: {}\",\n                        path.display()\n                    ),\n                ));\n            }\n            crate::platform_fs::validate_private_file(&path)?;\n            state = UnsentinelledRootState::StoppedVolume;\n        }\n        Ok(state)\n    }\n\n    fn validate_runtime_key_bootstrap(&self, keys_dir: &Path) -> io::Result<()> {\n        crate::platform_fs::validate_private_directory(keys_dir)?;\n        let mut entries = keys_dir.read_dir()?.collect::<Result<Vec<_>, _>>()?;\n        entries.sort_by_key(std::fs::DirEntry::file_name);\n        for entry in entries {\n            let path = entry.path();\n            if path != self.runtime_key_path() {\n                return Err(io::Error::new(\n                    io::ErrorKind::InvalidData,\n                    format!(\n                        \"unadmitted entry in the fresh runtime-key bootstrap: {}\",\n                        path.display()\n                    ),\n                ));\n            }\n            crate::platform_fs::validate_private_file(&path)?;\n        }\n        Ok(())\n    }\n\n    /// Root directory path (`~/.astrid/`).\n    #[must_use]\n    pub fn root(&self) -> &Path {\n        &self.root\n    }\n","sourceCodeStart":496,"sourceCodeEnd":532,"githubUrl":"https://github.com/astrid-runtime/astrid/blob/affd8760f44190dbdfbec23403f4c4b642c33112/crates/astrid-core/src/dirs.rs#L496-L532","documentation":"Thrown by validate_runtime_key_bootstrap (invoked from validate_fresh_root_entries) in crates/astrid-core/src/dirs.rs:514 when, during runtime-key provisioning, the keys directory contains an entry other than the expected runtime key file, or (per the message at this site) the durable media for the runtime key is a symlink or not a regular file. The bootstrap path must contain exactly the one expected key file as a regular file; anything else fails with InvalidData.","triggerScenarios":"Running validate_runtime_identity_provisioning/ensure() when keys_dir contains extra files (leftover keys, editor backups like key.bak, .DS_Store), or the runtime key file itself is a symlink or non-regular file (redirected media).","commonSituations":"Re-provisioning after a partial install left stale key material; users symlinking key files into secret managers or mounted secrets; backup-restore tools recreating keys as directories or symlinks.","solutions":["Empty the keys directory so it contains only the expected runtime key file, then re-run provisioning.","Replace any symlinked/non-regular key file with a real regular file (copy the bytes, don't link).","Regenerate the runtime key through the normal provisioning flow if the existing material is untrusted.","Check with symlink_metadata (`ls -la`) that the key is a regular file before provisioning."],"exampleFix":"# before\n$ ls -la ~/.astrid/keys\nruntime.key -> /run/secrets/key\nerror: Astrid durable media is redirected or not a regular file\n\n# after\n$ rm ~/.astrid/keys/runtime.key\n$ cp /run/secrets/key ~/.astrid/keys/runtime.key\n$ chmod 600 ~/.astrid/keys/runtime.key","handlingStrategy":"validation","validationCode":"// Rust\nfn keys_dir_clean(keys_dir: &Path, expected_key: &Path) -> io::Result<()> {\n    for entry in std::fs::read_dir(keys_dir)? {\n        let path = entry?.path();\n        let md = std::fs::symlink_metadata(&path)?;\n        if path != expected_key || md.file_type().is_symlink() || !md.is_file() {\n            return Err(io::Error::new(io::ErrorKind::InvalidData,\n                format!(\"bad keys dir entry: {}\", path.display())));\n        }\n    }\n    Ok(())\n}","typeGuard":"fn is_regular_key_file(path: &Path) -> bool {\n    std::fs::symlink_metadata(path)\n        .map(|md| !md.file_type().is_symlink() && md.is_file())\n        .unwrap_or(false)\n}","tryCatchPattern":"match provisioning_result {\n    Err(e) if e.kind() == io::ErrorKind::InvalidData => {\n        // clean keys dir of extra entries, replace symlinks with real files, retry\n    }\n    r => r?,\n}","preventionTips":["Keep the keys directory containing only the expected runtime key","Copy secret-manager material into a regular file instead of symlinking","Set restrictive permissions (0600) on key files, don't relocate them via links","Inspect keys dir after backup restores before re-provisioning"],"tags":["filesystem","symlink","keys","security"],"backgroundTag":"invalid-argument-value","analyzedSha":"affd8760f44190dbdfbec23403f4c4b642c33112","analyzedAt":"2026-09-09T21:28:12.402Z","contentChangedAt":"2026-09-09T21:28:12.402Z","schemaVersion":2},"datasetVersion":"2026-09-14T05:17:10.506Z"}