[MDX] Include url
in glob result (#3981)
* deps: add es-module-lexer * feat: inject url export on mdx files * fix: apply url transform in prod * test: page urls with overrides * fix: revert test skips * chore: changeset * fix: add newline before export
This commit is contained in:
parent
eaf187f2c4
commit
61fec63044
10 changed files with 91 additions and 9 deletions
5
.changeset/shiny-pumpkins-return.md
Normal file
5
.changeset/shiny-pumpkins-return.md
Normal file
|
@ -0,0 +1,5 @@
|
|||
---
|
||||
'@astrojs/mdx': patch
|
||||
---
|
||||
|
||||
Include page url in MDX glob result
|
|
@ -30,7 +30,8 @@
|
|||
"test": "mocha --exit --timeout 20000"
|
||||
},
|
||||
"dependencies": {
|
||||
"@mdx-js/rollup": "^2.1.1"
|
||||
"@mdx-js/rollup": "^2.1.1",
|
||||
"es-module-lexer": "^0.10.5"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@types/chai": "^4.3.1",
|
||||
|
@ -39,8 +40,8 @@
|
|||
"astro": "workspace:*",
|
||||
"astro-scripts": "workspace:*",
|
||||
"chai": "^4.3.6",
|
||||
"mocha": "^9.2.2",
|
||||
"linkedom": "^0.14.12"
|
||||
"linkedom": "^0.14.12",
|
||||
"mocha": "^9.2.2"
|
||||
},
|
||||
"engines": {
|
||||
"node": "^14.18.0 || >=16.12.0"
|
||||
|
|
|
@ -1,11 +1,13 @@
|
|||
import mdxPlugin from '@mdx-js/rollup';
|
||||
import type { AstroIntegration } from 'astro';
|
||||
import mdxPlugin from '@mdx-js/rollup';
|
||||
import { parse as parseESM } from 'es-module-lexer';
|
||||
import { getFileInfo } from './utils.js';
|
||||
|
||||
export default function mdx(): AstroIntegration {
|
||||
return {
|
||||
name: '@astrojs/mdx',
|
||||
hooks: {
|
||||
'astro:config:setup': ({ updateConfig, addPageExtension, command }: any) => {
|
||||
'astro:config:setup': ({ updateConfig, config, addPageExtension, command }: any) => {
|
||||
addPageExtension('.mdx');
|
||||
updateConfig({
|
||||
vite: {
|
||||
|
@ -20,14 +22,23 @@ export default function mdx(): AstroIntegration {
|
|||
mdExtensions: [],
|
||||
}),
|
||||
},
|
||||
command === 'dev' && {
|
||||
{
|
||||
name: '@astrojs/mdx',
|
||||
transform(code: string, id: string) {
|
||||
if (!id.endsWith('.mdx')) return;
|
||||
// TODO: decline HMR updates until we have a stable approach
|
||||
return `${code}\nif (import.meta.hot) {
|
||||
const [, moduleExports] = parseESM(code);
|
||||
|
||||
if (!moduleExports.includes('url')) {
|
||||
const { fileUrl } = getFileInfo(id, config);
|
||||
code += `\nexport const url = ${JSON.stringify(fileUrl)};`;
|
||||
}
|
||||
if (command === 'dev') {
|
||||
// TODO: decline HMR updates until we have a stable approach
|
||||
code += `\nif (import.meta.hot) {
|
||||
import.meta.hot.decline();
|
||||
}`;
|
||||
}`
|
||||
}
|
||||
return code;
|
||||
},
|
||||
},
|
||||
],
|
||||
|
|
21
packages/integrations/mdx/src/utils.ts
Normal file
21
packages/integrations/mdx/src/utils.ts
Normal file
|
@ -0,0 +1,21 @@
|
|||
import type { AstroConfig } from 'astro';
|
||||
|
||||
function appendForwardSlash(path: string) {
|
||||
return path.endsWith('/') ? path : path + '/';
|
||||
}
|
||||
|
||||
/** @see 'vite-plugin-utils' for source */
|
||||
export function getFileInfo(id: string, config: AstroConfig) {
|
||||
const sitePathname = appendForwardSlash(
|
||||
config.site ? new URL(config.base, config.site).pathname : config.base
|
||||
);
|
||||
|
||||
const fileId = id.split('?')[0];
|
||||
let fileUrl = fileId.includes('/pages/')
|
||||
? fileId.replace(/^.*?\/pages\//, sitePathname).replace(/(\/index)?\.mdx$/, '')
|
||||
: undefined;
|
||||
if (fileUrl && config.trailingSlash === 'always') {
|
||||
fileUrl = appendForwardSlash(fileUrl);
|
||||
}
|
||||
return { fileId, fileUrl };
|
||||
}
|
9
packages/integrations/mdx/test/fixtures/mdx-url-export/src/pages/pages.json.js
vendored
Normal file
9
packages/integrations/mdx/test/fixtures/mdx-url-export/src/pages/pages.json.js
vendored
Normal file
|
@ -0,0 +1,9 @@
|
|||
export async function get() {
|
||||
const mdxPages = await import.meta.glob('./*.mdx', { eager: true });
|
||||
|
||||
return {
|
||||
body: JSON.stringify({
|
||||
urls: Object.values(mdxPages ?? {}).map(v => v?.url),
|
||||
})
|
||||
}
|
||||
}
|
1
packages/integrations/mdx/test/fixtures/mdx-url-export/src/pages/test-1.mdx
vendored
Normal file
1
packages/integrations/mdx/test/fixtures/mdx-url-export/src/pages/test-1.mdx
vendored
Normal file
|
@ -0,0 +1 @@
|
|||
# I'm a page with a url of "/test-1!"
|
1
packages/integrations/mdx/test/fixtures/mdx-url-export/src/pages/test-2.mdx
vendored
Normal file
1
packages/integrations/mdx/test/fixtures/mdx-url-export/src/pages/test-2.mdx
vendored
Normal file
|
@ -0,0 +1 @@
|
|||
# I'm a page with a url of "/test-2!"
|
3
packages/integrations/mdx/test/fixtures/mdx-url-export/src/pages/with-url-override.mdx
vendored
Normal file
3
packages/integrations/mdx/test/fixtures/mdx-url-export/src/pages/with-url-override.mdx
vendored
Normal file
|
@ -0,0 +1,3 @@
|
|||
export const url = '/AH!'
|
||||
|
||||
# I'm a test with a url override!
|
28
packages/integrations/mdx/test/mdx-url-export.js
Normal file
28
packages/integrations/mdx/test/mdx-url-export.js
Normal file
|
@ -0,0 +1,28 @@
|
|||
import mdx from '@astrojs/mdx';
|
||||
|
||||
import { expect } from 'chai';
|
||||
import { loadFixture } from '../../../astro/test/test-utils.js';
|
||||
|
||||
describe('MDX url export', () => {
|
||||
let fixture;
|
||||
|
||||
before(async () => {
|
||||
fixture = await loadFixture({
|
||||
root: new URL('./fixtures/mdx-url-export/', import.meta.url),
|
||||
integrations: [mdx()],
|
||||
});
|
||||
|
||||
await fixture.build();
|
||||
});
|
||||
|
||||
it('generates correct urls in glob result', async () => {
|
||||
const { urls } = JSON.parse(await fixture.readFile('/pages.json'));
|
||||
expect(urls).to.include('/test-1');
|
||||
expect(urls).to.include('/test-2');
|
||||
});
|
||||
|
||||
it('respects "export url" overrides in glob result', async () => {
|
||||
const { urls } = JSON.parse(await fixture.readFile('/pages.json'));
|
||||
expect(urls).to.include('/AH!');
|
||||
});
|
||||
});
|
|
@ -2098,10 +2098,12 @@ importers:
|
|||
astro: workspace:*
|
||||
astro-scripts: workspace:*
|
||||
chai: ^4.3.6
|
||||
es-module-lexer: ^0.10.5
|
||||
linkedom: ^0.14.12
|
||||
mocha: ^9.2.2
|
||||
dependencies:
|
||||
'@mdx-js/rollup': 2.1.2
|
||||
es-module-lexer: 0.10.5
|
||||
devDependencies:
|
||||
'@types/chai': 4.3.1
|
||||
'@types/mocha': 9.1.1
|
||||
|
|
Loading…
Reference in a new issue