From 7ee1f9cbbf11d32cd5f7015608ee816c0a38b327 Mon Sep 17 00:00:00 2001 From: Christopher MANEU Date: Fri, 25 Sep 2026 15:32:43 +0200 Subject: [PATCH 1/2] fix(docs): render Markdown tables in MDX pages Enable GFM explicitly for the installed MDX integration, and add built-output regression tests to the Pages workflow. Fixes #1427 Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com> --- .github/workflows/static.yml | 2 ++ website/README.md | 8 +++++ website/astro.config.mjs | 2 ++ website/package.json | 1 + website/tests/tables.test.mjs | 59 +++++++++++++++++++++++++++++++++++ 5 files changed, 72 insertions(+) create mode 100644 website/tests/tables.test.mjs diff --git a/.github/workflows/static.yml b/.github/workflows/static.yml index 452dcd2e..9fd6826f 100644 --- a/.github/workflows/static.yml +++ b/.github/workflows/static.yml @@ -67,6 +67,8 @@ jobs: SITE: https://microsoft.github.io BASE_PATH: /scope run: pnpm run build + - name: Test rendered documentation + run: pnpm test:build - name: Upload artifact if: github.ref == 'refs/heads/main' uses: actions/upload-pages-artifact@v3 diff --git a/website/README.md b/website/README.md index d5f4e582..32815f72 100644 --- a/website/README.md +++ b/website/README.md @@ -49,12 +49,17 @@ Sidebar order is defined in `astro.config.mjs`, not by directory order. | `pnpm build` | Build the production site to `./dist/` | | `pnpm preview` | Preview the production build locally | | `pnpm test` | Test site plugins with Node's built-in test runner | +| `pnpm test:build` | Test rendered Markdown/MDX tables in `dist/` after a build | | `pnpm refresh:openapi` | Generate the OpenAPI snapshot from `scope-core` | ## Authoring docs - Use `.md` for plain Markdown, `.mdx` whenever the page contains JSX (e.g. Starlight ``). +- Use standard pipe-delimited Markdown tables in both `.md` and `.mdx`. + Keep `markdown.gfm: true` explicit in [astro.config.mjs](astro.config.mjs): + the installed MDX integration does not inherit Astro's Markdown processor + defaults, so otherwise MDX tables render as plain text. - Write internal Markdown links and literal MDX `href`/`src` attributes relative to the site root, such as `/getting-started/access/`. [src/plugins/remark-base-path.mjs](src/plugins/remark-base-path.mjs) @@ -104,11 +109,14 @@ public deployment locally, run these commands from `website/`: ```sh pnpm test SITE=https://microsoft.github.io BASE_PATH=/scope pnpm build +pnpm test:build SITE=https://microsoft.github.io BASE_PATH=/scope pnpm preview ``` Open `/scope/` on the preview server. Keep `BASE_PATH` the same for the build and preview so assets, navigation, and search use the same URLs. +CI runs `pnpm test:build` after building to catch table-rendering regressions +in both Markdown and MDX pages. ## Learn more diff --git a/website/astro.config.mjs b/website/astro.config.mjs index 3f662e00..13542618 100644 --- a/website/astro.config.mjs +++ b/website/astro.config.mjs @@ -55,6 +55,8 @@ export default defineConfig({ base, server: { port: docPort }, markdown: { + // The installed MDX integration does not inherit the processor's GFM default. + gfm: true, remarkPlugins: [[remarkBasePath, { base }], remarkHttpSnippets], }, integrations: [ diff --git a/website/package.json b/website/package.json index 513b77f9..e5525e41 100644 --- a/website/package.json +++ b/website/package.json @@ -9,6 +9,7 @@ "build": "astro build", "preview": "worktree-env && astro preview", "test": "node --test src/plugins/*.test.mjs", + "test:build": "node --test tests/*.test.mjs", "astro": "astro", "refresh:openapi": "cd .. && pnpm --filter api generate:openapi" }, diff --git a/website/tests/tables.test.mjs b/website/tests/tables.test.mjs new file mode 100644 index 00000000..1de1c168 --- /dev/null +++ b/website/tests/tables.test.mjs @@ -0,0 +1,59 @@ +// Copyright (c) Microsoft Corporation. +// Licensed under the MIT License. + +import assert from 'node:assert/strict'; +import { readFile } from 'node:fs/promises'; +import { test } from 'node:test'; + +async function readTables(page) { + const html = await readFile(new URL(`../dist/${page}/index.html`, import.meta.url), 'utf8'); + return html.match(/]*>[\s\S]*?<\/table>/g) ?? []; +} + +function assertTable(table, headers, fields) { + assert.deepEqual( + Array.from(table.matchAll(/]*>([\s\S]*?)<\/th>/g), ([, text]) => text), + headers, + ); + assert.deepEqual( + Array.from( + table.matchAll(/]*>\s*]*>]*>([^<]+)<\/code>/g), + ([, field]) => field, + ), + fields, + ); + assert.equal(Array.from(table.matchAll(/ { + const tables = await readTables('guides/defining-profiles'); + assert.equal(tables.length, 1, 'The profile anatomy must render as an HTML table, not pipe-delimited text'); + assertTable(tables[0], ['Field', 'Layer', 'Description'], [ + 'name', + 'description', + 'workerType', + 'model', + 'agentVersion', + 'mcpServers', + 'skillRevisions', + 'extensions', + ]); + assert.match(tables[0], /Choosing a coding agent<\/a>/); + assert.match(tables[0], /VS Code Copilot only\.<\/strong>/); +}); + +test('preserves tables in the plain Markdown profile schema reference', async () => { + const tables = await readTables('reference/profile-schema'); + assert.equal(tables.length, 2); + assertTable(tables[0], ['Field', 'Type', 'Required', 'Description'], ['id', 'name', 'description']); + assertTable(tables[1], ['Field', 'Type', 'Required', 'Description'], [ + 'id', + 'profileId', + 'workerType', + 'model', + 'agentVersion', + 'mcpServers', + 'skillRevisions', + 'createdAt', + ]); +}); From 1612fdaf3d03a8f42f6c4014d9c054dac80e3821 Mon Sep 17 00:00:00 2001 From: Christopher MANEU Date: Fri, 25 Sep 2026 15:34:33 +0200 Subject: [PATCH 2/2] test(docs): run rendered table checks during site builds Use the existing build command for CI coverage without changing GitHub Actions workflow permissions. Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com> --- .github/workflows/static.yml | 2 -- website/README.md | 7 +++---- website/package.json | 2 +- 3 files changed, 4 insertions(+), 7 deletions(-) diff --git a/.github/workflows/static.yml b/.github/workflows/static.yml index 9fd6826f..452dcd2e 100644 --- a/.github/workflows/static.yml +++ b/.github/workflows/static.yml @@ -67,8 +67,6 @@ jobs: SITE: https://microsoft.github.io BASE_PATH: /scope run: pnpm run build - - name: Test rendered documentation - run: pnpm test:build - name: Upload artifact if: github.ref == 'refs/heads/main' uses: actions/upload-pages-artifact@v3 diff --git a/website/README.md b/website/README.md index 32815f72..956e66a2 100644 --- a/website/README.md +++ b/website/README.md @@ -46,7 +46,7 @@ Sidebar order is defined in `astro.config.mjs`, not by directory order. | :--------------------- | :--------------------------------------------------------- | | `pnpm install` | Install dependencies | | `pnpm dev` | Start local dev server at `localhost:4321` | -| `pnpm build` | Build the production site to `./dist/` | +| `pnpm build` | Build the production site to `./dist/` and test its output | | `pnpm preview` | Preview the production build locally | | `pnpm test` | Test site plugins with Node's built-in test runner | | `pnpm test:build` | Test rendered Markdown/MDX tables in `dist/` after a build | @@ -109,14 +109,13 @@ public deployment locally, run these commands from `website/`: ```sh pnpm test SITE=https://microsoft.github.io BASE_PATH=/scope pnpm build -pnpm test:build SITE=https://microsoft.github.io BASE_PATH=/scope pnpm preview ``` Open `/scope/` on the preview server. Keep `BASE_PATH` the same for the build and preview so assets, navigation, and search use the same URLs. -CI runs `pnpm test:build` after building to catch table-rendering regressions -in both Markdown and MDX pages. +`pnpm build` runs `pnpm test:build` after generating the site, so local and +CI builds catch table-rendering regressions in both Markdown and MDX pages. ## Learn more diff --git a/website/package.json b/website/package.json index e5525e41..0cc7a877 100644 --- a/website/package.json +++ b/website/package.json @@ -6,7 +6,7 @@ "scripts": { "dev": "worktree-env && astro dev", "start": "worktree-env && astro dev", - "build": "astro build", + "build": "astro build && pnpm test:build", "preview": "worktree-env && astro preview", "test": "node --test src/plugins/*.test.mjs", "test:build": "node --test tests/*.test.mjs",