{"record":{"id":"fc18091b976716ee","repo":"alibaba/open-code-review","slug":"resolve-repository-path-q-w-fc1809","errorCode":null,"errorMessage":"resolve repository path %q: %w","messagePattern":"resolve repository path %q: %w","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"error","filePath":"internal/tool/filereader.go","lineNumber":97,"sourceCode":"\t}\n}\n\nfunc (fr *FileReader) readFromDisk(path string) (string, error) {\n\tfullPath, err := fr.resolveWorkspacePath(path)\n\tif err != nil {\n\t\treturn \"\", err\n\t}\n\tcontent, err := os.ReadFile(fullPath)\n\tif err != nil {\n\t\treturn \"\", fmt.Errorf(\"read file %q: %w\", path, err)\n\t}\n\treturn string(content), nil\n}\n\nfunc (fr *FileReader) resolveWorkspacePath(path string) (string, error) {\n\trepoRoot, err := pathutil.CanonicalPath(fr.RepoDir)\n\tif err != nil {\n\t\treturn \"\", fmt.Errorf(\"resolve repository path %q: %w\", fr.RepoDir, err)\n\t}\n\n\tfullPath := filepath.Join(repoRoot, path)\n\tif !pathutil.WithinBase(repoRoot, fullPath) {\n\t\treturn \"\", fmt.Errorf(\"file path %q is outside repository\", path)\n\t}\n\n\tresolvedPath, err := filepath.EvalSymlinks(fullPath)\n\tif err != nil {\n\t\tif os.IsNotExist(err) {\n\t\t\treturn fullPath, nil\n\t\t}\n\t\treturn \"\", fmt.Errorf(\"resolve file %q: %w\", path, err)\n\t}\n\tif !pathutil.WithinBase(repoRoot, resolvedPath) {\n\t\treturn \"\", fmt.Errorf(\"file path %q is outside repository\", path)\n\t}\n\treturn resolvedPath, nil","sourceCodeStart":79,"sourceCodeEnd":115,"githubUrl":"https://github.com/alibaba/open-code-review/blob/5cf97d0d15cbd41b602513c4be3bfec3cee5bf7f/internal/tool/filereader.go#L79-L115","documentation":"Error from FileReader.resolveWorkspacePath when pathutil.CanonicalPath fails on fr.RepoDir — the repository root itself cannot be canonicalized (e.g. it does not exist or a path component is not resolvable). No file-specific validation happens; this is a configuration-level failure of the FileReader's RepoDir setting.","triggerScenarios":"Constructing FileReader with a RepoDir that is a non-existent path, a broken symlink, or otherwise uncanonicalizable, then calling Read/ReadLines in workspace mode so readFromDisk/readLinesFromDisk invoke resolveWorkspacePath.","commonSituations":"Running the CLI outside a git repository or with a bad --repo flag; RepoDir pointing to a deleted temp directory; renamed/moved project root; wrong working directory when RepoDir defaults to cwd.","solutions":["Verify RepoDir points to an existing directory (ls <RepoDir>) and correct the value.","Run the tool from inside the repository if RepoDir is derived from the working directory.","Recreate the missing directory or fix the broken symlink that RepoDir points through."],"exampleFix":"// before\nfr := &tool.FileReader{RepoDir: \"/tmp/stale-worktree\"}\n// after\nfr := &tool.FileReader{RepoDir: \"/home/dev/project\"} // existing repo root","handlingStrategy":"validation","validationCode":"info, err := os.Stat(repoDir)\nif err != nil { return fmt.Errorf(\"repo dir %q: %w\", repoDir, err) }\nif !info.IsDir() { return fmt.Errorf(\"%q is not a directory\", repoDir) }\nif _, err := filepath.EvalSymlinks(repoDir); err != nil { return fmt.Errorf(\"cannot resolve %q: %w\", repoDir, err) }","typeGuard":"func validRepoDir(dir string) bool { info, err := os.Stat(dir); return err == nil && info.IsDir() }","tryCatchPattern":"content, err := fr.Read(ctx, rel)\nif err != nil && strings.Contains(err.Error(), \"resolve repository path\") {\n    return nil, fmt.Errorf(\"FileReader misconfigured: set RepoDir to an existing directory: %w\", err)\n}","preventionTips":["Set RepoDir from an absolute, verified path (filepath.Abs + os.Stat) at startup.","Prefer resolving RepoDir via git rev-parse --show-toplevel rather than cwd assumptions.","Fail fast with a clear message if RepoDir does not exist, instead of letting reads fail later."],"tags":["configuration","path-resolution","workspace","file-io"],"backgroundTag":"invalid-repository-path","analyzedSha":"5cf97d0d15cbd41b602513c4be3bfec3cee5bf7f","analyzedAt":"2026-09-02T02:08:09.116Z","contentChangedAt":null,"schemaVersion":2},"datasetVersion":"2026-09-08T10:18:20.063Z"}