{"record":{"id":"74f2bdb623a617fb","repo":"FuelLabs/sway","slug":"failed-to-find-path-root-path-dependency","errorCode":null,"errorMessage":"Failed to find path root: `path` dependency \\\"{}\\\" has no parent","messagePattern":"Failed to find path root: `path` dependency \\\\\"(.+?)\\\\\" has no parent","errorType":"exception","errorClass":"anyhow::Error","httpStatus":null,"severity":"error","filePath":"forc-pkg/src/pkg.rs","lineNumber":1339,"sourceCode":"            \"invalid `path_root` for path dependency package {:?}\",\n            &graph[path_dep].name\n        )\n    }\n    Ok(())\n}\n\n/// Given any node in the graph, find the node that is the path root for that node.\nfn find_path_root(graph: &Graph, mut node: NodeIx) -> Result<NodeIx> {\n    loop {\n        let pkg = &graph[node];\n        match pkg.source {\n            source::Pinned::Path(ref src) => {\n                let parent = graph\n                    .edges_directed(node, Direction::Incoming)\n                    .next()\n                    .map(|edge| edge.source())\n                    .ok_or_else(|| {\n                        anyhow!(\n                            \"Failed to find path root: `path` dependency \\\"{}\\\" has no parent\",\n                            src\n                        )\n                    })?;\n                node = parent;\n            }\n            source::Pinned::Git(_)\n            | source::Pinned::Ipfs(_)\n            | source::Pinned::Member(_)\n            | source::Pinned::Registry(_) => {\n                return Ok(node);\n            }\n        }\n    }\n}\n\n/// Given an empty or partially completed `graph`, complete the graph.\n///","sourceCodeStart":1321,"sourceCodeEnd":1357,"githubUrl":"https://github.com/FuelLabs/sway/blob/47e5e902faa42baf652dd6a0c88cd23390c1a614/forc-pkg/src/pkg.rs#L1321-L1357","documentation":"find_path_root walks incoming edges upward from a node whose pinned source is Path; the loop assumes every path-sourced node has a parent (something depends on it). If a path-pinned node has no incoming edges, the walk cannot find a filesystem root and this error fires - a path dependency exists as a graph root, which is structurally invalid.","triggerScenarios":"A lock/graph where a Path-pinned package is a root node - e.g. Forc.lock hand-edited to pin the project itself as Path, or graph pruning removed a parent edge while leaving the child; typically not producible from well-formed manifests.","commonSituations":"Manually edited Forc.lock; artifacts of stale locks after removing dependents; forc-pkg regressions.","solutions":["Delete Forc.lock and rebuild so paths are re-derived from the manifests.","Avoid editing Forc.lock by hand - change dependencies in Forc.toml and let forc regenerate.","If it recurs from a clean state, report to FuelLabs/sway with the manifests and lock."],"exampleFix":"# before\nforc build   # Failed to find path root: `path` dependency \"../lib\" has no parent\n\n# after\nrm Forc.lock && forc build","handlingStrategy":"try-catch","validationCode":"// every Path-pinned node must have at least one dependent (incoming edge)\nfor ix in graph.node_indices() {\n    if let forc_pkg::source::Pinned::Path(_) = graph[ix].source {\n        if graph.edges_directed(ix, petgraph::Direction::Incoming).next().is_none() {\n            // invalid structure: regenerate Forc.lock before building\n        }\n    }\n}","typeGuard":null,"tryCatchPattern":"match build_plan_result {\n    Ok(plan) => { /* ... */ }\n    Err(e) if e.to_string().contains(\"Failed to find path root\") => {\n        let _ = std::fs::remove_file(&lock_path);\n        // regenerate once; if it reproduces from a clean lock, report upstream\n    }\n    Err(e) => return Err(e),\n}","preventionTips":["Never pin or reorder path entries by editing Forc.lock manually.","After deleting a dependent package, regenerate the lock so orphaned path nodes are pruned."],"tags":["graph","path","dependencies","lock-file"],"backgroundTag":null,"analyzedSha":"47e5e902faa42baf652dd6a0c88cd23390c1a614","analyzedAt":"2026-08-16T07:57:45.555Z","schemaVersion":2},"datasetVersion":"2026-08-16T08:17:34.114Z"}