{"record":{"id":"493db6ed38d910a3","repo":"xai-org/grok-build","slug":"exactly-one-of-worktreepath-or-idorpath-must-be-se","errorCode":null,"errorMessage":"exactly one of worktreePath or idOrPath must be set, not both","messagePattern":"exactly one of worktreePath or idOrPath must be set, not both","errorType":"validation","errorClass":"anyhow::Error","httpStatus":null,"severity":"error","filePath":"crates/codegen/xai-grok-workspace/src/worktree/mod.rs","lineNumber":1329,"sourceCode":"        session_id: req.session_id.clone(),\n        worktree_path: absolute_path,\n        commit: report.commit,\n        source_git_root,\n        copied_changes: Some(copied_changes),\n    }\n}\n\n// ============================================================================\n// Remove Worktree\n// ============================================================================\n\npub async fn remove_worktree(\n    req: &RemoveWorktreeRequest,\n    copy_context: &BackgroundCopyContext,\n) -> Result<RemoveWorktreeResponse> {\n    let resolved = match (&req.worktree_path, &req.id_or_path) {\n        (Some(_), Some(_)) => {\n            anyhow::bail!(\"exactly one of worktreePath or idOrPath must be set, not both\")\n        }\n        (Some(path), None) => path.clone(),\n        (None, Some(id)) => match resolve_worktree_by_id_or_path(id)? {\n            Some(p) => p.display().to_string(),\n            None => anyhow::bail!(\"worktree not found: {id}\"),\n        },\n        (None, None) => anyhow::bail!(\"either worktreePath or idOrPath must be set\"),\n    };\n    let worktree_path = Path::new(&resolved);\n\n    tracing::info!(\n        target: WORKTREE_LOG,\n        path = %resolved,\n        force = req.force,\n        dry_run = req.dry_run,\n        \"REMOVE_START: removing worktree\"\n    );\n","sourceCodeStart":1311,"sourceCodeEnd":1347,"githubUrl":"https://github.com/xai-org/grok-build/blob/bc7f02eddd3d84085849dc19ed216f11c23b0571/crates/codegen/xai-grok-workspace/src/worktree/mod.rs#L1311-L1347","documentation":"remove_worktree requires the caller to identify the target worktree in exactly one way: either an explicit worktree_path or an id_or_path that gets resolved to a path. This error is thrown from an exclusivity check when both fields of RemoveWorktreeRequest are populated, because the request is ambiguous — the API refuses to guess which identifier is authoritative.","triggerScenarios":"Calling remove_worktree (or the remove-worktree command backed by it) with a RemoveWorktreeRequest where both req.worktree_path = Some(...) and req.id_or_path = Some(...) are set. Typically caused by a client that fills all optional fields, or by a wrapper layer that adds id_or_path on top of an already path-based request.","commonSituations":"CLI tools or HTTP clients that serialize the whole request struct without omitting unset fields; scripts that copy an example setting both fields; a middle-layer that auto-injects id_or_path while the caller also passes a path.","solutions":["Set only one of worktree_path or id_or_path to Some and clear the other before calling remove_worktree","If you already know the absolute path, drop id_or_path and use worktree_path directly","If you only have an id or short path, drop worktree_path and let resolve_worktree_by_id_or_path resolve it","Fix the caller/serializer to omit None/default fields so both never get populated together"],"exampleFix":"// before\nlet req = RemoveWorktreeRequest { worktree_path: Some(path.clone()), id_or_path: Some(id) };\n// after\nlet req = RemoveWorktreeRequest { worktree_path: Some(path), id_or_path: None };","handlingStrategy":"validation","validationCode":"fn validate_remove(req: &RemoveWorktreeRequest) -> Result<()> {\n    if req.worktree_path.is_some() && req.id_or_path.is_some() {\n        anyhow::bail!(\"set only one of worktree_path or id_or_path\");\n    }\n    if req.worktree_path.is_none() && req.id_or_path.is_none() {\n        anyhow::bail!(\"worktree_path or id_or_path is required\");\n    }\n    Ok(())\n}","typeGuard":"fn has_exactly_one_target(req: &RemoveWorktreeRequest) -> bool {\n    req.worktree_path.is_some() ^ req.id_or_path.is_some()\n}","tryCatchPattern":null,"preventionTips":["Construct requests via a helper that takes an enum (Path(PathBuf) | Id(String)) instead of two Option fields","Never blanket-serialize optional fields; use skip_serializing_if = \"Option::is_none\"","Unit-test request builders to assert exactly one identifier is set"],"tags":["validation","api-misuse","rust"],"backgroundTag":"mutually-exclusive-parameters","analyzedSha":"bc7f02eddd3d84085849dc19ed216f11c23b0571","analyzedAt":"2026-08-31T04:59:42.031Z","schemaVersion":2},"datasetVersion":"2026-08-31T09:17:48.483Z"}