{"record":{"id":"2a504d25edcdcbbe","repo":"can1357/oh-my-pi","slug":"export-requires-output-path","errorCode":null,"errorMessage":"export requires --output <path>","messagePattern":"export requires --output <path>","errorType":"exception","errorClass":null,"httpStatus":null,"severity":"info","filePath":"packages/coding-agent/src/slash-commands/helpers/security.ts","lineNumber":191,"sourceCode":"\nasync function exportResults(runtime: SlashCommandRuntime, rest: string): Promise<void> {\n\tconst tokens = parseCommandArgs(rest);\n\tconst scanId = tokens[0];\n\tif (!scanId) throw new Error(\"export requires <scan-id> --output <path> [--format bundle|sarif|report]\");\n\tlet outputPath: string | undefined;\n\tlet format: \"bundle\" | \"sarif\" | \"report\" = \"bundle\";\n\tfor (let index = 1; index < tokens.length; index++) {\n\t\tconst token = tokens[index]!;\n\t\tif (token === \"--output\") outputPath = requireToken(tokens, ++index, token);\n\t\telse if (token === \"--format\") {\n\t\t\tconst value = requireToken(tokens, ++index, token);\n\t\t\tif (value !== \"bundle\" && value !== \"sarif\" && value !== \"report\") {\n\t\t\t\tthrow new Error(`Unknown export format: ${value}`);\n\t\t\t}\n\t\t\tformat = value;\n\t\t} else throw new Error(`Unknown export option: ${token}`);\n\t}\n\tif (!outputPath) throw new Error(\"export requires --output <path>\");\n\tconst store = await SecurityStore.openForCwd(runtime.cwd);\n\tconst bundle = await store.getBundle(scanIdFromInput(scanId));\n\tif (!bundle) throw new Error(`Unknown security scan: ${scanId}`);\n\tlet content: string;\n\tif (format === \"sarif\") {\n\t\tif (!bundle.sarif) throw new Error(`Security scan ${scanId} has no SARIF result`);\n\t\tcontent = `${JSON.stringify(bundle.sarif, null, 2)}\\n`;\n\t} else if (format === \"report\") {\n\t\tif (bundle.report === undefined) throw new Error(`Security scan ${scanId} has no report`);\n\t\tcontent = bundle.report;\n\t} else {\n\t\tcontent = `${JSON.stringify(bundle, null, 2)}\\n`;\n\t}\n\tconst absolute = path.resolve(runtime.cwd, outputPath);\n\tawait writeSecurityFileAtomic(absolute, content, { hardenParent: false });\n\tawait runtime.output(`Exported security scan ${scanId} to ${shortenPath(absolute)}.`);\n}\n","sourceCodeStart":173,"sourceCodeEnd":209,"githubUrl":"https://github.com/can1357/oh-my-pi/blob/969062200754ea02cfac922e5ebb8c608c079e15/packages/coding-agent/src/slash-commands/helpers/security.ts#L173-L209","documentation":"Even with a valid scan id and format, /security export needs a destination path via --output. exportResults() throws this error after option parsing when outputPath is still undefined. Without it the command would have nowhere to write the serialized bundle.","triggerScenarios":"Running /security export <scan-id> with no --output flag; passing --format but forgetting --output; an automation strips the --output pair because of a quoting bug leaving the value consumed elsewhere.","commonSituations":"Developer expects output to stdout or a default filename (export always writes to an explicit path); a wrapper script drops arguments containing spaces that were not quoted; the user combined subcommand syntax from memory.","solutions":["Add --output <path>: /security export <scan-id> --output ./export.json","Quote paths containing spaces: --output \"./my exports/bundle.json\"","The path is resolved against runtime.cwd if relative"],"exampleFix":"// before\n/security export scan-abc --format report\n// after\n/security export scan-abc --format report --output ./report.md","handlingStrategy":"validation","validationCode":"function validateExportHasOutput(rest: string): boolean {\n  const tokens = rest.trim().split(/\\s+/).filter(Boolean);\n  const i = tokens.indexOf(\"--output\");\n  return i !== -1 && typeof tokens[i + 1] === \"string\";\n}\n// require true before invoking /security export","typeGuard":null,"tryCatchPattern":"try {\n  await runSlashCommand(`/security export ${scanId} ${args}`);\n} catch (err) {\n  if (err instanceof Error && err.message === \"export requires --output <path>\") {\n    // re-issue with an explicit --output path\n  } else throw err;\n}","preventionTips":["Always include --output <path>; export never writes to stdout or a default filename","Quote destination paths containing spaces so the value survives tokenization","Resolve relative paths against the session cwd mentally — path.resolve(runtime.cwd, outputPath) is applied"],"tags":["cli","argument-validation","slash-command","usage-error"],"backgroundTag":"missing-required-argument","analyzedSha":"969062200754ea02cfac922e5ebb8c608c079e15","analyzedAt":"2026-08-31T10:29:35.737Z","schemaVersion":2},"datasetVersion":"2026-08-31T14:17:45.589Z"}