diff --git a/.github/workflows/ci-front.yaml b/.github/workflows/ci-front.yaml index c40a018584e1..265bf6d03a0d 100644 --- a/.github/workflows/ci-front.yaml +++ b/.github/workflows/ci-front.yaml @@ -18,7 +18,7 @@ concurrency: jobs: front-sb-build: - runs-on: ci-8-cores + runs-on: ubuntu-latest env: REACT_APP_SERVER_BASE_URL: http://localhost:3000 NX_REJECT_UNKNOWN_LOCAL_CACHE: 0 @@ -39,7 +39,7 @@ jobs: - name: Front / Write .env run: npx nx reset:env twenty-front - name: Front / Build storybook - run: npx nx storybook:build twenty-front + run: npx nx storybook:build twenty-front --configuration=test front-sb-test: runs-on: ci-8-cores needs: front-sb-build diff --git a/nx.json b/nx.json index a0567a4bb423..9dabefb84012 100644 --- a/nx.json +++ b/nx.json @@ -116,6 +116,11 @@ "command": "storybook build", "output-dir": "storybook-static", "config-dir": ".storybook" + }, + "configurations": { + "test": { + "command": "storybook build --test" + } } }, "storybook:dev": { @@ -138,6 +143,9 @@ "host": "localhost", "port": 6006, "silent": true + }, + "configurations": { + "test": {} } }, "storybook:coverage": { @@ -192,7 +200,7 @@ "executor": "nx:run-commands", "options": { "commands": [ - "npx concurrently --kill-others --success=first -n SB,TEST 'nx storybook:static {projectName} --port={args.port}' 'npx wait-on tcp:{args.port} && nx storybook:test {projectName} --port={args.port}'" + "npx concurrently --kill-others --success=first -n SB,TEST 'nx storybook:static {projectName} --port={args.port} --configuration=test' 'npx wait-on tcp:{args.port} && nx storybook:test {projectName} --port={args.port}'" ], "port": 6006 } diff --git a/packages/twenty-front/.storybook/main.ts b/packages/twenty-front/.storybook/main.ts index 9f356c31a651..764ae8aecf5e 100644 --- a/packages/twenty-front/.storybook/main.ts +++ b/packages/twenty-front/.storybook/main.ts @@ -45,6 +45,15 @@ const config: StorybookConfig = { name: '@storybook/react-vite', options: {}, }, + build: { + test: { + disableMDXEntries: true, + disabledAddons: [ + '@storybook/addon-docs', + '@storybook/addon-essentials/docs', + ], + }, + }, docs: { autodocs: false, }, diff --git a/packages/twenty-front/package.json b/packages/twenty-front/package.json index c17719e30146..7d7e2f2e0c4b 100644 --- a/packages/twenty-front/package.json +++ b/packages/twenty-front/package.json @@ -6,7 +6,7 @@ "scripts": { "build": "npx vite build && sh ./scripts/inject-runtime-env.sh", "build:sourcemaps": "VITE_BUILD_SOURCEMAP=true NODE_OPTIONS=--max-old-space-size=4096 npx nx build", - "storybook:build:chromatic": "nx storybook:build", + "storybook:build:chromatic": "nx storybook:build --configuration=test", "start:prod": "NODE_ENV=production npx vite --host", "tsup": "npx tsup" }, diff --git a/packages/twenty-front/project.json b/packages/twenty-front/project.json index b5673df9fe28..332bfc4fafb1 100644 --- a/packages/twenty-front/project.json +++ b/packages/twenty-front/project.json @@ -64,30 +64,7 @@ "env": { "NODE_OPTIONS": "--max_old_space_size=5000" } }, "configurations": { - "docs": { - "env": { - "NODE_OPTIONS": "--max_old_space_size=5000", - "STORYBOOK_SCOPE": "ui-docs" - } - }, - "modules": { - "env": { - "NODE_OPTIONS": "--max_old_space_size=5000", - "STORYBOOK_SCOPE": "modules" - } - }, - "pages": { - "env": { - "NODE_OPTIONS": "--max_old_space_size=5000", - "STORYBOOK_SCOPE": "pages" - } - }, - "performance": { - "env": { - "NODE_OPTIONS": "--max_old_space_size=5000", - "STORYBOOK_SCOPE": "performance" - } - } + "test": {} } }, "storybook:dev": { @@ -102,10 +79,7 @@ "storybook:static": { "options": { "port": 6006 }, "configurations": { - "docs": { "env": { "STORYBOOK_SCOPE": "ui-docs" } }, - "modules": { "env": { "STORYBOOK_SCOPE": "modules" } }, - "pages": { "env": { "STORYBOOK_SCOPE": "pages" } }, - "performance": { "env": { "STORYBOOK_SCOPE": "performance" } } + "test": {} } }, "storybook:coverage": { @@ -137,7 +111,7 @@ "storybook:static:test": { "options": { "commands": [ - "npx concurrently --kill-others --success=first -n SB,TEST 'nx storybook:static {projectName} --configuration={args.scope} --port={args.port}' 'npx wait-on tcp:{args.port} && nx storybook:test {projectName} --port={args.port} --configuration={args.scope}'" + "npx concurrently --kill-others --success=first -n SB,TEST 'nx storybook:static {projectName} --configuration=test --port={args.port}' 'npx wait-on tcp:{args.port} && nx storybook:test {projectName} --port={args.port} --configuration={args.scope}'" ], "port": 6006 }, diff --git a/packages/twenty-front/src/modules/ui/input/components/IconPicker.tsx b/packages/twenty-front/src/modules/ui/input/components/IconPicker.tsx index b0a0dd2276fd..f1f7cff90ab8 100644 --- a/packages/twenty-front/src/modules/ui/input/components/IconPicker.tsx +++ b/packages/twenty-front/src/modules/ui/input/components/IconPicker.tsx @@ -18,7 +18,7 @@ import { IconButton, IconButtonVariant } from '../button/components/IconButton'; import { LightIconButton } from '../button/components/LightIconButton'; import { IconPickerHotkeyScope } from '../types/IconPickerHotkeyScope'; -type IconPickerProps = { +export type IconPickerProps = { disabled?: boolean; dropdownId?: string; onChange: (params: { iconKey: string; Icon: IconComponent }) => void; @@ -154,6 +154,11 @@ export const IconPicker = ({ dropdownHotkeyScope={{ scope: IconPickerHotkeyScope.IconPicker }} clickableComponent={ { + const [{ selectedIconKey }, updateArgs] = useArgs(); + + return ( + { + updateArgs({ selectedIconKey: iconKey }); + }} + selectedIconKey={selectedIconKey} + /> + ); +}; const meta: Meta = { title: 'UI/Input/IconPicker/IconPicker', component: IconPicker, decorators: [IconsProviderDecorator, ComponentDecorator], + render: Render, }; export default meta; @@ -18,39 +36,45 @@ type Story = StoryObj; export const Default: Story = {}; -export const WithSelectedIcon: Story = { - args: { selectedIconKey: 'IconCalendarEvent' }, -}; - export const WithOpen: Story = { play: async ({ canvasElement }) => { const canvas = within(canvasElement); - const iconPickerButton = await canvas.findByRole('button'); + const iconPickerButton = await canvas.findByRole('button', { + name: 'Click to select icon (no icon selected)', + }); - userEvent.click(iconPickerButton); + await userEvent.click(iconPickerButton); }, }; -export const WithOpenAndSelectedIcon: Story = { +export const WithSelectedIcon: Story = { args: { selectedIconKey: 'IconCalendarEvent' }, +}; + +export const WithOpenAndSelectedIcon: Story = { + ...WithSelectedIcon, play: async ({ canvasElement }) => { const canvas = within(canvasElement); - const iconPickerButton = await canvas.findByRole('button'); + const iconPickerButton = await canvas.findByRole('button', { + name: 'Click to select icon (selected: IconCalendarEvent)', + }); - userEvent.click(iconPickerButton); + await userEvent.click(iconPickerButton); }, }; export const WithSearch: Story = { - args: { selectedIconKey: 'IconBuildingSkyscraper' }, + ...WithSelectedIcon, play: async ({ canvasElement }) => { const canvas = within(canvasElement); - const iconPickerButton = await canvas.findByRole('button'); + const iconPickerButton = await canvas.findByRole('button', { + name: 'Click to select icon (selected: IconCalendarEvent)', + }); - userEvent.click(iconPickerButton); + await userEvent.click(iconPickerButton); const searchInput = await canvas.findByRole('textbox'); @@ -67,13 +91,15 @@ export const WithSearch: Story = { }; export const WithSearchAndClose: Story = { - args: { selectedIconKey: 'IconBuildingSkyscraper' }, + ...WithSelectedIcon, play: async ({ canvasElement }) => { const canvas = within(canvasElement); - const iconPickerButton = await canvas.findByRole('button'); + let iconPickerButton = await canvas.findByRole('button', { + name: 'Click to select icon (selected: IconCalendarEvent)', + }); - userEvent.click(iconPickerButton); + await userEvent.click(iconPickerButton); let searchInput = await canvas.findByRole('textbox'); @@ -87,13 +113,19 @@ export const WithSearchAndClose: Story = { expect(searchedIcon).toBeInTheDocument(); - userEvent.click(searchedIcon); + await userEvent.click(searchedIcon); - await sleep(100); + await sleep(500); + + expect(searchedIcon).not.toBeInTheDocument(); + + iconPickerButton = await canvas.findByRole('button', { + name: 'Click to select icon (selected: IconBuildingSkyscraper)', + }); userEvent.click(iconPickerButton); - await sleep(100); + await sleep(500); searchInput = await canvas.findByRole('textbox'); diff --git a/packages/twenty-ui/.storybook/main.ts b/packages/twenty-ui/.storybook/main.ts index 270259adfdd7..a27e1bccf947 100644 --- a/packages/twenty-ui/.storybook/main.ts +++ b/packages/twenty-ui/.storybook/main.ts @@ -16,6 +16,15 @@ const config: StorybookConfig = { name: '@storybook/react-vite', options: {}, }, + build: { + test: { + disableMDXEntries: true, + disabledAddons: [ + '@storybook/addon-docs', + '@storybook/addon-essentials/docs', + ], + }, + }, }; export default config; diff --git a/packages/twenty-ui/project.json b/packages/twenty-ui/project.json index c25a1f4d106e..641a15fae554 100644 --- a/packages/twenty-ui/project.json +++ b/packages/twenty-ui/project.json @@ -38,7 +38,11 @@ }, "test": {}, "typecheck": {}, - "storybook:build": {}, + "storybook:build": { + "configurations": { + "test": {} + } + }, "storybook:dev": { "options": { "port": 6007 } }, @@ -46,6 +50,9 @@ "options": { "buildTarget": "twenty-ui:storybook:build", "port": 6007 + }, + "configurations": { + "test": {} } }, "storybook:coverage": {},