{"record":{"id":"f7ac7340ff47783d","repo":"spacedriveapp/spacedrive","slug":"could-not-determine-binary-directory","errorCode":null,"errorMessage":"Could not determine binary directory","messagePattern":"Could not determine binary directory","errorType":"exception","errorClass":"anyhow::Error","httpStatus":null,"severity":"error","filePath":"apps/cli/src/domains/daemon/mod.rs","lineNumber":47,"sourceCode":"\t\tdirs::home_dir().ok_or_else(|| anyhow::anyhow!(\"Could not determine home directory\"))?;\n\tlet launch_agents_dir = home.join(\"Library/LaunchAgents\");\n\n\t// Create LaunchAgents directory if it doesn't exist\n\tfs::create_dir_all(&launch_agents_dir)?;\n\n\t// Determine plist filename based on instance\n\tlet plist_name = if let Some(ref inst) = instance {\n\t\tformat!(\"com.spacedrive.daemon.{}.plist\", inst)\n\t} else {\n\t\t\"com.spacedrive.daemon.plist\".to_string()\n\t};\n\tlet plist_path = launch_agents_dir.join(&plist_name);\n\n\t// Get the current daemon binary path\n\tlet current_exe = std::env::current_exe()?;\n\tlet daemon_path = current_exe\n\t\t.parent()\n\t\t.ok_or_else(|| anyhow::anyhow!(\"Could not determine binary directory\"))?\n\t\t.join(\"sd-daemon\");\n\n\tif !daemon_path.exists() {\n\t\treturn Err(anyhow::anyhow!(\n\t\t\t\"Daemon binary not found at {}. Ensure both 'sd-cli' and 'sd-daemon' are in the same directory.\",\n\t\t\tdaemon_path.display()\n\t\t));\n\t}\n\n\t// Determine log paths\n\tlet log_dir = data_dir.join(\"logs\");\n\tfs::create_dir_all(&log_dir)?;\n\tlet stdout_log = log_dir.join(\"daemon.out.log\");\n\tlet stderr_log = log_dir.join(\"daemon.err.log\");\n\n\t// Build program arguments\n\tlet mut program_args = vec![\n\t\tdaemon_path.to_string_lossy().to_string(),","sourceCodeStart":29,"sourceCodeEnd":65,"githubUrl":"https://github.com/spacedriveapp/spacedrive/blob/6dfeccf2113039e35f2ce735f945e70dc3e4ea45/apps/cli/src/domains/daemon/mod.rs#L29-L65","documentation":"Returned by the sync transport's request path when the in-memory device registry (a read-guarded map) has no NodeId mapping for the target device UUID. The registry only knows paired-and-connected devices, so the message names the two causes directly: the device was never paired with this instance, or it is currently offline/disconnected. This fails before any stream is opened.","triggerScenarios":"Calling send_request (or any transport API resolving device UUID → NodeId) for a device that has not completed pairing with this node, or one whose connection dropped so it was removed from the live registry.","commonSituations":"Trying to sync before finishing the pairing handshake; target daemon restarted and not yet reconnected; registry populated per-session so a daemon restart clears it until peers reconnect; stale device UUID persisted by a client.","solutions":["Verify the device is paired (check the pairing/registry state via the device API) and re-pair if not.","Confirm the target daemon is running and connected; wait for it to reappear in the registry after restarts.","Validate the UUID being passed matches the currently paired device (not an old identifier).","Retry the request once the peer reconnects — this is a connectivity-precondition failure, not a message-format problem."],"exampleFix":"// before\ntransport.send_request(device_uuid, request).await?; // errors if offline\n\n// after (check registry first)\nlet online = {\n    let reg = device_registry.read().await;\n    reg.get_node_id_for_device(device_uuid).is_some()\n};\nif !online {\n    // wait for reconnect / prompt user; do not send\n    return Err(anyhow::anyhow!(\"device offline, retry later\"));\n}\ntransport.send_request(device_uuid, request).await?;","handlingStrategy":"validation","validationCode":"// Check the registry before sending; avoid the round trip entirely.\nasync fn device_available(\n    registry: &tokio::sync::RwLock<DeviceRegistry>,\n    device: uuid::Uuid,\n) -> bool {\n    registry.read().await.get_node_id_for_device(device).is_some()\n}","typeGuard":null,"tryCatchPattern":"match transport.send_request(target_device, request).await {\n    Ok(resp) => Ok(resp),\n    Err(e) if e.to_string().contains(\"not found in registry\") => {\n        // precondition failure: prompt pairing or wait for reconnect; do not blind-retry\n        Err(mark_device_offline(target_device, e))\n    }\n    Err(e) => Err(e),\n}","preventionTips":["Complete pairing before exposing sync UI for a device.","Drive UI availability off the registry (online/offline state), not assumptions.","Remember the registry is session-scoped: after daemon restarts, wait for peers to reconnect before sending."],"tags":["rust","networking","p2p","pairing","offline"],"backgroundTag":null,"analyzedSha":"6dfeccf2113039e35f2ce735f945e70dc3e4ea45","analyzedAt":"2026-08-16T11:26:17.074Z","schemaVersion":2},"datasetVersion":"2026-08-16T13:17:31.715Z"}