From a134660ef772cd203b957c14394985fc0e354df4 Mon Sep 17 00:00:00 2001 From: Kendall Gassner Date: Tue, 21 Jan 2025 20:05:31 +0000 Subject: [PATCH 01/39] Run storybook axe scans on CI --- packages/react/src/__tests__/storybook.test.tsx | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/packages/react/src/__tests__/storybook.test.tsx b/packages/react/src/__tests__/storybook.test.tsx index d0bc7d1a7b7..e7680ba66a6 100644 --- a/packages/react/src/__tests__/storybook.test.tsx +++ b/packages/react/src/__tests__/storybook.test.tsx @@ -1,4 +1,5 @@ import glob from 'fast-glob' +import {checkStoriesForAxeViolations} from '../utils/testing' import groupBy from 'lodash.groupby' import fs from 'node:fs' import path from 'node:path' @@ -122,6 +123,10 @@ describe.each(components)('%s', (_component, stories) => { }) } }) + + const name = path.basename(relativeFilepath).split('.')[0] + const directory = `../../${path.dirname(relativeFilepath)}/` + checkStoriesForAxeViolations(name, directory) } }) From 6d3928a392da086657eecec3f27609ad55153140 Mon Sep 17 00:00:00 2001 From: Kendall Gassner Date: Tue, 21 Jan 2025 23:29:01 +0000 Subject: [PATCH 02/39] test --- e2e/components/all.test.ts | 99 +++++++++++++++++++ .../react/src/__tests__/storybook.test.tsx | 80 +-------------- packages/react/src/utils/testing.tsx | 76 ++++++++++++++ 3 files changed, 178 insertions(+), 77 deletions(-) create mode 100644 e2e/components/all.test.ts diff --git a/e2e/components/all.test.ts b/e2e/components/all.test.ts new file mode 100644 index 00000000000..a5636db0b91 --- /dev/null +++ b/e2e/components/all.test.ts @@ -0,0 +1,99 @@ +import {test, expect} from '@playwright/test' +import path from 'path' +import {stories} from '../../packages/react/src/utils/testing' +import {visit} from '../test-helpers/storybook' +import {themes} from '../test-helpers/themes' + +// const stories: Array<{title: string; id: string; viewports?: Array}> = [ +// { +// title: 'Default', +// id: 'experimental-components-banner--default', +// viewports: ['primer.breakpoint.xs', 'primer.breakpoint.sm'], +// }, +// { +// title: 'Critical', +// id: 'experimental-components-banner-features--critical', +// }, +// { +// title: 'Dismiss', +// id: 'experimental-components-banner-features--dismiss', +// }, +// { +// title: 'Dismiss With Actions', +// id: 'experimental-components-banner-features--dismiss-with-actions', +// }, +// { +// title: 'Info', +// id: 'experimental-components-banner-features--info', +// }, +// { +// title: 'Success', +// id: 'experimental-components-banner-features--success', +// }, +// { +// title: 'Upsell', +// id: 'experimental-components-banner-features--upsell', +// }, +// { +// title: 'Warning', +// id: 'experimental-components-banner-features--warning', +// }, +// { +// title: 'WithActions', +// id: 'experimental-components-banner-features--with-actions', +// viewports: ['primer.breakpoint.xs', 'primer.breakpoint.sm'], +// }, +// { +// title: 'WithHiddenTitle', +// id: 'experimental-components-banner-features--with-hidden-title', +// }, +// { +// title: 'WithHiddenTitleAndActions', +// id: 'experimental-components-banner-features--with-hidden-title-and-actions', +// viewports: ['primer.breakpoint.xs', 'primer.breakpoint.sm'], +// }, +// { +// title: 'DismissibleWithHiddenTitleAndActions', +// id: 'experimental-components-banner-features--dismissible-with-hidden-title-and-actions', +// viewports: ['primer.breakpoint.xs', 'primer.breakpoint.sm'], +// }, +// { +// title: 'DismissibleWithHiddenTitleAndSecondaryAction', +// id: 'experimental-components-banner-features--dismissible-with-hidden-title-and-secondary-action', +// viewports: ['primer.breakpoint.xs', 'primer.breakpoint.sm'], +// }, +// { +// title: 'InSidebar', +// id: 'experimental-components-banner-examples--in-sidebar', +// }, +// { +// title: 'Multiline', +// id: 'experimental-components-banner-examples--multiline', +// viewports: ['primer.breakpoint.xs', 'primer.breakpoint.sm'], +// }, +// ] + +test.describe('axe @aat', () => { + for (const {story, relativeFilepath, type} of stories) { + for (const storyName of Object.keys(story)) { + const name = path.basename(relativeFilepath).split('.')[0] + + for (const theme of themes) { + test.describe(theme, () => { + test('axe @aat', async ({page}) => { + await visit(page, { + id: `${name}-${type}--${storyName + .split(/(?=[A-Z])/) + .join('-') + .toLowerCase()}`, + globals: { + colorScheme: theme, + }, + }) + await expect(page).toHaveNoViolations() + }) + }) + } + } + } +}) diff --git a/packages/react/src/__tests__/storybook.test.tsx b/packages/react/src/__tests__/storybook.test.tsx index e7680ba66a6..10dc5a829e7 100644 --- a/packages/react/src/__tests__/storybook.test.tsx +++ b/packages/react/src/__tests__/storybook.test.tsx @@ -1,81 +1,9 @@ import glob from 'fast-glob' -import {checkStoriesForAxeViolations} from '../utils/testing' +import {stories, ROOT_DIRECTORY, allowlist} from '../utils/testing' import groupBy from 'lodash.groupby' import fs from 'node:fs' import path from 'node:path' -const ROOT_DIRECTORY = path.resolve(__dirname, '..', '..') -// Components opted into the new story format -// TODO: Remove this allowlist when all components use the new story format -const allowlist = [ - 'ActionList', - 'ActionMenu', - 'AnchoredOverlay', - 'Autocomplete', - 'Avatar', - 'AvatarStack', - 'AvatarPair', - 'Breadcrumbs', - 'BranchName', - 'Blankslate', - 'Box', - 'Button', - 'Checkbox', - 'CheckboxGroup', - 'ConfirmationDialog', - 'CounterLabel', - 'DataTable', - 'Details', - 'Dialog', - 'Flash', - 'FormControl', - 'Header', - 'Heading', - 'IconButton', - 'FilteredActionList', - 'Link', - 'Octicon', - 'Pagehead', - 'Pagination', - 'ProgressBar', - 'Radio', - 'RadioGroup', - 'RelativeTime', - 'Select', - 'SegmentedControl', - 'Spinner', - 'StateLabel', - 'SubNav', - 'TabNav', - 'Textarea', - 'TextInput', - 'TextInputWithTokens', - 'Tooltip', - 'TreeView', - 'Timeline', - 'ToggleSwitch', - 'Token', - 'UnderlineNav2', -] -const stories = glob - .sync('src/**/*.stories.tsx', { - cwd: ROOT_DIRECTORY, - }) - // Filter out deprecated stories - .filter(file => !file.includes('deprecated')) - .filter(file => - allowlist.some( - component => file.includes(`/${component}.stories.tsx`) || file.includes(`/${component}.features.stories.tsx`), - ), - ) - .map(file => { - const filepath = path.join(ROOT_DIRECTORY, file) - const type = path.basename(filepath, '.stories.tsx').endsWith('features') ? 'feature' : 'default' - const name = type === 'feature' ? path.basename(file, '.features.stories.tsx') : path.basename(file, '.stories.tsx') - - return {name, story: require(filepath), type, relativeFilepath: path.relative(ROOT_DIRECTORY, filepath)} - }) - const components = Object.entries( groupBy(stories, ({name}) => { return name @@ -103,6 +31,8 @@ describe.each(components)('%s', (_component, stories) => { expect(story.default.title).toMatch(type === 'default' ? defaultTitlePattern : featureTitlePattern) }) + console.log(Object.keys(story), type) + if (type === 'default') { test('exports a Default story', () => { expect(story.Default).toBeDefined() @@ -123,10 +53,6 @@ describe.each(components)('%s', (_component, stories) => { }) } }) - - const name = path.basename(relativeFilepath).split('.')[0] - const directory = `../../${path.dirname(relativeFilepath)}/` - checkStoriesForAxeViolations(name, directory) } }) diff --git a/packages/react/src/utils/testing.tsx b/packages/react/src/utils/testing.tsx index a01cb435dec..b9047bca7da 100644 --- a/packages/react/src/utils/testing.tsx +++ b/packages/react/src/utils/testing.tsx @@ -8,6 +8,8 @@ import customRules from '@github/axe-github' import {ThemeProvider} from '..' import {default as defaultTheme} from '../theme' import type {LiveRegionElement} from '@primer/live-region-element' +import path from 'path' +import {glob} from 'fast-glob' type ComputedStyles = Record> @@ -16,6 +18,80 @@ const readFile = promisify(require('fs').readFile) export const COMPONENT_DISPLAY_NAME_REGEX = /^[A-Z][A-Za-z]+(\.[A-Z][A-Za-z]+)*$/ +export const ROOT_DIRECTORY = path.resolve(__dirname, '..', '..') + +// Components opted into the new story format +// TODO: Remove this allowlist when all components use the new story format +export const allowlist = [ + 'ActionList', + 'ActionMenu', + 'AnchoredOverlay', + 'Autocomplete', + 'Avatar', + 'AvatarStack', + 'AvatarPair', + 'Breadcrumbs', + 'BranchName', + 'Blankslate', + 'Box', + 'Button', + 'Checkbox', + 'CheckboxGroup', + 'ConfirmationDialog', + 'CounterLabel', + 'DataTable', + 'Details', + 'Dialog', + 'Flash', + 'FormControl', + 'Header', + 'Heading', + 'IconButton', + 'FilteredActionList', + 'Link', + 'Octicon', + 'Pagehead', + 'Pagination', + 'ProgressBar', + 'Radio', + 'RadioGroup', + 'RelativeTime', + 'Select', + 'SegmentedControl', + 'Spinner', + 'StateLabel', + 'SubNav', + 'TabNav', + 'Textarea', + 'TextInput', + 'TextInputWithTokens', + 'Tooltip', + 'TreeView', + 'Timeline', + 'ToggleSwitch', + 'Token', + 'UnderlineNav2', +] + +export const stories = glob + .sync('src/**/*.stories.tsx', { + cwd: ROOT_DIRECTORY, + }) + // Filter out deprecated stories + .filter(file => !file.includes('deprecated')) + .filter(file => + allowlist.some( + component => file.includes(`/${component}.stories.tsx`) || file.includes(`/${component}.features.stories.tsx`), + ), + ) + .map(file => { + const filepath = path.join(ROOT_DIRECTORY, file) + const type = path.basename(filepath, '.stories.tsx').endsWith('features') ? 'feature' : 'default' + const name = type === 'feature' ? path.basename(file, '.features.stories.tsx') : path.basename(file, '.stories.tsx') + + return {name, story: require(filepath), type, relativeFilepath: path.relative(ROOT_DIRECTORY, filepath)} + }) + declare global { // eslint-disable-next-line @typescript-eslint/no-namespace namespace jest { From 55171899feb7193264625117a2f349edafef1bbb Mon Sep 17 00:00:00 2001 From: Kendall Gassner Date: Tue, 21 Jan 2025 23:29:30 +0000 Subject: [PATCH 03/39] clean --- e2e/components/all.test.ts | 69 ------------------------ packages/react/src/Button/ButtonBase.tsx | 3 +- 2 files changed, 2 insertions(+), 70 deletions(-) diff --git a/e2e/components/all.test.ts b/e2e/components/all.test.ts index a5636db0b91..31037e10508 100644 --- a/e2e/components/all.test.ts +++ b/e2e/components/all.test.ts @@ -4,75 +4,6 @@ import {stories} from '../../packages/react/src/utils/testing' import {visit} from '../test-helpers/storybook' import {themes} from '../test-helpers/themes' -// const stories: Array<{title: string; id: string; viewports?: Array}> = [ -// { -// title: 'Default', -// id: 'experimental-components-banner--default', -// viewports: ['primer.breakpoint.xs', 'primer.breakpoint.sm'], -// }, -// { -// title: 'Critical', -// id: 'experimental-components-banner-features--critical', -// }, -// { -// title: 'Dismiss', -// id: 'experimental-components-banner-features--dismiss', -// }, -// { -// title: 'Dismiss With Actions', -// id: 'experimental-components-banner-features--dismiss-with-actions', -// }, -// { -// title: 'Info', -// id: 'experimental-components-banner-features--info', -// }, -// { -// title: 'Success', -// id: 'experimental-components-banner-features--success', -// }, -// { -// title: 'Upsell', -// id: 'experimental-components-banner-features--upsell', -// }, -// { -// title: 'Warning', -// id: 'experimental-components-banner-features--warning', -// }, -// { -// title: 'WithActions', -// id: 'experimental-components-banner-features--with-actions', -// viewports: ['primer.breakpoint.xs', 'primer.breakpoint.sm'], -// }, -// { -// title: 'WithHiddenTitle', -// id: 'experimental-components-banner-features--with-hidden-title', -// }, -// { -// title: 'WithHiddenTitleAndActions', -// id: 'experimental-components-banner-features--with-hidden-title-and-actions', -// viewports: ['primer.breakpoint.xs', 'primer.breakpoint.sm'], -// }, -// { -// title: 'DismissibleWithHiddenTitleAndActions', -// id: 'experimental-components-banner-features--dismissible-with-hidden-title-and-actions', -// viewports: ['primer.breakpoint.xs', 'primer.breakpoint.sm'], -// }, -// { -// title: 'DismissibleWithHiddenTitleAndSecondaryAction', -// id: 'experimental-components-banner-features--dismissible-with-hidden-title-and-secondary-action', -// viewports: ['primer.breakpoint.xs', 'primer.breakpoint.sm'], -// }, -// { -// title: 'InSidebar', -// id: 'experimental-components-banner-examples--in-sidebar', -// }, -// { -// title: 'Multiline', -// id: 'experimental-components-banner-examples--multiline', -// viewports: ['primer.breakpoint.xs', 'primer.breakpoint.sm'], -// }, -// ] - test.describe('axe @aat', () => { for (const {story, relativeFilepath, type} of stories) { for (const storyName of Object.keys(story)) { diff --git a/packages/react/src/Button/ButtonBase.tsx b/packages/react/src/Button/ButtonBase.tsx index 3ef7ae902b1..f9f580707e0 100644 --- a/packages/react/src/Button/ButtonBase.tsx +++ b/packages/react/src/Button/ButtonBase.tsx @@ -72,7 +72,8 @@ const ButtonBase = forwardRef( if ( innerRef.current && !(innerRef.current instanceof HTMLButtonElement) && - !((innerRef.current as unknown) instanceof HTMLAnchorElement) + !((innerRef.current as unknown) instanceof HTMLAnchorElement) && + !((innerRef.current as HTMLElement).tagName === 'SUMMARY') ) { // eslint-disable-next-line no-console console.warn('This component should be an instanceof a semantic button or anchor') From 87a95d21655d2cbc9460c4df5254545c8e1ae0bb Mon Sep 17 00:00:00 2001 From: Kendall Gassner Date: Tue, 21 Jan 2025 23:32:58 +0000 Subject: [PATCH 04/39] remove console --- packages/react/src/__tests__/storybook.test.tsx | 2 -- 1 file changed, 2 deletions(-) diff --git a/packages/react/src/__tests__/storybook.test.tsx b/packages/react/src/__tests__/storybook.test.tsx index 10dc5a829e7..63935d37cd7 100644 --- a/packages/react/src/__tests__/storybook.test.tsx +++ b/packages/react/src/__tests__/storybook.test.tsx @@ -31,8 +31,6 @@ describe.each(components)('%s', (_component, stories) => { expect(story.default.title).toMatch(type === 'default' ? defaultTitlePattern : featureTitlePattern) }) - console.log(Object.keys(story), type) - if (type === 'default') { test('exports a Default story', () => { expect(story.Default).toBeDefined() From dc061f8da4f74b253ec211a3063d50d19eb5d060 Mon Sep 17 00:00:00 2001 From: Kendall Gassner Date: Tue, 21 Jan 2025 23:46:05 +0000 Subject: [PATCH 05/39] rephrase id --- e2e/components/all.test.ts | 6 ++---- 1 file changed, 2 insertions(+), 4 deletions(-) diff --git a/e2e/components/all.test.ts b/e2e/components/all.test.ts index 31037e10508..02a61e8041b 100644 --- a/e2e/components/all.test.ts +++ b/e2e/components/all.test.ts @@ -5,15 +5,13 @@ import {visit} from '../test-helpers/storybook' import {themes} from '../test-helpers/themes' test.describe('axe @aat', () => { - for (const {story, relativeFilepath, type} of stories) { + for (const {story} of stories) { for (const storyName of Object.keys(story)) { - const name = path.basename(relativeFilepath).split('.')[0] - for (const theme of themes) { test.describe(theme, () => { test('axe @aat', async ({page}) => { await visit(page, { - id: `${name}-${type}--${storyName + id: `${story.default.title.replace('/', '-').toLowerCase()}--${storyName .split(/(?=[A-Z])/) .join('-') .toLowerCase()}`, From 154e0629a2f5cfd6bfdc9e5e245c60a401995dd1 Mon Sep 17 00:00:00 2001 From: Kendall Gassner Date: Tue, 21 Jan 2025 23:51:45 +0000 Subject: [PATCH 06/39] unused --- e2e/components/all.test.ts | 1 - 1 file changed, 1 deletion(-) diff --git a/e2e/components/all.test.ts b/e2e/components/all.test.ts index 02a61e8041b..f8a8125d867 100644 --- a/e2e/components/all.test.ts +++ b/e2e/components/all.test.ts @@ -1,5 +1,4 @@ import {test, expect} from '@playwright/test' -import path from 'path' import {stories} from '../../packages/react/src/utils/testing' import {visit} from '../test-helpers/storybook' import {themes} from '../test-helpers/themes' From 5ebec1d7bf990b8c46d8d7233464d79d05ebd287 Mon Sep 17 00:00:00 2001 From: Kendall Gassner Date: Thu, 23 Jan 2025 13:30:36 -0800 Subject: [PATCH 07/39] edits --- .github/workflows/ci.yml | 75 ++++++++--------- e2e/components/Axe.test.ts | 34 ++++++++ e2e/components/all.test.ts | 27 ------- .../react/src/__tests__/storybook.test.tsx | 80 ++++++++++++++++++- packages/react/src/utils/testing.tsx | 76 ------------------ 5 files changed, 151 insertions(+), 141 deletions(-) create mode 100644 e2e/components/Axe.test.ts delete mode 100644 e2e/components/all.test.ts diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index 5db06240809..18a0330f427 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -26,7 +26,7 @@ jobs: uses: actions/setup-node@v4 with: node-version: 22 - cache: 'npm' + cache: "npm" - name: Install dependencies run: npm ci - name: Check for unformatted files @@ -41,7 +41,7 @@ jobs: uses: actions/setup-node@v4 with: node-version: 22 - cache: 'npm' + cache: "npm" - name: Install dependencies run: npm ci - name: Lint JavaScript @@ -60,7 +60,7 @@ jobs: uses: actions/setup-node@v4 with: node-version: 22 - cache: 'npm' + cache: "npm" - name: Install dependencies run: npm ci - name: Build @@ -77,7 +77,7 @@ jobs: uses: actions/setup-node@v4 with: node-version: 22 - cache: 'npm' + cache: "npm" - name: Install dependencies run: npm ci - name: Build project @@ -94,7 +94,7 @@ jobs: uses: actions/setup-node@v4 with: node-version: 22 - cache: 'npm' + cache: "npm" - name: Install dependencies run: npm ci - name: Build @@ -112,7 +112,7 @@ jobs: uses: actions/setup-node@v4 with: node-version: 22 - cache: 'npm' + cache: "npm" - name: Install dependencies run: npm ci - name: Build storybook @@ -129,7 +129,7 @@ jobs: - name: Run VRT uses: docker://mcr.microsoft.com/playwright:v1.47.2-jammy env: - STORYBOOK_URL: 'http://172.17.0.1:6006' + STORYBOOK_URL: "http://172.17.0.1:6006" with: args: npx playwright test --grep @vrt --shard="${{ matrix.shard }}/${{ strategy.job-total }}" - name: Stop storybook @@ -152,7 +152,7 @@ jobs: uses: actions/setup-node@v4 with: node-version: 22 - cache: 'npm' + cache: "npm" - name: install dependencies run: npm ci - name: download all reports @@ -188,7 +188,7 @@ jobs: uses: actions/setup-node@v4 with: node-version: 22 - cache: 'npm' + cache: "npm" - name: Install dependencies run: npm ci - name: Build storybook @@ -205,7 +205,7 @@ jobs: - name: Run VRT uses: docker://mcr.microsoft.com/playwright:v1.47.2-jammy env: - STORYBOOK_URL: 'http://172.17.0.1:6006' + STORYBOOK_URL: "http://172.17.0.1:6006" with: args: npx playwright test --grep @vrt --shard="${{ matrix.shard }}/${{ strategy.job-total }}" - name: Stop storybook @@ -228,7 +228,7 @@ jobs: uses: actions/setup-node@v4 with: node-version: 22 - cache: 'npm' + cache: "npm" - name: install dependencies run: npm ci - name: download all reports @@ -248,19 +248,39 @@ jobs: if: ${{ needs.vrt-runner-all-flags.result == 'failure' }} run: exit 1 + build-components-json: + runs-on: ubuntu-latest + steps: + - name: Checkout repository + uses: actions/checkout@v4 + - name: Use Node.js 20.x + uses: actions/setup-node@v4 + with: + node-version: 22 + cache: "npm" + - name: Install dependencies + run: npm ci + - name: Build storybook to generate story IDs + run: npm run build:storybook + working-directory: packages/react + - name: Build components.json + run: npx tsx script/components-json/build.ts --storybook-data 'storybook-static/index.json' + working-directory: packages/react + aat-runner: runs-on: ubuntu-latest-16-cores strategy: fail-fast: false matrix: shard: [1, 2, 3, 4] + needs: build-components-json steps: - uses: actions/checkout@v4 - name: Use Node.js 20.x uses: actions/setup-node@v4 with: node-version: 22 - cache: 'npm' + cache: "npm" - name: Install dependencies run: npm ci - name: Build storybook @@ -277,7 +297,7 @@ jobs: - name: Run AAT uses: docker://mcr.microsoft.com/playwright:v1.47.2-jammy env: - STORYBOOK_URL: 'http://172.17.0.1:6006' + STORYBOOK_URL: "http://172.17.0.1:6006" with: args: npx playwright test --grep @aat --shard="${{ matrix.shard }}/${{ strategy.job-total }}" - name: Stop storybook @@ -300,7 +320,7 @@ jobs: uses: actions/setup-node@v4 with: node-version: 22 - cache: 'npm' + cache: "npm" - name: install dependencies run: npm ci - name: download all reports @@ -336,7 +356,7 @@ jobs: uses: actions/setup-node@v4 with: node-version: 22 - cache: 'npm' + cache: "npm" - name: Install dependencies run: npm ci - name: Build storybook @@ -353,7 +373,7 @@ jobs: - name: Run AAT uses: docker://mcr.microsoft.com/playwright:v1.47.2-jammy env: - STORYBOOK_URL: 'http://172.17.0.1:6006' + STORYBOOK_URL: "http://172.17.0.1:6006" with: args: npx playwright test --grep @aat --shard="${{ matrix.shard }}/${{ strategy.job-total }}" - name: Stop storybook @@ -376,7 +396,7 @@ jobs: uses: actions/setup-node@v4 with: node-version: 22 - cache: 'npm' + cache: "npm" - name: install dependencies run: npm ci - name: download all reports @@ -396,25 +416,6 @@ jobs: if: ${{ needs.aat-runner-all-flags.result == 'failure' }} run: exit 1 - build-components-json: - runs-on: ubuntu-latest - steps: - - name: Checkout repository - uses: actions/checkout@v4 - - name: Use Node.js 20.x - uses: actions/setup-node@v4 - with: - node-version: 22 - cache: 'npm' - - name: Install dependencies - run: npm ci - - name: Build storybook to generate story IDs - run: npm run build:storybook - working-directory: packages/react - - name: Build components.json - run: npx tsx script/components-json/build.ts --storybook-data 'storybook-static/index.json' - working-directory: packages/react - sizes: runs-on: ubuntu-latest steps: @@ -424,7 +425,7 @@ jobs: uses: actions/setup-node@v4 with: node-version: 22 - cache: 'npm' + cache: "npm" - name: Install dependencies run: npm ci - name: Build diff --git a/e2e/components/Axe.test.ts b/e2e/components/Axe.test.ts new file mode 100644 index 00000000000..a48807edf60 --- /dev/null +++ b/e2e/components/Axe.test.ts @@ -0,0 +1,34 @@ +import {test, expect} from '@playwright/test' +import componentsConfig from '../../packages/react/generated/components.json' +import {visit} from '../test-helpers/storybook' +import {themes} from '../test-helpers/themes' + +type Component = { + stories: Array<{ + id: string + }> +} + +const {components} = componentsConfig + +test.describe('@aat', () => { + for (const [name, component] of Object.entries(components as Record)) { + test.describe(name, () => { + for (const story of component.stories) { + for (const theme of themes) { + test.describe(theme, () => { + test(`${story.id}`, async ({page}) => { + await visit(page, { + id: story.id, + globals: { + colorScheme: themes[0], + }, + }) + await expect(page).toHaveNoViolations() + }) + }) + } + } + }) + } +}) diff --git a/e2e/components/all.test.ts b/e2e/components/all.test.ts deleted file mode 100644 index f8a8125d867..00000000000 --- a/e2e/components/all.test.ts +++ /dev/null @@ -1,27 +0,0 @@ -import {test, expect} from '@playwright/test' -import {stories} from '../../packages/react/src/utils/testing' -import {visit} from '../test-helpers/storybook' -import {themes} from '../test-helpers/themes' - -test.describe('axe @aat', () => { - for (const {story} of stories) { - for (const storyName of Object.keys(story)) { - for (const theme of themes) { - test.describe(theme, () => { - test('axe @aat', async ({page}) => { - await visit(page, { - id: `${story.default.title.replace('/', '-').toLowerCase()}--${storyName - .split(/(?=[A-Z])/) - .join('-') - .toLowerCase()}`, - globals: { - colorScheme: theme, - }, - }) - await expect(page).toHaveNoViolations() - }) - }) - } - } - } -}) diff --git a/packages/react/src/__tests__/storybook.test.tsx b/packages/react/src/__tests__/storybook.test.tsx index 63935d37cd7..67f985a3e34 100644 --- a/packages/react/src/__tests__/storybook.test.tsx +++ b/packages/react/src/__tests__/storybook.test.tsx @@ -1,9 +1,87 @@ import glob from 'fast-glob' -import {stories, ROOT_DIRECTORY, allowlist} from '../utils/testing' import groupBy from 'lodash.groupby' import fs from 'node:fs' import path from 'node:path' +const ROOT_DIRECTORY = path.resolve(__dirname, '..', '..') + +// Components opted into the new story format +// TODO: Remove this allowlist when all components use the new story format +const allowlist = [ + 'ActionList', + 'ActionMenu', + 'AnchoredOverlay', + 'Autocomplete', + 'Avatar', + 'AvatarStack', + 'AvatarPair', + 'Breadcrumbs', + 'BranchName', + 'Blankslate', + 'Box', + 'Button', + 'Checkbox', + 'CheckboxGroup', + 'ConfirmationDialog', + 'CounterLabel', + 'DataTable', + 'Details', + 'Dialog', + 'Flash', + 'FormControl', + 'Header', + 'Heading', + 'IconButton', + 'FilteredActionList', + 'Link', + 'Octicon', + 'Pagehead', + 'Pagination', + 'ProgressBar', + 'Radio', + 'RadioGroup', + 'RelativeTime', + 'Select', + 'SegmentedControl', + 'Spinner', + 'StateLabel', + 'SubNav', + 'TabNav', + 'Textarea', + 'TextInput', + 'TextInputWithTokens', + 'Tooltip', + 'TreeView', + 'Timeline', + 'ToggleSwitch', + 'Token', + 'UnderlineNav2', +] + +const stories = glob + .sync('src/**/*.stories.tsx', { + cwd: ROOT_DIRECTORY, + }) + // Filter out deprecated stories + .filter(file => !file.includes('deprecated')) + .filter(file => + allowlist.some( + component => file.includes(`/${component}.stories.tsx`) || file.includes(`/${component}.features.stories.tsx`), + ), + ) + .map(file => { + const filepath = path.join(ROOT_DIRECTORY, file) + const type = path.basename(filepath, '.stories.tsx').endsWith('features') ? 'feature' : 'default' + const name = type === 'feature' ? path.basename(file, '.features.stories.tsx') : path.basename(file, '.stories.tsx') + + return { + name, + story: require(filepath), + type, + relativeFilepath: path.relative(ROOT_DIRECTORY, filepath), + } + }) + const components = Object.entries( groupBy(stories, ({name}) => { return name diff --git a/packages/react/src/utils/testing.tsx b/packages/react/src/utils/testing.tsx index b9047bca7da..a01cb435dec 100644 --- a/packages/react/src/utils/testing.tsx +++ b/packages/react/src/utils/testing.tsx @@ -8,8 +8,6 @@ import customRules from '@github/axe-github' import {ThemeProvider} from '..' import {default as defaultTheme} from '../theme' import type {LiveRegionElement} from '@primer/live-region-element' -import path from 'path' -import {glob} from 'fast-glob' type ComputedStyles = Record> @@ -18,80 +16,6 @@ const readFile = promisify(require('fs').readFile) export const COMPONENT_DISPLAY_NAME_REGEX = /^[A-Z][A-Za-z]+(\.[A-Z][A-Za-z]+)*$/ -export const ROOT_DIRECTORY = path.resolve(__dirname, '..', '..') - -// Components opted into the new story format -// TODO: Remove this allowlist when all components use the new story format -export const allowlist = [ - 'ActionList', - 'ActionMenu', - 'AnchoredOverlay', - 'Autocomplete', - 'Avatar', - 'AvatarStack', - 'AvatarPair', - 'Breadcrumbs', - 'BranchName', - 'Blankslate', - 'Box', - 'Button', - 'Checkbox', - 'CheckboxGroup', - 'ConfirmationDialog', - 'CounterLabel', - 'DataTable', - 'Details', - 'Dialog', - 'Flash', - 'FormControl', - 'Header', - 'Heading', - 'IconButton', - 'FilteredActionList', - 'Link', - 'Octicon', - 'Pagehead', - 'Pagination', - 'ProgressBar', - 'Radio', - 'RadioGroup', - 'RelativeTime', - 'Select', - 'SegmentedControl', - 'Spinner', - 'StateLabel', - 'SubNav', - 'TabNav', - 'Textarea', - 'TextInput', - 'TextInputWithTokens', - 'Tooltip', - 'TreeView', - 'Timeline', - 'ToggleSwitch', - 'Token', - 'UnderlineNav2', -] - -export const stories = glob - .sync('src/**/*.stories.tsx', { - cwd: ROOT_DIRECTORY, - }) - // Filter out deprecated stories - .filter(file => !file.includes('deprecated')) - .filter(file => - allowlist.some( - component => file.includes(`/${component}.stories.tsx`) || file.includes(`/${component}.features.stories.tsx`), - ), - ) - .map(file => { - const filepath = path.join(ROOT_DIRECTORY, file) - const type = path.basename(filepath, '.stories.tsx').endsWith('features') ? 'feature' : 'default' - const name = type === 'feature' ? path.basename(file, '.features.stories.tsx') : path.basename(file, '.stories.tsx') - - return {name, story: require(filepath), type, relativeFilepath: path.relative(ROOT_DIRECTORY, filepath)} - }) - declare global { // eslint-disable-next-line @typescript-eslint/no-namespace namespace jest { From 05bff8ba8b145d7d39fde03af8e27cf04b466a3d Mon Sep 17 00:00:00 2001 From: Kendall Gassner Date: Thu, 23 Jan 2025 13:59:25 -0800 Subject: [PATCH 08/39] try --- .github/workflows/ci.yml | 47 +++++++++++++++++++++------------------- 1 file changed, 25 insertions(+), 22 deletions(-) diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index 1337b9b76fe..f1b9723ed7f 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -100,12 +100,35 @@ jobs: - name: Build run: npm run build -ws --if-present + build-components-json: + runs-on: ubuntu-latest + steps: + - name: Checkout repository + uses: actions/checkout@v4 + - name: Use Node.js 20.x + uses: actions/setup-node@v4 + with: + node-version: 22 + cache: "npm" + - name: Install dependencies + run: npm ci + - name: Build storybook to generate story IDs + run: npm run build:storybook + working-directory: packages/react + - name: Build components.json + run: npx tsx script/components-json/build.ts --storybook-data 'storybook-static/index.json' + working-directory: packages/react + - name: Build hooks.json + run: npx tsx script/hooks-json/build.ts + working-directory: packages/react + vrt-runner: runs-on: ubuntu-latest-16-cores strategy: fail-fast: false matrix: shard: [1, 2, 3, 4] + needs: build-components-json steps: - uses: actions/checkout@v4 - name: Use Node.js 20.x @@ -178,6 +201,7 @@ jobs: fail-fast: false matrix: shard: [1, 2, 3, 4] + needs: build-components-json env: VITE_PRIMER_REACT_CSS_MODULES_TEAM: 1 VITE_PRIMER_REACT_CSS_MODULES_STAFF: 1 @@ -248,28 +272,6 @@ jobs: if: ${{ needs.vrt-runner-all-flags.result == 'failure' }} run: exit 1 - build-components-json: - runs-on: ubuntu-latest - steps: - - name: Checkout repository - uses: actions/checkout@v4 - - name: Use Node.js 20.x - uses: actions/setup-node@v4 - with: - node-version: 22 - cache: "npm" - - name: Install dependencies - run: npm ci - - name: Build storybook to generate story IDs - run: npm run build:storybook - working-directory: packages/react - - name: Build components.json - run: npx tsx script/components-json/build.ts --storybook-data 'storybook-static/index.json' - working-directory: packages/react - - name: Build hooks.json - run: npx tsx script/hooks-json/build.ts - working-directory: packages/react - aat-runner: runs-on: ubuntu-latest-16-cores strategy: @@ -349,6 +351,7 @@ jobs: fail-fast: false matrix: shard: [1, 2, 3, 4] + needs: build-components-json env: VITE_PRIMER_REACT_CSS_MODULES_TEAM: 1 VITE_PRIMER_REACT_CSS_MODULES_STAFF: 1 From 9c29e5ef86dd93a38800c5fa0c1b179280d98c7d Mon Sep 17 00:00:00 2001 From: Kendall Gassner Date: Thu, 23 Jan 2025 14:55:27 -0800 Subject: [PATCH 09/39] test --- .github/workflows/ci.yml | 15 +++++++++++++++ 1 file changed, 15 insertions(+) diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index f1b9723ed7f..e99b7152f98 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -121,6 +121,11 @@ jobs: - name: Build hooks.json run: npx tsx script/hooks-json/build.ts working-directory: packages/react + - name: Upload Artifact + uses: actions/upload-artifact@v3 + with: + name: components.json + path: packages/react/generated/components.json vrt-runner: runs-on: ubuntu-latest-16-cores @@ -149,6 +154,11 @@ jobs: pid=$! echo "pid=$pid" >> $GITHUB_OUTPUT sleep 5 + - name: Download Artifact + uses: actions/download-artifact@v3 + with: + name: components.json + path: packages/react/generated/components.json - name: Run VRT uses: docker://mcr.microsoft.com/playwright:v1.47.2-jammy env: @@ -299,6 +309,11 @@ jobs: pid=$! echo "pid=$pid" >> $GITHUB_OUTPUT sleep 5 + - name: Download Artifact + uses: actions/download-artifact@v3 + with: + name: components.json + path: packages/react/generated/components.json - name: Run AAT uses: docker://mcr.microsoft.com/playwright:v1.47.2-jammy env: From a07320c0bb916c5a31dd1150d48f951c0b69534c Mon Sep 17 00:00:00 2001 From: Kendall Gassner Date: Thu, 23 Jan 2025 14:56:44 -0800 Subject: [PATCH 10/39] test --- .github/workflows/ci.yml | 10 ++++++++++ 1 file changed, 10 insertions(+) diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index e99b7152f98..456e27be16c 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -236,6 +236,11 @@ jobs: pid=$! echo "pid=$pid" >> $GITHUB_OUTPUT sleep 5 + - name: Download Artifact + uses: actions/download-artifact@v3 + with: + name: components.json + path: packages/react/generated/components.json - name: Run VRT uses: docker://mcr.microsoft.com/playwright:v1.47.2-jammy env: @@ -391,6 +396,11 @@ jobs: pid=$! echo "pid=$pid" >> $GITHUB_OUTPUT sleep 5 + - name: Download Artifact + uses: actions/download-artifact@v3 + with: + name: components.json + path: packages/react/generated/components.json - name: Run AAT uses: docker://mcr.microsoft.com/playwright:v1.47.2-jammy env: From 3b3a0b011706361a4f3052001141d5b8f2c824f3 Mon Sep 17 00:00:00 2001 From: Kendall Gassner Date: Thu, 23 Jan 2025 15:07:14 -0800 Subject: [PATCH 11/39] store --- .github/workflows/ci.yml | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index 456e27be16c..907e4de856f 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -124,7 +124,7 @@ jobs: - name: Upload Artifact uses: actions/upload-artifact@v3 with: - name: components.json + name: components-artifact path: packages/react/generated/components.json vrt-runner: @@ -157,7 +157,7 @@ jobs: - name: Download Artifact uses: actions/download-artifact@v3 with: - name: components.json + name: components-artifact path: packages/react/generated/components.json - name: Run VRT uses: docker://mcr.microsoft.com/playwright:v1.47.2-jammy @@ -239,7 +239,7 @@ jobs: - name: Download Artifact uses: actions/download-artifact@v3 with: - name: components.json + name: components-artifact path: packages/react/generated/components.json - name: Run VRT uses: docker://mcr.microsoft.com/playwright:v1.47.2-jammy @@ -317,7 +317,7 @@ jobs: - name: Download Artifact uses: actions/download-artifact@v3 with: - name: components.json + name: components-artifact path: packages/react/generated/components.json - name: Run AAT uses: docker://mcr.microsoft.com/playwright:v1.47.2-jammy @@ -399,7 +399,7 @@ jobs: - name: Download Artifact uses: actions/download-artifact@v3 with: - name: components.json + name: components-artifact path: packages/react/generated/components.json - name: Run AAT uses: docker://mcr.microsoft.com/playwright:v1.47.2-jammy From 35aefd2c4b03d90d8e3809f15f0d6e5e57f65daa Mon Sep 17 00:00:00 2001 From: Kendall Gassner Date: Thu, 23 Jan 2025 15:13:56 -0800 Subject: [PATCH 12/39] store --- .github/workflows/ci.yml | 20 ++++++++++---------- 1 file changed, 10 insertions(+), 10 deletions(-) diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index 907e4de856f..b6d4c6347ae 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -124,8 +124,8 @@ jobs: - name: Upload Artifact uses: actions/upload-artifact@v3 with: - name: components-artifact - path: packages/react/generated/components.json + name: components + path: packages/react/generated/components vrt-runner: runs-on: ubuntu-latest-16-cores @@ -157,8 +157,8 @@ jobs: - name: Download Artifact uses: actions/download-artifact@v3 with: - name: components-artifact - path: packages/react/generated/components.json + name: components + path: packages/react/generated/components - name: Run VRT uses: docker://mcr.microsoft.com/playwright:v1.47.2-jammy env: @@ -239,8 +239,8 @@ jobs: - name: Download Artifact uses: actions/download-artifact@v3 with: - name: components-artifact - path: packages/react/generated/components.json + name: components + path: packages/react/generated/components - name: Run VRT uses: docker://mcr.microsoft.com/playwright:v1.47.2-jammy env: @@ -317,8 +317,8 @@ jobs: - name: Download Artifact uses: actions/download-artifact@v3 with: - name: components-artifact - path: packages/react/generated/components.json + name: components + path: packages/react/generated/components - name: Run AAT uses: docker://mcr.microsoft.com/playwright:v1.47.2-jammy env: @@ -399,8 +399,8 @@ jobs: - name: Download Artifact uses: actions/download-artifact@v3 with: - name: components-artifact - path: packages/react/generated/components.json + name: components + path: packages/react/generated/components - name: Run AAT uses: docker://mcr.microsoft.com/playwright:v1.47.2-jammy env: From 59dbd1ba40840349bec25d74c9a4373c35f43ed6 Mon Sep 17 00:00:00 2001 From: Kendall Gassner Date: Thu, 23 Jan 2025 15:20:05 -0800 Subject: [PATCH 13/39] store --- .github/workflows/ci.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index b6d4c6347ae..5b5215393f4 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -125,7 +125,7 @@ jobs: uses: actions/upload-artifact@v3 with: name: components - path: packages/react/generated/components + path: packages/react/generated/components.json vrt-runner: runs-on: ubuntu-latest-16-cores From 029c4e922bbe937c92557078c8a6026eade83c4c Mon Sep 17 00:00:00 2001 From: Kendall Gassner Date: Thu, 23 Jan 2025 15:29:21 -0800 Subject: [PATCH 14/39] fic --- .github/workflows/ci.yml | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index 5b5215393f4..b0c5747d87b 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -240,7 +240,7 @@ jobs: uses: actions/download-artifact@v3 with: name: components - path: packages/react/generated/components + path: packages/react/generated - name: Run VRT uses: docker://mcr.microsoft.com/playwright:v1.47.2-jammy env: @@ -318,7 +318,7 @@ jobs: uses: actions/download-artifact@v3 with: name: components - path: packages/react/generated/components + path: packages/react/generated - name: Run AAT uses: docker://mcr.microsoft.com/playwright:v1.47.2-jammy env: @@ -400,7 +400,7 @@ jobs: uses: actions/download-artifact@v3 with: name: components - path: packages/react/generated/components + path: packages/react/generated - name: Run AAT uses: docker://mcr.microsoft.com/playwright:v1.47.2-jammy env: From a35400f2c042c4d117bb265b865571575e20587c Mon Sep 17 00:00:00 2001 From: Kendall Gassner Date: Fri, 24 Jan 2025 12:41:49 -0800 Subject: [PATCH 15/39] fix vrt --- .github/workflows/ci.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index b0c5747d87b..73d504e912a 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -158,7 +158,7 @@ jobs: uses: actions/download-artifact@v3 with: name: components - path: packages/react/generated/components + path: packages/react/generated - name: Run VRT uses: docker://mcr.microsoft.com/playwright:v1.47.2-jammy env: From 5b8a3648b037d2b96aacc9d49fe6a4ab65aa0307 Mon Sep 17 00:00:00 2001 From: Kendall Gassner Date: Mon, 27 Jan 2025 10:25:32 -0800 Subject: [PATCH 16/39] fix axe violation --- packages/react/src/ActionMenu/ActionMenu.tsx | 5 ++--- .../react/src/ButtonGroup/ButtonGroup.features.stories.tsx | 2 +- 2 files changed, 3 insertions(+), 4 deletions(-) diff --git a/packages/react/src/ActionMenu/ActionMenu.tsx b/packages/react/src/ActionMenu/ActionMenu.tsx index b2dd4b81a9b..2e08c000876 100644 --- a/packages/react/src/ActionMenu/ActionMenu.tsx +++ b/packages/react/src/ActionMenu/ActionMenu.tsx @@ -217,9 +217,8 @@ const Anchor = React.forwardRef(({children: }) /** this component is syntactical sugar 🍭 */ -export type ActionMenuButtonProps = Omit & { - children: React.ReactNode -} +export type ActionMenuButtonProps = ButtonProps + const MenuButton = React.forwardRef(({...props}, anchorRef) => { return ( diff --git a/packages/react/src/ButtonGroup/ButtonGroup.features.stories.tsx b/packages/react/src/ButtonGroup/ButtonGroup.features.stories.tsx index da2b99ff6e6..8258f7d2cc8 100644 --- a/packages/react/src/ButtonGroup/ButtonGroup.features.stories.tsx +++ b/packages/react/src/ButtonGroup/ButtonGroup.features.stories.tsx @@ -111,7 +111,7 @@ export const DropdownSplit = () => { {selectedAction} - More options + {actions.map((action, index) => { From f56f96c4f9f6d37c4e865af1373a6182b15255cd Mon Sep 17 00:00:00 2001 From: Kendall Gassner Date: Mon, 27 Jan 2025 12:22:10 -0800 Subject: [PATCH 17/39] fix --- .github/workflows/ci.yml | 38 +++++++++++++++++++------------------- 1 file changed, 19 insertions(+), 19 deletions(-) diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index 73d504e912a..b030eb22dfc 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -26,7 +26,7 @@ jobs: uses: actions/setup-node@v4 with: node-version: 22 - cache: "npm" + cache: 'npm' - name: Install dependencies run: npm ci - name: Check for unformatted files @@ -41,7 +41,7 @@ jobs: uses: actions/setup-node@v4 with: node-version: 22 - cache: "npm" + cache: 'npm' - name: Install dependencies run: npm ci - name: Lint JavaScript @@ -60,7 +60,7 @@ jobs: uses: actions/setup-node@v4 with: node-version: 22 - cache: "npm" + cache: 'npm' - name: Install dependencies run: npm ci - name: Build @@ -77,7 +77,7 @@ jobs: uses: actions/setup-node@v4 with: node-version: 22 - cache: "npm" + cache: 'npm' - name: Install dependencies run: npm ci - name: Build project @@ -94,7 +94,7 @@ jobs: uses: actions/setup-node@v4 with: node-version: 22 - cache: "npm" + cache: 'npm' - name: Install dependencies run: npm ci - name: Build @@ -109,7 +109,7 @@ jobs: uses: actions/setup-node@v4 with: node-version: 22 - cache: "npm" + cache: 'npm' - name: Install dependencies run: npm ci - name: Build storybook to generate story IDs @@ -140,7 +140,7 @@ jobs: uses: actions/setup-node@v4 with: node-version: 22 - cache: "npm" + cache: 'npm' - name: Install dependencies run: npm ci - name: Build storybook @@ -162,7 +162,7 @@ jobs: - name: Run VRT uses: docker://mcr.microsoft.com/playwright:v1.47.2-jammy env: - STORYBOOK_URL: "http://172.17.0.1:6006" + STORYBOOK_URL: 'http://172.17.0.1:6006' with: args: npx playwright test --grep @vrt --shard="${{ matrix.shard }}/${{ strategy.job-total }}" - name: Stop storybook @@ -185,7 +185,7 @@ jobs: uses: actions/setup-node@v4 with: node-version: 22 - cache: "npm" + cache: 'npm' - name: install dependencies run: npm ci - name: download all reports @@ -222,7 +222,7 @@ jobs: uses: actions/setup-node@v4 with: node-version: 22 - cache: "npm" + cache: 'npm' - name: Install dependencies run: npm ci - name: Build storybook @@ -244,7 +244,7 @@ jobs: - name: Run VRT uses: docker://mcr.microsoft.com/playwright:v1.47.2-jammy env: - STORYBOOK_URL: "http://172.17.0.1:6006" + STORYBOOK_URL: 'http://172.17.0.1:6006' with: args: npx playwright test --grep @vrt --shard="${{ matrix.shard }}/${{ strategy.job-total }}" - name: Stop storybook @@ -267,7 +267,7 @@ jobs: uses: actions/setup-node@v4 with: node-version: 22 - cache: "npm" + cache: 'npm' - name: install dependencies run: npm ci - name: download all reports @@ -300,7 +300,7 @@ jobs: uses: actions/setup-node@v4 with: node-version: 22 - cache: "npm" + cache: 'npm' - name: Install dependencies run: npm ci - name: Build storybook @@ -322,7 +322,7 @@ jobs: - name: Run AAT uses: docker://mcr.microsoft.com/playwright:v1.47.2-jammy env: - STORYBOOK_URL: "http://172.17.0.1:6006" + STORYBOOK_URL: 'http://172.17.0.1:6006' with: args: npx playwright test --grep @aat --shard="${{ matrix.shard }}/${{ strategy.job-total }}" - name: Stop storybook @@ -345,7 +345,7 @@ jobs: uses: actions/setup-node@v4 with: node-version: 22 - cache: "npm" + cache: 'npm' - name: install dependencies run: npm ci - name: download all reports @@ -382,7 +382,7 @@ jobs: uses: actions/setup-node@v4 with: node-version: 22 - cache: "npm" + cache: 'npm' - name: Install dependencies run: npm ci - name: Build storybook @@ -404,7 +404,7 @@ jobs: - name: Run AAT uses: docker://mcr.microsoft.com/playwright:v1.47.2-jammy env: - STORYBOOK_URL: "http://172.17.0.1:6006" + STORYBOOK_URL: 'http://172.17.0.1:6006' with: args: npx playwright test --grep @aat --shard="${{ matrix.shard }}/${{ strategy.job-total }}" - name: Stop storybook @@ -427,7 +427,7 @@ jobs: uses: actions/setup-node@v4 with: node-version: 22 - cache: "npm" + cache: 'npm' - name: install dependencies run: npm ci - name: download all reports @@ -456,7 +456,7 @@ jobs: uses: actions/setup-node@v4 with: node-version: 22 - cache: "npm" + cache: 'npm' - name: Install dependencies run: npm ci - name: Build From 74302e662e6b908aca169ed4c56dac6c89069066 Mon Sep 17 00:00:00 2001 From: Kendall Gassner Date: Mon, 27 Jan 2025 12:36:01 -0800 Subject: [PATCH 18/39] test --- e2e/components/Axe.test.ts | 35 ++++++++++++++++------------------- 1 file changed, 16 insertions(+), 19 deletions(-) diff --git a/e2e/components/Axe.test.ts b/e2e/components/Axe.test.ts index a48807edf60..4bd9c4a3be5 100644 --- a/e2e/components/Axe.test.ts +++ b/e2e/components/Axe.test.ts @@ -1,33 +1,30 @@ import {test, expect} from '@playwright/test' -import componentsConfig from '../../packages/react/generated/components.json' +import componentsConfig from '../../docs/public/storybook/index.json' import {visit} from '../test-helpers/storybook' import {themes} from '../test-helpers/themes' type Component = { - stories: Array<{ - id: string - }> + name: string } -const {components} = componentsConfig +const {entries} = componentsConfig test.describe('@aat', () => { - for (const [name, component] of Object.entries(components as Record)) { - test.describe(name, () => { - for (const story of component.stories) { - for (const theme of themes) { - test.describe(theme, () => { - test(`${story.id}`, async ({page}) => { - await visit(page, { - id: story.id, - globals: { - colorScheme: themes[0], - }, - }) - await expect(page).toHaveNoViolations() + for (const [id, entry] of Object.entries(entries as Record)) { + const {name} = entry + test.describe(id, () => { + for (const theme of themes) { + test.describe(theme, () => { + test(name, async ({page}) => { + await visit(page, { + id: id, + globals: { + colorScheme: themes[0], + }, }) + await expect(page).toHaveNoViolations() }) - } + }) } }) } From 0d4ca8a912547e176c896bdd1ac1617f675df93b Mon Sep 17 00:00:00 2001 From: Kendall Gassner Date: Mon, 27 Jan 2025 12:46:36 -0800 Subject: [PATCH 19/39] test --- e2e/components/Axe.test.ts | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/e2e/components/Axe.test.ts b/e2e/components/Axe.test.ts index 4bd9c4a3be5..28984b79788 100644 --- a/e2e/components/Axe.test.ts +++ b/e2e/components/Axe.test.ts @@ -1,5 +1,5 @@ import {test, expect} from '@playwright/test' -import componentsConfig from '../../docs/public/storybook/index.json' +import componentsConfig from '../../packages/react/storybook-static/index.json' import {visit} from '../test-helpers/storybook' import {themes} from '../test-helpers/themes' @@ -17,7 +17,7 @@ test.describe('@aat', () => { test.describe(theme, () => { test(name, async ({page}) => { await visit(page, { - id: id, + id, globals: { colorScheme: themes[0], }, From 0d8b47f6d136e45eee4a73791c524637f13ae3fc Mon Sep 17 00:00:00 2001 From: Kendall Gassner Date: Mon, 27 Jan 2025 13:09:27 -0800 Subject: [PATCH 20/39] ActionMenu story fix --- .../ActionMenu/ActionMenu.examples.stories.tsx | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) diff --git a/packages/react/src/ActionMenu/ActionMenu.examples.stories.tsx b/packages/react/src/ActionMenu/ActionMenu.examples.stories.tsx index ce1ca3662de..94986df4c28 100644 --- a/packages/react/src/ActionMenu/ActionMenu.examples.stories.tsx +++ b/packages/react/src/ActionMenu/ActionMenu.examples.stories.tsx @@ -410,15 +410,15 @@ export const MultipleSections = () => { - + Raw file content - alert('Workflows clicked')}>Download + alert('Workflows clicked')}>Download - alert('Workflows clicked')}>Jump to line - alert('Workflows clicked')}>Find in file + alert('Workflows clicked')}>Jump to line + alert('Workflows clicked')}>Find in file - alert('Workflows clicked')}>Copy path - alert('Workflows clicked')}>Copy permalink + alert('Workflows clicked')}>Copy path + alert('Workflows clicked')}>Copy permalink @@ -434,9 +434,9 @@ export const MultipleSections = () => { ))} - + View options - alert('Delete file')} variant="danger"> + alert('Delete file')} variant="danger"> Delete file From 7b28de0dc2e7f9f6cdbfa77b28933ee8978c0e25 Mon Sep 17 00:00:00 2001 From: Kendall Gassner Date: Mon, 27 Jan 2025 13:35:19 -0800 Subject: [PATCH 21/39] Header axe violations --- packages/react/src/Header/Header.dev.module.css | 5 +++-- packages/react/src/Header/Header.dev.stories.tsx | 6 +++--- 2 files changed, 6 insertions(+), 5 deletions(-) diff --git a/packages/react/src/Header/Header.dev.module.css b/packages/react/src/Header/Header.dev.module.css index 8d90de7725a..3c5c23be022 100644 --- a/packages/react/src/Header/Header.dev.module.css +++ b/packages/react/src/Header/Header.dev.module.css @@ -1,5 +1,6 @@ .HeaderDev { - background-color: var(--label-olive-bgColor-active); + background-color: var(--display-pine-bgColor-emphasis); + color: var(--color-prettylights-syntax-carriage-return-text) } .HeaderDevItem { @@ -7,5 +8,5 @@ } .HeaderDevLink { - color: var(--color-prettylights-syntax-markup-inserted-text); + color: var(--color-prettylights-syntax-carriage-return-text); } diff --git a/packages/react/src/Header/Header.dev.stories.tsx b/packages/react/src/Header/Header.dev.stories.tsx index 66756f36e93..a05c9898420 100644 --- a/packages/react/src/Header/Header.dev.stories.tsx +++ b/packages/react/src/Header/Header.dev.stories.tsx @@ -22,7 +22,7 @@ export const WithCss = () => ( primer_react_css_modules_ga: true, }} > -
+
@@ -38,7 +38,7 @@ export const WithCss = () => ( ) export const WithSx = () => ( -
+
@@ -60,7 +60,7 @@ export const WithSxAndCSS = () => ( primer_react_css_modules_ga: true, }} > -
+
From 597010e6c247a2a409e96cec6e1de49d86ccb585 Mon Sep 17 00:00:00 2001 From: Kendall Gassner Date: Mon, 27 Jan 2025 13:54:08 -0800 Subject: [PATCH 22/39] fix aria-label --- .../react/src/ButtonGroup/ButtonGroup.features.stories.tsx | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/packages/react/src/ButtonGroup/ButtonGroup.features.stories.tsx b/packages/react/src/ButtonGroup/ButtonGroup.features.stories.tsx index 8258f7d2cc8..1325f09c8c2 100644 --- a/packages/react/src/ButtonGroup/ButtonGroup.features.stories.tsx +++ b/packages/react/src/ButtonGroup/ButtonGroup.features.stories.tsx @@ -73,7 +73,7 @@ export const InactiveButtonsGroup = () => { ) const secondaryButton = ( - + ) return ( @@ -84,7 +84,7 @@ export const InactiveButtonsGroup = () => { {}}> - + {secondaryButton} From 7af1e657b5b6c8ce28f6d21c4a57b2ee5cf8ba62 Mon Sep 17 00:00:00 2001 From: Kendall Gassner Date: Mon, 27 Jan 2025 13:57:57 -0800 Subject: [PATCH 23/39] Eanable SelectPanel feature flag for FilteredActionList Story --- .../src/FilteredActionList/FilteredActionList.stories.tsx | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/packages/react/src/FilteredActionList/FilteredActionList.stories.tsx b/packages/react/src/FilteredActionList/FilteredActionList.stories.tsx index 288044c974b..637a6a57455 100644 --- a/packages/react/src/FilteredActionList/FilteredActionList.stories.tsx +++ b/packages/react/src/FilteredActionList/FilteredActionList.stories.tsx @@ -4,6 +4,7 @@ import {ThemeProvider} from '..' import {FilteredActionList} from '../FilteredActionList' import BaseStyles from '../BaseStyles' import Box from '../Box' +import {FeatureFlags} from '../FeatureFlags' const meta: Meta = { title: 'Components/FilteredActionList', @@ -57,7 +58,7 @@ export function Default(): JSX.Element { const filteredItems = items.filter(item => item.text.toLowerCase().startsWith(filter.toLowerCase())) return ( - <> +

Filtered Action List

Please select labels that describe your issue:
- +
) } From 2474ca917ef978fa4e7b1cf8bdf534202fc4d72f Mon Sep 17 00:00:00 2001 From: Kendall Gassner Date: Mon, 27 Jan 2025 14:07:33 -0800 Subject: [PATCH 24/39] format + lint + remove cli changes --- .github/workflows/ci.yml | 73 ++++++------------- .../react/src/Header/Header.dev.module.css | 2 +- 2 files changed, 23 insertions(+), 52 deletions(-) diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index b030eb22dfc..dcda667caba 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -100,40 +100,12 @@ jobs: - name: Build run: npm run build -ws --if-present - build-components-json: - runs-on: ubuntu-latest - steps: - - name: Checkout repository - uses: actions/checkout@v4 - - name: Use Node.js 20.x - uses: actions/setup-node@v4 - with: - node-version: 22 - cache: 'npm' - - name: Install dependencies - run: npm ci - - name: Build storybook to generate story IDs - run: npm run build:storybook - working-directory: packages/react - - name: Build components.json - run: npx tsx script/components-json/build.ts --storybook-data 'storybook-static/index.json' - working-directory: packages/react - - name: Build hooks.json - run: npx tsx script/hooks-json/build.ts - working-directory: packages/react - - name: Upload Artifact - uses: actions/upload-artifact@v3 - with: - name: components - path: packages/react/generated/components.json - vrt-runner: runs-on: ubuntu-latest-16-cores strategy: fail-fast: false matrix: shard: [1, 2, 3, 4] - needs: build-components-json steps: - uses: actions/checkout@v4 - name: Use Node.js 20.x @@ -154,11 +126,6 @@ jobs: pid=$! echo "pid=$pid" >> $GITHUB_OUTPUT sleep 5 - - name: Download Artifact - uses: actions/download-artifact@v3 - with: - name: components - path: packages/react/generated - name: Run VRT uses: docker://mcr.microsoft.com/playwright:v1.47.2-jammy env: @@ -211,7 +178,6 @@ jobs: fail-fast: false matrix: shard: [1, 2, 3, 4] - needs: build-components-json env: VITE_PRIMER_REACT_CSS_MODULES_TEAM: 1 VITE_PRIMER_REACT_CSS_MODULES_STAFF: 1 @@ -236,11 +202,6 @@ jobs: pid=$! echo "pid=$pid" >> $GITHUB_OUTPUT sleep 5 - - name: Download Artifact - uses: actions/download-artifact@v3 - with: - name: components - path: packages/react/generated - name: Run VRT uses: docker://mcr.microsoft.com/playwright:v1.47.2-jammy env: @@ -293,7 +254,6 @@ jobs: fail-fast: false matrix: shard: [1, 2, 3, 4] - needs: build-components-json steps: - uses: actions/checkout@v4 - name: Use Node.js 20.x @@ -314,11 +274,6 @@ jobs: pid=$! echo "pid=$pid" >> $GITHUB_OUTPUT sleep 5 - - name: Download Artifact - uses: actions/download-artifact@v3 - with: - name: components - path: packages/react/generated - name: Run AAT uses: docker://mcr.microsoft.com/playwright:v1.47.2-jammy env: @@ -371,7 +326,6 @@ jobs: fail-fast: false matrix: shard: [1, 2, 3, 4] - needs: build-components-json env: VITE_PRIMER_REACT_CSS_MODULES_TEAM: 1 VITE_PRIMER_REACT_CSS_MODULES_STAFF: 1 @@ -396,11 +350,6 @@ jobs: pid=$! echo "pid=$pid" >> $GITHUB_OUTPUT sleep 5 - - name: Download Artifact - uses: actions/download-artifact@v3 - with: - name: components - path: packages/react/generated - name: Run AAT uses: docker://mcr.microsoft.com/playwright:v1.47.2-jammy env: @@ -447,6 +396,28 @@ jobs: if: ${{ needs.aat-runner-all-flags.result == 'failure' }} run: exit 1 + build-components-json: + runs-on: ubuntu-latest + steps: + - name: Checkout repository + uses: actions/checkout@v4 + - name: Use Node.js 20.x + uses: actions/setup-node@v4 + with: + node-version: 22 + cache: 'npm' + - name: Install dependencies + run: npm ci + - name: Build storybook to generate story IDs + run: npm run build:storybook + working-directory: packages/react + - name: Build components.json + run: npx tsx script/components-json/build.ts --storybook-data 'storybook-static/index.json' + working-directory: packages/react + - name: Build hooks.json + run: npx tsx script/hooks-json/build.ts + working-directory: packages/react + sizes: runs-on: ubuntu-latest steps: diff --git a/packages/react/src/Header/Header.dev.module.css b/packages/react/src/Header/Header.dev.module.css index 3c5c23be022..2dd11157414 100644 --- a/packages/react/src/Header/Header.dev.module.css +++ b/packages/react/src/Header/Header.dev.module.css @@ -1,6 +1,6 @@ .HeaderDev { + color: var(--color-prettylights-syntax-carriage-return-text); background-color: var(--display-pine-bgColor-emphasis); - color: var(--color-prettylights-syntax-carriage-return-text) } .HeaderDevItem { From 762568dee6a034d23f03cfca0e61faee70f345e5 Mon Sep 17 00:00:00 2001 From: Kendall Gassner Date: Mon, 27 Jan 2025 14:10:33 -0800 Subject: [PATCH 25/39] lint --- packages/react/src/Header/Header.dev.module.css | 1 + 1 file changed, 1 insertion(+) diff --git a/packages/react/src/Header/Header.dev.module.css b/packages/react/src/Header/Header.dev.module.css index 2dd11157414..21f1bfc9705 100644 --- a/packages/react/src/Header/Header.dev.module.css +++ b/packages/react/src/Header/Header.dev.module.css @@ -1,5 +1,6 @@ .HeaderDev { color: var(--color-prettylights-syntax-carriage-return-text); + /* eslint-disable-next-line primer/no-display-colors */ background-color: var(--display-pine-bgColor-emphasis); } From 6c3b040c95e97ac22e5fa77599d82df3096b1c94 Mon Sep 17 00:00:00 2001 From: Kendall Gassner Date: Mon, 27 Jan 2025 14:11:29 -0800 Subject: [PATCH 26/39] lint --- packages/react/src/Header/Header.dev.module.css | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/packages/react/src/Header/Header.dev.module.css b/packages/react/src/Header/Header.dev.module.css index 21f1bfc9705..4cc998f661c 100644 --- a/packages/react/src/Header/Header.dev.module.css +++ b/packages/react/src/Header/Header.dev.module.css @@ -1,6 +1,6 @@ .HeaderDev { color: var(--color-prettylights-syntax-carriage-return-text); - /* eslint-disable-next-line primer/no-display-colors */ + /* stylelint-disable-next-line primer/no-display-colors */ background-color: var(--display-pine-bgColor-emphasis); } From c76b15234166c1a8bc5cdc94419a47ac86299e24 Mon Sep 17 00:00:00 2001 From: Kendall Gassner Date: Mon, 27 Jan 2025 14:34:38 -0800 Subject: [PATCH 27/39] unique aria-labels on banner --- e2e/components/Axe.test.ts | 1 + packages/react/src/Banner/Banner.stories.tsx | 2 ++ 2 files changed, 3 insertions(+) diff --git a/e2e/components/Axe.test.ts b/e2e/components/Axe.test.ts index 28984b79788..af478dc3ae9 100644 --- a/e2e/components/Axe.test.ts +++ b/e2e/components/Axe.test.ts @@ -1,4 +1,5 @@ import {test, expect} from '@playwright/test' +// @ts-ignore import componentsConfig from '../../packages/react/storybook-static/index.json' import {visit} from '../test-helpers/storybook' import {themes} from '../test-helpers/themes' diff --git a/packages/react/src/Banner/Banner.stories.tsx b/packages/react/src/Banner/Banner.stories.tsx index 9952921b71e..069bb0b619f 100644 --- a/packages/react/src/Banner/Banner.stories.tsx +++ b/packages/react/src/Banner/Banner.stories.tsx @@ -38,6 +38,7 @@ export const Playground: StoryObj = { {primaryAction} : null} secondaryAction={ @@ -49,6 +50,7 @@ export const Playground: StoryObj = { {primaryAction} : null} secondaryAction={ From 61df1145475a13352c74ad7a859c1b8d1694f6a2 Mon Sep 17 00:00:00 2001 From: Kendall Gassner Date: Mon, 27 Jan 2025 14:43:47 -0800 Subject: [PATCH 28/39] replace link with button on deprecated storybook example --- .../UnderlinePanels/UnderlinePanels.stories.tsx | 6 ------ .../react/src/stories/deprecated/ActionMenu.stories.tsx | 6 ++---- 2 files changed, 2 insertions(+), 10 deletions(-) diff --git a/packages/react/src/experimental/UnderlinePanels/UnderlinePanels.stories.tsx b/packages/react/src/experimental/UnderlinePanels/UnderlinePanels.stories.tsx index bcbf370d80f..788a2fc12cb 100644 --- a/packages/react/src/experimental/UnderlinePanels/UnderlinePanels.stories.tsx +++ b/packages/react/src/experimental/UnderlinePanels/UnderlinePanels.stories.tsx @@ -16,11 +16,6 @@ const meta: Meta = { name: 'string', }, }, - 'aria-labelledby': { - type: { - name: 'string', - }, - }, id: { type: { name: 'string', @@ -34,7 +29,6 @@ const meta: Meta = { }, args: { 'aria-label': 'Select a tab', - 'aria-labelledby': 'tab', id: 'test', loadingCounters: false, }, diff --git a/packages/react/src/stories/deprecated/ActionMenu.stories.tsx b/packages/react/src/stories/deprecated/ActionMenu.stories.tsx index 89918a136eb..45355491f75 100644 --- a/packages/react/src/stories/deprecated/ActionMenu.stories.tsx +++ b/packages/react/src/stories/deprecated/ActionMenu.stories.tsx @@ -15,13 +15,11 @@ import type {Meta} from '@storybook/react' import React, {useCallback, useState, useRef} from 'react' import styled from 'styled-components' import {ThemeProvider} from '../..' -import type {LinkProps} from '../../Link' -import Link from '../../Link' import type {ActionMenuProps} from '../../deprecated' import {ActionMenu, ActionList} from '../../deprecated' import type {ItemProps} from '../../deprecated/ActionList' import BaseStyles from '../../BaseStyles' -import {Button} from '../../Button' +import {Button, type ButtonProps} from '../../Button' const meta: Meta = { title: 'Deprecated/Components/ActionMenu', @@ -233,7 +231,7 @@ export function ComplexListStory(): JSX.Element { ComplexListStory.storyName = 'Complex List' export function CustomTrigger(): JSX.Element { - const customAnchor = (props: LinkProps) => + const customAnchor = (props: ButtonProps) =>