diff --git a/.changeset/chilly-stingrays-play.md b/.changeset/chilly-stingrays-play.md new file mode 100644 index 0000000000..623425157e --- /dev/null +++ b/.changeset/chilly-stingrays-play.md @@ -0,0 +1,6 @@ +--- +'astro': minor +'@astrojs/mdx': patch +--- + +Update Markdown type signature to match new markdown plugin,and update top-level layout props for better alignment diff --git a/packages/astro/src/@types/astro.ts b/packages/astro/src/@types/astro.ts index 458fa0fe06..64b2462388 100644 --- a/packages/astro/src/@types/astro.ts +++ b/packages/astro/src/@types/astro.ts @@ -884,32 +884,29 @@ export interface AstroInstance { export interface MarkdownInstance> { frontmatter: T; + /** Absolute file path (e.g. `/home/user/projects/.../file.md`) */ file: string; + /** Browser URL for files under `/src/pages` (e.g. `/en/guides/markdown-content`) */ url: string | undefined; + /** Component to render content in `.astro` files. Usage: `` */ Content: AstroComponentFactory; - /** raw Markdown file content, excluding frontmatter */ + /** raw Markdown file content, excluding layout HTML and YAML frontmatter */ rawContent(): string; - /** Markdown file compiled to valid Astro syntax. Queryable with most HTML parsing libraries */ - compiledContent(): Promise; - getHeadings(): Promise; + /** Markdown file compiled to HTML, excluding layout HTML */ + compiledContent(): string; + /** List of headings (h1 -> h6) with associated metadata */ + getHeadings(): MarkdownHeading[]; /** @deprecated Renamed to `getHeadings()` */ getHeaders(): void; - default: () => Promise<{ - metadata: MarkdownMetadata; - frontmatter: MarkdownContent; - $$metadata: Metadata; - default: AstroComponentFactory; - }>; + default: AstroComponentFactory; } export interface MDXInstance - extends Omit, 'rawContent' | 'compiledContent' | 'Content' | 'default'> { + extends Omit, 'rawContent' | 'compiledContent'> { /** MDX does not support rawContent! If you need to read the Markdown contents to calculate values (ex. reading time), we suggest injecting frontmatter via remark plugins. Learn more on our docs: https://docs.astro.build/en/guides/integrations-guide/mdx/#inject-frontmatter-via-remark-or-rehype-plugins */ rawContent: never; /** MDX does not support compiledContent! If you need to read the HTML contents to calculate values (ex. reading time), we suggest injecting frontmatter via rehype plugins. Learn more on our docs: https://docs.astro.build/en/guides/integrations-guide/mdx/#inject-frontmatter-via-remark-or-rehype-plugins */ compiledContent: never; - default: AstroComponentFactory; - Content: AstroComponentFactory; } export interface MarkdownLayoutProps> { @@ -917,6 +914,8 @@ export interface MarkdownLayoutProps> { file: MarkdownInstance['file']; url: MarkdownInstance['url']; } & T; + file: MarkdownInstance['file']; + url: MarkdownInstance['url']; headings: MarkdownHeading[]; rawContent: MarkdownInstance['rawContent']; compiledContent: MarkdownInstance['compiledContent']; diff --git a/packages/astro/src/vite-plugin-markdown/index.ts b/packages/astro/src/vite-plugin-markdown/index.ts index acaefed24f..6d6c1dd4b4 100644 --- a/packages/astro/src/vite-plugin-markdown/index.ts +++ b/packages/astro/src/vite-plugin-markdown/index.ts @@ -106,6 +106,8 @@ export default function markdown({ config, logging }: AstroPluginOptions): Plugi return ${ layout ? `h(Layout, { + file, + url, content, frontmatter: content, headings: getHeadings(), diff --git a/packages/astro/test/astro-markdown.test.js b/packages/astro/test/astro-markdown.test.js index 0f08333655..59eb07822d 100644 --- a/packages/astro/test/astro-markdown.test.js +++ b/packages/astro/test/astro-markdown.test.js @@ -118,6 +118,24 @@ describe('Astro Markdown', () => { expect(headingSlugs).to.contain('section-2'); }); + it('passes "file" and "url" to layout', async () => { + const html = await fixture.readFile('/with-layout/index.html'); + const $ = cheerio.load(html); + + const frontmatterFile = $('[data-frontmatter-file]')?.text(); + const frontmatterUrl = $('[data-frontmatter-url]')?.text(); + const file = $('[data-file]')?.text(); + const url = $('[data-url]')?.text(); + + expect(frontmatterFile?.endsWith('with-layout.md')).to.equal( + true, + '"file" prop does not end with correct path or is undefined' + ); + expect(frontmatterUrl).to.equal('/with-layout'); + expect(file).to.equal(frontmatterFile); + expect(url).to.equal(frontmatterUrl); + }); + describe('Vite env vars (#3412)', () => { it('Allows referencing import.meta.env in content', async () => { const html = await fixture.readFile('/vite-env-vars/index.html'); diff --git a/packages/astro/test/fixtures/astro-markdown/src/layouts/Base.astro b/packages/astro/test/fixtures/astro-markdown/src/layouts/Base.astro index 64817bad9e..70de435d25 100644 --- a/packages/astro/test/fixtures/astro-markdown/src/layouts/Base.astro +++ b/packages/astro/test/fixtures/astro-markdown/src/layouts/Base.astro @@ -1,7 +1,13 @@ --- const { content = { title: "content didn't work" }, - frontmatter = { title: "frontmatter didn't work" }, + file = "file didn't work", + url = "url didn't work", + frontmatter = { + title: "frontmatter didn't work", + file: "file didn't work", + url: "url didn't work", + }, headings = [], compiledContent = () => '', rawContent = () => '', @@ -21,6 +27,10 @@ const {

{content.title}

{frontmatter.title}

{compiledContent()}

+

{frontmatter.file}

+

{frontmatter.url}

+

{frontmatter.file}

+

{frontmatter.url}

{rawContent()}

Layout rendered!

    diff --git a/packages/integrations/mdx/src/astro-data-utils.ts b/packages/integrations/mdx/src/astro-data-utils.ts index 6bd2186e27..9be96022e8 100644 --- a/packages/integrations/mdx/src/astro-data-utils.ts +++ b/packages/integrations/mdx/src/astro-data-utils.ts @@ -51,6 +51,8 @@ export function rehypeApplyFrontmatterExport(pageFrontmatter: Record{frontmatter.title}

    {frontmatter.file}

    {frontmatter.url}

    +

    {frontmatter.file}

    +

    {frontmatter.url}

    Layout rendered!

      {headings.map(heading =>
    • {heading.slug}
    • )} diff --git a/packages/integrations/mdx/test/mdx-frontmatter.test.js b/packages/integrations/mdx/test/mdx-frontmatter.test.js index 039a12ddcc..539fdbf996 100644 --- a/packages/integrations/mdx/test/mdx-frontmatter.test.js +++ b/packages/integrations/mdx/test/mdx-frontmatter.test.js @@ -57,17 +57,21 @@ describe('MDX frontmatter', () => { expect(headingSlugs).to.contain('section-2'); }); - it('passes "file" and "url" to layout via frontmatter', async () => { + it('passes "file" and "url" to layout', async () => { const html = await fixture.readFile('/with-headings/index.html'); const { document } = parseHTML(html); const frontmatterFile = document.querySelector('[data-frontmatter-file]')?.textContent; const frontmatterUrl = document.querySelector('[data-frontmatter-url]')?.textContent; + const file = document.querySelector('[data-file]')?.textContent; + const url = document.querySelector('[data-url]')?.textContent; expect(frontmatterFile?.endsWith('with-headings.mdx')).to.equal( true, '"file" prop does not end with correct path or is undefined' ); expect(frontmatterUrl).to.equal('/with-headings'); + expect(file).to.equal(frontmatterFile); + expect(url).to.equal(frontmatterUrl); }); });