{"record":{"id":"8d97e45063271435","repo":"withastro/astro","slug":"invalidfrontmatterinjectionerror","errorCode":"InvalidFrontmatterInjectionError","errorMessage":"A remark or rehype plugin attempted to inject invalid frontmatter. Ensure \"astro.frontmatter\" is set to a valid JSON object that is not `null` or `undefined`.","messagePattern":"A remark or rehype plugin attempted to inject invalid frontmatter\\. Ensure \"astro\\.frontmatter\" is set to a valid JSON object that is not `null` or `undefined`\\.","errorType":"exception","errorClass":"AstroError","httpStatus":null,"severity":"error","filePath":"packages/astro/src/vite-plugin-markdown/index.ts","lineNumber":98,"sourceCode":"\t\t\t\tif (!renderer) {\n\t\t\t\t\tconst { markdown: md, image } = settings.config;\n\t\t\t\t\trenderer = md.processor.createRenderer({\n\t\t\t\t\t\timage,\n\t\t\t\t\t\tsyntaxHighlight: md.syntaxHighlight,\n\t\t\t\t\t\tshikiConfig: md.shikiConfig,\n\t\t\t\t\t\tgfm: md.gfm,\n\t\t\t\t\t\tsmartypants: md.smartypants,\n\t\t\t\t\t});\n\t\t\t\t}\n\n\t\t\t\tconst renderResult = await (await renderer).render(raw.content, {\n\t\t\t\t\tfileURL,\n\t\t\t\t\tfrontmatter: raw.frontmatter,\n\t\t\t\t});\n\n\t\t\t\t// Improve error message for invalid astro frontmatter\n\t\t\t\tif (!isFrontmatterValid(renderResult.metadata.frontmatter)) {\n\t\t\t\t\tthrow new AstroError(AstroErrorData.InvalidFrontmatterInjectionError);\n\t\t\t\t}\n\n\t\t\t\tlet html = renderResult.code;\n\t\t\t\tconst {\n\t\t\t\t\theadings,\n\t\t\t\t\tlocalImagePaths: rawLocalImagePaths,\n\t\t\t\t\tremoteImagePaths,\n\t\t\t\t\tfrontmatter,\n\t\t\t\t} = renderResult.metadata;\n\n\t\t\t\t// Add default charset for markdown pages\n\t\t\t\tconst isMarkdownPage = isPage(fileURL, settings);\n\t\t\t\tconst charset = isMarkdownPage ? '<meta charset=\"utf-8\">' : '';\n\n\t\t\t\t// Resolve all the extracted images from the content\n\t\t\t\tconst localImagePaths: MarkdownImagePath[] = [];\n\t\t\t\tfor (const imagePath of rawLocalImagePaths) {\n\t\t\t\t\tlocalImagePaths.push({","sourceCodeStart":80,"sourceCodeEnd":116,"githubUrl":"https://github.com/withastro/astro/blob/d081033d5fe8e8a68c4bbbad4af9d2deb9c74bca/packages/astro/src/vite-plugin-markdown/index.ts#L80-L116","documentation":"Thrown (code `InvalidFrontmatterInjectionError`) after Markdown rendering when a remark or rehype plugin has set `astro.frontmatter` on the file data to something that is not a valid JSON-serializable object — i.e. null or undefined. The plugin validates `renderResult.metadata.frontmatter` with `isFrontmatterValid` before continuing; injected frontmatter must be a plain object.","triggerScenarios":"A custom remark/rehype plugin assigns `file.data.astro.frontmatter = null`, `= undefined`, `= 'string'`, or deletes the key during Markdown processing. Astro's Markdown renderer collects that injected data and the post-render check fails.","commonSituations":"Writing a remark plugin that conditionally sets frontmatter and forgets to initialize the object. A plugin mutating `file.data.astro.frontmatter` to a non-object. Combining community remark plugins that conflict over frontmatter injection.","solutions":["Ensure your remark/rehype plugin sets frontmatter to a plain object: `file.data.astro.frontmatter = { ...existing, myKey: 'value' }`.","Never assign null/undefined; if you have nothing to inject, leave the key unset or assign `{}`.","Spread the existing frontmatter to avoid clobbering other plugins' injections."],"exampleFix":"// before — remark plugin\nexport function myRemark() {\n  return (tree, file) => {\n    file.data.astro.frontmatter = null;\n  };\n}\n\n// after\nexport function myRemark() {\n  return (tree, file) => {\n    file.data.astro.frontmatter = { ...(file.data.astro.frontmatter || {}), myKey: 'value' };\n  };\n}","handlingStrategy":"validation","validationCode":"function isFrontmatterValid(fm) {\n  return fm !== null && fm !== undefined && typeof fm === 'object' && !Array.isArray(fm);\n}","typeGuard":"function isValidFrontmatter(fm): fm is Record<string, unknown> {\n  return typeof fm === 'object' && fm !== null && !Array.isArray(fm);\n}","tryCatchPattern":null,"preventionTips":["In remark/rehype plugins, always spread existing frontmatter: { ...file.data.astro.frontmatter, ... }.","Never assign null/undefined to astro.frontmatter.","Test your remark plugin against a sample Markdown file before wiring it into the Astro config."],"tags":["markdown","remark","rehype","frontmatter","plugins"],"backgroundTag":null,"analyzedSha":"d081033d5fe8e8a68c4bbbad4af9d2deb9c74bca","analyzedAt":"2026-08-12T13:37:29.035Z","schemaVersion":2},"datasetVersion":"2026-08-12T18:17:37.767Z"}