diff --git a/.changeset/fix-esm-functional-size-tokens.md b/.changeset/fix-esm-functional-size-tokens.md new file mode 100644 index 0000000000..6b07ddebaf --- /dev/null +++ b/.changeset/fix-esm-functional-size-tokens.md @@ -0,0 +1,5 @@ +--- +'@primer/react-brand': patch +--- + +Fixed missing size and animation tokens in tree-shaken ESM component bundles like `Button`. Now all control tokens are loaded globally as a side-effect. diff --git a/.github/workflows/integration_test_nextjs.yml b/.github/workflows/integration_test_nextjs.yml index 7da9767d58..5cd0115a61 100644 --- a/.github/workflows/integration_test_nextjs.yml +++ b/.github/workflows/integration_test_nextjs.yml @@ -96,10 +96,13 @@ jobs: run: | rm ./${{ env.NEXTJS_FOLDER }}/app/page.tsx cp ./packages/e2e/integration-tests/nextjs/page.tsx ./${{ env.NEXTJS_FOLDER }}/app + mkdir ./${{ env.NEXTJS_FOLDER }}/app/button-only + cp ./packages/e2e/integration-tests/nextjs/button-only/page.tsx ./${{ env.NEXTJS_FOLDER }}/app/button-only cp ./packages/e2e/cypress.config.js ./${{ env.NEXTJS_FOLDER }} mkdir ${{ env.NEXTJS_FOLDER }}/integration-tests cp -r ./packages/e2e/integration-tests/fixtures ./${{ env.NEXTJS_FOLDER }}/integration-tests cp -r ./packages/e2e/integration-tests/tests ./${{ env.NEXTJS_FOLDER }}/integration-tests + cp ./packages/e2e/integration-tests/nextjs/check-size-tokens.cy.ts ./${{ env.NEXTJS_FOLDER }}/integration-tests/tests - name: Excluded cypress tests in-place # includes temp workaround for cypress bug. remove when fixed diff --git a/packages/e2e/integration-tests/nextjs/button-only/page.tsx b/packages/e2e/integration-tests/nextjs/button-only/page.tsx new file mode 100644 index 0000000000..34d39d4e29 --- /dev/null +++ b/packages/e2e/integration-tests/nextjs/button-only/page.tsx @@ -0,0 +1,7 @@ +'use client' + +import {Button} from '../../integration-tests/fixtures' + +export default function ButtonOnlyPage() { + return +} diff --git a/packages/e2e/integration-tests/nextjs/check-size-tokens.cy.ts b/packages/e2e/integration-tests/nextjs/check-size-tokens.cy.ts new file mode 100644 index 0000000000..9dd403c8bc --- /dev/null +++ b/packages/e2e/integration-tests/nextjs/check-size-tokens.cy.ts @@ -0,0 +1,15 @@ +describe('Size token integration tests', () => { + it('loads shared size tokens without Stack on the page', () => { + cy.visit('http://localhost:3000/button-only') + + cy.get('[data-testid="button-only"]').should(button => { + const ownerWindow = button[0].ownerDocument.defaultView + + if (!ownerWindow) throw new Error('Expected the Button document to have a window') + + const controlSize = ownerWindow.getComputedStyle(button[0]).getPropertyValue('--brand-control-medium-size').trim() + + expect(controlSize).not.to.equal('') + }) + }) +}) diff --git a/packages/react/src/css/stylesheets.ts b/packages/react/src/css/stylesheets.ts index 9bdb631d3f..30040dcb47 100644 --- a/packages/react/src/css/stylesheets.ts +++ b/packages/react/src/css/stylesheets.ts @@ -9,6 +9,8 @@ import './reset.css' import '@primer/brand-primitives/lib/design-tokens/css/tokens/base/colors/color-scales-with-modes.css' import '@primer/brand-primitives/lib/design-tokens/css/tokens/base/size/size.css' import '@primer/brand-primitives/lib/design-tokens/css/tokens/base/typography/typography.css' +import '@primer/brand-primitives/lib/design-tokens/css/tokens/functional/animation/base.css' +import '@primer/brand-primitives/lib/design-tokens/css/tokens/functional/size/size.css' import '@primer/brand-primitives/lib/design-tokens/css/tokens/functional/typography/typography-responsive.css' import '@primer/brand-primitives/lib/design-tokens/css/tokens/functional/size/breakpoints.css' import '@primer/brand-primitives/lib/design-tokens/css/tokens/functional/size/border.css'