{"record":{"id":"20178e2614bae5d1","repo":"can1357/oh-my-pi","slug":"path-entry-entry-only-line-range-selectors","errorCode":null,"errorMessage":"path entry \"${entry}\" — only line-range selectors like \":50-100\" are supported (no \":raw\"/\":conflicts\")","messagePattern":"path entry \"(.+?)\" — only line-range selectors like \":50-100\" are supported \\(no \":raw\"/\":conflicts\"\\)","errorType":"validation","errorClass":"ToolError","httpStatus":null,"severity":"error","filePath":"packages/coding-agent/src/tools/grep.ts","lineNumber":189,"sourceCode":"\t\t\tif (!isReadSelectorGrammar(internalSplit.sel)) {\n\t\t\t\tthrow new ToolError(\n\t\t\t\t\t`path entry \"${entry}\" has an invalid selector \":${internalSplit.sel}\" — use \":N-M\" line ranges, \":raw\"/\":conflicts\", a range plus \":raw\", or percent-encode a literal \":\" as %3A`,\n\t\t\t\t);\n\t\t\t}\n\t\t\tspecs.push({ original: entry, clean: internalSplit.path, ranges: selectorLineRanges(internalSplit.sel) });\n\t\t\tcontinue;\n\t\t}\n\t\t// Prefer a literal filesystem match when one exists — a real file named\n\t\t// `test:1-2` outranks the `:1-2` selector interpretation (issue #4618).\n\t\tconst strictSplit = splitPathAndSel(entry);\n\t\tconst split = await splitPathAndSelPreferringLiteral(entry, cwd);\n\t\tconst literalFilesystemMatch = strictSplit.sel !== undefined && split.sel === undefined;\n\t\tlet clean = literalFilesystemMatch ? resolveReadPath(entry, cwd) : entry;\n\t\tlet ranges: [LineRange, ...LineRange[]] | undefined;\n\t\tif (!literalFilesystemMatch && split.sel) {\n\t\t\tconst parsed = parseLineRanges(split.sel);\n\t\t\tif (!parsed) {\n\t\t\t\tthrow new ToolError(\n\t\t\t\t\t`path entry \"${entry}\" — only line-range selectors like \":50-100\" are supported (no \":raw\"/\":conflicts\")`,\n\t\t\t\t);\n\t\t\t}\n\t\t\tif (hasGlobPathChars(split.path)) {\n\t\t\t\tthrow new ToolError(`Line-range selector requires a single file, not a glob: ${entry}`);\n\t\t\t}\n\t\t\tclean = split.path;\n\t\t\tranges = parsed;\n\t\t}\n\t\tspecs.push({\n\t\t\toriginal: entry,\n\t\t\tclean,\n\t\t\tliteralFilesystemMatch,\n\t\t\tranges,\n\t\t});\n\t}\n\treturn specs;\n}","sourceCodeStart":171,"sourceCodeEnd":207,"githubUrl":"https://github.com/can1357/oh-my-pi/blob/969062200754ea02cfac922e5ebb8c608c079e15/packages/coding-agent/src/tools/grep.ts#L171-L207","documentation":"In the non-internal-URL branch, parsePathSpecs parses the ':sel' suffix with parseLineRanges; grep only supports line-range selectors, so ':raw' or ':conflicts' (read-only selectors) fail to parse and are rejected with this error.","triggerScenarios":"Path entries like 'file.ts:raw' or 'file.ts:conflicts' passed to grep; entry resolves as a literal filesystem match (strictSplit found a selector the normal split did not) and the selector is not a line range.","commonSituations":"Reusing read-tool arguments for grep; assuming grep supports raw/conflict chunk selectors like the read tool.","solutions":["Remove ':raw'/':conflicts' from the path entry and pass only a plain path or ':N-M' ranges","Use the read tool if you need :raw/:conflicts selectors","Search the whole file with grep and read specific chunks separately"],"exampleFix":"// before\nawait grepTool.execute({ pattern: \"foo\", path: \"src/app.ts:raw\" })\n// after\nawait grepTool.execute({ pattern: \"foo\", path: \"src/app.ts\" })","handlingStrategy":"validation","validationCode":"function stripReadOnlySelectors(entry: string): string {\n  return entry.replace(/:(raw|conflicts)$/i, \"\");\n}\nawait grepTool.execute({ pattern, path: entries.map(stripReadOnlySelectors) });","typeGuard":"function hasReadOnlySelector(entry: string): boolean {\n  return /:(raw|conflicts)(:\\d+-\\d+)?$/.test(entry);\n}","tryCatchPattern":"try {\n  return await grepTool.execute({ pattern, path: entries });\n} catch (err) {\n  if (err instanceof ToolError && err.message.includes(\":raw\\\"/\\\":conflicts\")) {\n    return await grepTool.execute({ pattern, path: entries.map(e => e.split(\":\")[0]) });\n  }\n  throw err;\n}","preventionTips":["Do not share path-spec strings between the read tool and grep tool","Strip :raw/:conflicts before calling grep","Use the read tool for chunk-selector semantics"],"tags":["parsing","selector-syntax","grep-tool"],"backgroundTag":"invalid-path-selector","analyzedSha":"969062200754ea02cfac922e5ebb8c608c079e15","analyzedAt":"2026-08-31T10:29:35.737Z","schemaVersion":2},"datasetVersion":"2026-08-31T14:17:45.589Z"}