garrytan/gstack · error · Error
pdf: --from-file ${payloadPath} is not valid JSON (${msg}).
Error message
pdf: --from-file ${payloadPath} is not valid JSON (${msg}). What it means
Thrown by parsePdfFromFile() when JSON.parse(raw) fails on the file contents. The error message includes the underlying parse error for diagnosis. The file passed path validation and was read successfully, but its content is not syntactically valid JSON.
Source
Thrown at browse/src/meta-commands.ts:158
export function parsePdfFromFile(payloadPath: string): ParsedPdfArgs {
// Parity with load-html --from-file (browse/src/write-commands.ts) and
// the direct load-html <file> path: every caller-supplied file path
// must pass validateReadPath so the safe-dirs policy can't be skirted
// by routing reads through the --from-file shortcut.
try {
validateReadPath(path.resolve(payloadPath));
} catch {
throw new Error(
`pdf: --from-file ${payloadPath} must be under ${SAFE_DIRECTORIES.join(' or ')} (security policy). Copy the payload into the project tree or /tmp first.`
);
}
const raw = fs.readFileSync(payloadPath, 'utf8');
let json: any;
try {
json = JSON.parse(raw);
} catch (err) {
const msg = err instanceof Error ? err.message : String(err);
throw new Error(`pdf: --from-file ${payloadPath} is not valid JSON (${msg}).`);
}
if (json === null || typeof json !== 'object' || Array.isArray(json)) {
throw new Error(`pdf: --from-file ${payloadPath} must be a JSON object, got ${Array.isArray(json) ? 'array' : typeof json}.`);
}
const out: ParsedPdfArgs = {
output: json.output || `${TEMP_DIR}/browse-page.pdf`,
format: json.format,
width: json.width,
height: json.height,
marginTop: json.marginTop,
marginRight: json.marginRight,
marginBottom: json.marginBottom,
marginLeft: json.marginLeft,
headerTemplate: json.headerTemplate,
footerTemplate: json.footerTemplate,
pageNumbers: json.pageNumbers === true,
tagged: json.tagged === true,
outline: json.outline === true,View on GitHub (pinned to 94993f7401)
Solutions
- Validate the JSON file with a linter or 'jq .' before passing it
- Remove trailing commas, comments, and ensure all keys and string values use double quotes
- Check for empty or truncated files — ensure the write completed
Example fix
// before — pdf-config.json (invalid)
{
"format": "A4",
"printBackground": true, // trailing comma + comment
}
// after — valid JSON
{
"format": "A4",
"printBackground": true
} Defensive patterns
Strategy: validation
Validate before calling
// Validate JSON before passing the file
const raw = fs.readFileSync(payloadPath, 'utf8');
try {
JSON.parse(raw);
} catch (e) {
throw new Error(`Payload is not valid JSON: ${e.message}`);
} Try / catch
try {
const parsed = parsePdfFromFile(payloadPath);
} catch (e) {
if (e.message.includes('not valid JSON')) {
console.error('Fix JSON syntax in', payloadPath);
}
} Prevention
- Lint JSON files with 'jq .' or a JSON validator before using them as --from-file payloads
- Avoid trailing commas, comments, and single quotes in JSON config files
- Ensure file writes complete fully before referencing them
When it happens
Trigger: Pointing --from-file at a file that exists and is readable but contains malformed JSON — syntax errors, trailing commas, unquoted keys, single quotes, comments, or empty file.
Common situations: Hand-written JSON with trailing commas or comments (which are invalid in standard JSON), empty file, file saved with a BOM, or file partially written/corrupted.
Related errors
- pdf: --from-file ${payloadPath} must be a JSON object, got $
- excalidraw scene has no elements array
- Skill name is empty.
- Invalid skill name "${name}". Must be lowercase letters/digi
- stageSkill: files map is empty.
AI-assisted analysis of garrytan/gstack@94993f7401 (2026-08-12).
Data as JSON: /api/errors/65436d4f0d7af066.
Report an issue: GitHub.