{"record":{"id":"5cc6f6fd353f20b9","repo":"astrid-runtime/astrid","slug":"winfsp-mountpoint-is-not-a-directory","errorCode":null,"errorMessage":"WinFsp mountpoint is not a directory: {}","messagePattern":"WinFsp mountpoint is not a directory: (.+?)","errorType":"validation","errorClass":null,"httpStatus":null,"severity":"error","filePath":"crates/astrid-storage-provider-winfsp/src/win.rs","lineNumber":108,"sourceCode":"    stdout.flush().context(\"flush WinFsp readiness\")?;\n\n    let result = runtime.block_on(daemon_loop(filesystem, control_listener));\n    if let Err(error) = result {\n        eprintln!(\"{PROVIDER_NAME}: daemon stopped after failure: {error:#}\");\n        return Err(error);\n    }\n    Ok(())\n}\n\nfn wait_for_mountpoint_ready(mountpoint: &Path) -> Result<()> {\n    let started = Instant::now();\n    loop {\n        // A directory mount is represented by a WinFsp junction. Follow that\n        // reparse point so readiness proves the mounted root is serving I/O,\n        // rather than inspecting the junction object itself.\n        match std::fs::metadata(mountpoint) {\n            Ok(metadata) if metadata.is_dir() => return Ok(()),\n            Ok(_) => bail!(\n                \"WinFsp mountpoint is not a directory: {}\",\n                mountpoint.display()\n            ),\n            Err(error) if error.kind() == std::io::ErrorKind::NotFound => {},\n            Err(error) => {\n                return Err(error).with_context(|| {\n                    format!(\n                        \"inspect WinFsp mountpoint readiness {}\",\n                        mountpoint.display()\n                    )\n                });\n            },\n        }\n        if started.elapsed() >= MOUNTPOINT_READY_TIMEOUT {\n            bail!(\n                \"WinFsp mountpoint did not become ready within {} seconds: {}\",\n                MOUNTPOINT_READY_TIMEOUT.as_secs(),\n                mountpoint.display()","sourceCodeStart":90,"sourceCodeEnd":126,"githubUrl":"https://github.com/astrid-runtime/astrid/blob/affd8760f44190dbdfbec23403f4c4b642c33112/crates/astrid-storage-provider-winfsp/src/win.rs#L90-L126","documentation":"wait_for_mountpoint_ready polls the mountpoint until std::fs::metadata reports a directory. A directory mount appears as a WinFsp junction; the code follows the reparse point so readiness means the mounted root actually serves I/O. If the path exists but metadata says it is not a directory (typically a regular file), the wait fails immediately with this error.","triggerScenarios":"A regular file exists at the requested mountpoint path, so when the poll finds Ok(metadata) and metadata.is_dir() is false, it bails with the formatted path.","commonSituations":"Creating the mountpoint with `touch` or a tool that made a file instead of a directory; a leftover file from a previous run at the same path; a stale junction replaced by a file.","solutions":["Delete or rename the file occupying the mountpoint path and create a directory in its place (mkdir)","Pick a different mountpoint path that does not exist or is a directory","Before mounting, check fs::metadata and abort early if the path exists but is not a directory"],"exampleFix":"// before\nstd::fs::write(\"C:\\\\mounts\\\\astrid\", \"\")?; // creates a file at the mountpoint\nmount(...)?;\n// after\nif let Ok(md) = std::fs::metadata(\"C:\\\\mounts\\\\astrid\") {\n    assert!(md.is_dir(), \"mountpoint must be a directory\");\n} else {\n    std::fs::create_dir_all(\"C:\\\\mounts\\\\astrid\")?;\n}\nmount(...)?;","handlingStrategy":"validation","validationCode":"if let Ok(md) = std::fs::metadata(&mountpoint) {\n    if !md.is_dir() {\n        return Err(format!(\"{} exists and is not a directory; remove it or choose another path\", mountpoint.display()));\n    }\n}","typeGuard":"fn is_directory(p: &Path) -> bool {\n    std::fs::metadata(p).map(|m| m.is_dir()).unwrap_or(false)\n}","tryCatchPattern":"match mount_err {\n    Err(e) if e.to_string().contains(\"not a directory\") => {\n        let _ = std::fs::remove_file(&mountpoint);\n        std::fs::create_dir_all(&mountpoint)?;\n        retry_mount()?;\n    }\n    other => other?,\n}","preventionTips":["mkdir (not touch) the intended mountpoint before mounting","Use unique mountpoint paths per run to avoid stale-file collisions","Check path existence/type in mount-preparation code"],"tags":["windows","winfsp","mount","paths"],"backgroundTag":"path-is-not-a-directory","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"}