From 03f9ace0bc351a192537a55311479125653e245d Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Rapha=C3=ABl=20Bosi?= <71827178+bosiraphael@users.noreply.github.com> Date: Mon, 15 Jun 2026 15:54:28 +0200 Subject: [PATCH] Make flaky Storybook stories deterministic for Argos (animations + lazy-load) (#21609) MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Follow-up to #21594. A set of stories were still flagged flaky by Argos after the data/image/date fixes. The remaining causes are **animation** and **lazy-load timing**, not data. Argos's screenshot stabilization waits for fonts and images and disables CSS animations at capture, but it does **not** stop JS-driven animations (react-spring) or wait for `React.lazy` chunks to load. Two global, test-only changes in the Storybook Vitest setup, plus an `optimizeDeps` entry: **1. Disable JS animations (charts).** GraphWidgetLineChart (incl. `--catalog`) and the pie chart draw via `@react-spring/web` (`useAnimatedPath`/`useArcsTransition`, used by nivo), so they get captured mid-draw. - `Globals.assign({ skipAnimation: true })` from `@react-spring/web` (single hoisted instance → covers nivo), mirroring the existing `MotionGlobalConfig.skipAnimations`. - A global CSS rule zeroing animation/transition durations (belt-and-suspenders for the pre-capture window). - `@react-spring/web` added to `optimizeDeps.include` (next to `@nivo/*`) so importing it in the setup file doesn't trigger a mid-run Vite re-optimization. **2. Pre-warm lazy chunks.** RichTextFieldInput (BlockNote editor), AiChatMessage (`react-markdown`/`remark-gfm`), and AppNavigationDrawer (favorites/workspace section dispatchers) lazy-load behind `Suspense`; the snapshot could capture the skeleton fallback instead of the loaded content. Pre-warming the chunks at setup time (same pattern already used for the workflow-step mock) caches them before stories render. The settings object-about form was already covered by the framer-motion/CSS animation disable. --- .../twenty-front/.storybook/vitest.setup.ts | 22 +++++++++++++++++-- packages/twenty-front/vite.config.ts | 1 + 2 files changed, 21 insertions(+), 2 deletions(-) diff --git a/packages/twenty-front/.storybook/vitest.setup.ts b/packages/twenty-front/.storybook/vitest.setup.ts index c3d0fa7c70..de1f68906d 100644 --- a/packages/twenty-front/.storybook/vitest.setup.ts +++ b/packages/twenty-front/.storybook/vitest.setup.ts @@ -1,12 +1,30 @@ +import { Globals } from '@react-spring/web'; import { setProjectAnnotations } from '@storybook/react-vite'; import { MotionGlobalConfig } from 'framer-motion'; import * as projectAnnotations from './preview'; MotionGlobalConfig.skipAnimations = true; +Globals.assign({ skipAnimation: true }); -// Pre-warm the dynamic import used by WorkflowStepDecorator so the -// module is cached before any test runs (avoids flaky timeouts in CI). +const disableCssAnimationsStyle = document.createElement('style'); +disableCssAnimationsStyle.innerHTML = `*, *::before, *::after { + animation-duration: 0s !important; + animation-delay: 0s !important; + transition-duration: 0s !important; + transition-delay: 0s !important; +}`; +document.head.appendChild(disableCssAnimationsStyle); + +// Pre-warm the dynamic imports used by lazy() story components so the +// modules are cached before any test runs (avoids flaky timeouts and Argos +// screenshots that capture a Suspense skeleton instead of the loaded content). import('~/testing/utils/getTestEnrichedObjectMetadataItemsMock'); +import('react-markdown'); +import('remark-gfm'); +import('@/activities/components/ActivityRichTextEditor'); +import('@/object-record/record-field/ui/meta-types/input/components/RichTextFieldEditor'); +import('@/navigation-menu-item/display/sections/favorites/components/FavoritesSectionDispatcher'); +import('@/navigation-menu-item/display/sections/workspace/components/WorkspaceSectionDispatcher'); // This is an important step to apply the right configuration when testing your stories. // More info at: https://storybook.js.org/docs/api/portable-stories/portable-stories-vitest#setprojectannotations diff --git a/packages/twenty-front/vite.config.ts b/packages/twenty-front/vite.config.ts index 33d02e124b..5424e5c619 100644 --- a/packages/twenty-front/vite.config.ts +++ b/packages/twenty-front/vite.config.ts @@ -154,6 +154,7 @@ export default defineConfig(({ mode }) => { '@nivo/pie', '@nivo/line', '@nivo/arcs', + '@react-spring/web', 'd3-shape', ], },