Skip to content

Upgrade build tooling to Vite 8 - #4038

Merged
GiantRobots merged 19 commits into
mainfrom
vite8
Oct 20, 2026
Merged

GiantRobots merged 19 commits into
mainfrom
vite8

Conversation

@GiantRobots

@GiantRobots GiantRobots commented Oct 15, 2026 •

Copy link
Copy Markdown
Collaborator

Why

Upgrade Temporal UI from Vite 6 to Vite 8 while preserving product behavior and the existing browser support floor. This also removes the existing Vitest peer mismatch and validates the Rolldown/Oxc toolchain before adopting it.

Tracking: FE-1147

What changed

Change Reason
Vite 6 → 8.3.4 and plugin-Svelte 6 → 7.3.1 Adopt the Rolldown/Oxc toolchain with compatible Svelte integration.
Vitest/UI/coverage → 4.1.11 Add Vite 8 support and remove the previous Vitest peer mismatch.
@types/node 18 → 22.18.0 Match the repository’s Node 22 runtime and current peer ranges.
Preserve Chrome 87, Edge 88, Firefox 78, and Safari 14 build targets Avoid silently raising the existing browser support floor.
esbuild override 0.25 → 0.28.2 Satisfy Vite 8’s optional peer range and keep Storybook tooling aligned.
Migrate test configuration and mocks for Vite 8/Vitest 4 Replace removed options while preserving test behavior.
Harden the packed catalog consumer test Verify a clean external consumer installs and builds the package on Vite 8.

No production component, page, service, or route implementation changed. Dependency/config changes are global, so every route was included in validation.

Validation

Automated behavior

  • Unit: 289 files, 3,785 passed, 2 skipped.
  • Coverage: 74.27% statements / 71.14% branches / 60.92% functions / 76.46% lines.
  • Playwright: 401 integration tests passed (1 skipped); 37 E2E tests passed (5 skipped).
  • Vite 6 vs Vite 8 A/B:
    • 75/75 direct route, redirect, error, and endpoint entries matched.
    • 74/74 applicable SvelteKit client navigations matched (/render is server-only).
    • Zero behavioral, request, DOM, accessibility, console, redirect, or screenshot differences after normalizing approved minified stack details.
  • Package boundary: a clean external consumer installs the packed UI and builds on Vite 8.
  • Linux: current-head GitHub checks pass on ubuntu-latest for lint, types, unit, integration, E2E, and server tests.

Build outputs

All static, Docker, embedded-server, Vercel, package, Storybook, and catalog outputs build successfully and have provenance-bound inventories.

Output Raw Gzip Brotli
Static/Docker/server -2.15% about -3.4% about -3.2%
Vercel -1.32% -2.44% -2.35%
Package +0.002% +0.003% +0.003%
Storybook +0.36% +0.06% +0.89%

No compressed output exceeds the 5% investigation threshold.

Development/runtime smoke tests

  • Full ui-server mode rendered successfully.
  • Cross-family client navigation preserved browser state.
  • Svelte markup and CSS HMR updated without a full reload.
  • with-auth reached the local OIDC sign-in page.
  • Catalog list/detail rendered, worker readiness passed, and the hello example completed.
  • Go server build/race tests, catalog verification, and GitHub automation tests passed.

Known non-blocking items

  • Vite warns that extensionless config imports and __dirname are incompatible with a future native config-loader default. Vite 8's current bundled loader works; handle before a future major.
  • Rolldown tolerates top-level await in SvelteKit SSR utilities. The server runs on Node 22, which supports it; server builds and E2E pass.
  • Existing Svelte state_referenced_locally warnings predate this migration and should be handled as component-level cleanup.
  • Exact historical Chrome/Firefox/Safari binaries were unavailable; build targets are preserved and current Chromium/Linux CI is green.
  • Existing Storybook accessibility failures and standalone accessibility HAR timeouts reproduce unchanged on Vite 6.

Reviewer commands

pnpm install --frozen-lockfile --strict-peer-dependencies
pnpm lint
pnpm check
pnpm test --run
pnpm test:coverage
pnpm build:local
pnpm catalog:test-package
pnpm test:integration
pnpm test:e2e

Checklist

  • Manual development/HMR/auth/catalog validation
  • Unit, coverage, integration, and E2E validation
  • Vite 6 versus Vite 8 route and build A/B
  • Linux CI green on the current PR head

GiantRobots and others added 16 commits October 14, 2026 20:27
Add an exhaustive route manifest, archived preview runtime, artifact inventories, and strict Vite baseline/candidate parity collection before changing the toolchain.

Constraint: Cover all 61 page routes, 12 load-only routes, the error boundary, and /render

Confidence: high

Scope-risk: narrow
Co-authored-by: Cursor <cursoragent@cursor.com>
Vite 8 and Vitest 4 require Node 20/22+ type definitions, and the repository runtime is Node 22.18.0.

Constraint: Keep runtime packages unchanged

Confidence: high

Scope-risk: narrow
Co-authored-by: Cursor <cursoragent@cursor.com>
Align Vitest, its UI, and V8 coverage provider for Vite 8 support. Migrate removed config and stricter constructor/module mock semantics without changing product behavior or assertions.

Constraint: Keep Vite 6.4.3 during this prerequisite checkpoint

Confidence: high

Scope-risk: moderate
Co-authored-by: Cursor <cursoragent@cursor.com>
Pin Vite's current Chrome 87, Edge 88, Firefox 78, and Safari 14 defaults before later Vite majors raise them.

Constraint: Do not reduce the browserslist support floor

Confidence: high

Scope-risk: broad
Co-authored-by: Cursor <cursoragent@cursor.com>
Apply the Vite 6-to-7 checkpoint before changing bundlers, while retaining plugin-Svelte 6 and the existing browser floor.

Constraint: Isolate Vite API changes from Rolldown changes

Confidence: high

Scope-risk: broad
Co-authored-by: Cursor <cursoragent@cursor.com>
Alias Vite 7.2.2 to rolldown-vite so bundler-specific behavior is isolated before the Vite 8 and plugin-Svelte 7 upgrade.

Constraint: Do not add optimizer or interop workarounds without a failing reproduction

Confidence: high

Scope-risk: broad
Co-authored-by: Cursor <cursoragent@cursor.com>
Keep raw console stacks in evidence while comparing approved errors by stable classification so bundler minification does not create false A/B failures.

Constraint: Unexpected console errors still fail route evidence

Confidence: high

Scope-risk: narrow
Co-authored-by: Cursor <cursoragent@cursor.com>
Raise the global esbuild override to the supported 0.28 line so Vite 8 does not resolve its optional peer to unsupported 0.25.x.

Constraint: Preserve one security-controlled esbuild version across Storybook and tooling

Confidence: high

Scope-risk: moderate
Co-authored-by: Cursor <cursoragent@cursor.com>
Move to Vite 8 and plugin-Svelte 7 atomically, remove the temporary Rolldown alias, migrate removed plugin hot options, and validate the clean catalog consumer against the target toolchain.

Constraint: Preserve existing browser targets and product behavior

Confidence: high

Scope-risk: broad
Co-authored-by: Cursor <cursoragent@cursor.com>
Keep the synthetic clean-consumer package aligned with catalog component imports so its Vite 8 build validates the actual package boundary.

Constraint: Test fixture only; no published source behavior change

Confidence: high

Scope-risk: narrow
Co-authored-by: Cursor <cursoragent@cursor.com>
Use inert config-time defaults so Knip and Playwright listing can load the migration config while runtime setup continues to require full provenance.

Confidence: high

Scope-risk: narrow
Co-authored-by: Cursor <cursoragent@cursor.com>
Allow evidence inventories to create their parent directories while retaining exclusive archive writes.

Confidence: high

Scope-risk: narrow
Co-authored-by: Cursor <cursoragent@cursor.com>
Exclude ignored archives from Vitest discovery, bind artifact matrices to commit and lock provenance, and record research, dependency scope, route impact, validation results, and residual risks.

Constraint: Preserve raw generated evidence outside git while keeping aggregate results reproducible

Confidence: high

Scope-risk: narrow
Co-authored-by: Cursor <cursoragent@cursor.com>
Exercise real SvelteKit navigation for all 74 applicable route entries, preserve existing family interactions, and fail on missing or differing client-side outcomes.

Constraint: Only /render is exempt as a server response

Confidence: high

Scope-risk: narrow
Co-authored-by: Cursor <cursoragent@cursor.com>
Record reproducible provenance, current coverage, exhaustive client navigation, direct development/HMR assertions, and the accepted SSR top-level-await warning.

Confidence: high

Scope-risk: narrow
Co-authored-by: Cursor <cursoragent@cursor.com>
Record the historical baseline provenance algorithm and current final test counts so the exhaustive route evidence is reproducible.

Confidence: high

Scope-risk: narrow
Co-authored-by: Cursor <cursoragent@cursor.com>
@GiantRobots
GiantRobots requested a review from a team as a code owner October 15, 2026 14:53
@vercel

vercel Bot commented Oct 15, 2026 •

Copy link
Copy Markdown

The latest updates on your projects. Learn more about Vercel for GitHub.

Project Deployment Actions Updated
holocene Ready Ready Preview Oct 20, 2026 5:17pm UTC

Request Review

@GraceGardner GraceGardner left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

:)

@tegan-temporal

Copy link
Copy Markdown
Contributor

do we need to commit the scripts? I feel like once this merges we don't have a need for them anymore?

const dateTimeFormatSpy = vi
.spyOn(global.Intl, 'DateTimeFormat')
.mockImplementation((_, options) => {
.mockImplementation(function (_, options) {

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

not a blocker, but I'm curious was this required for some reason?

Copy link
Copy Markdown
Collaborator Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Because the production code does this:

new Intl.DateTimeFormat(...)

The spy replaces Intl.DateTimeFormat, so its implementation must also be constructible. JavaScript arrow functions cannot
be constructors:

new (() => {}); // TypeError
new (function () {})(); // valid

Arrow functions have lexical this and no constructor capability. Vitest 4 preserves that distinction more strictly;
Vitest 3’s mock wrapper previously hid it.

https://v4.vitest.dev/guide/migration#spyon-and-fn-support-constructors

@GiantRobots GiantRobots changed the title Vite8 Upgrade build tooling to Vite 8 Oct 20, 2026
@GiantRobots
GiantRobots merged commit 25a9847 into main Oct 20, 2026
19 checks passed
@GiantRobots
GiantRobots deleted the vite8 branch October 20, 2026 19:33
rossnelson added a commit that referenced this pull request Oct 21, 2026
Auto-generated version bump from 2.56.0 to 2.57.0

Bump type: minor
go.temporal.io/api: upgraded since last version (minimum minor)

Changes included:
- [`e15c805a`](e15c805) fix(nexus): show error alert when starting a standalone Nexus operation fails (FE-1083) (#4026)
- [`dad76961`](dad7696) feat(io): add button and button-link components (FE-1090) (#4028)
- [`8ecbc7e5`](8ecbc7e) Add tooltip to truncated filter chips (#4034)
- [`2a687175`](2a68717) Allow text selection in workflow descriptions in relationships (#4035)
- [`4c440b26`](4c440b2) refactor(io): centralize chip and badge styling (FE-1095) (#4029)
- [`beccfa52`](beccfa5) Reuse badge styling and grouped corners for tags (FE-1093) (#4030)
- [`e6cece8e`](e6cece8) Add reusable native select with custom arrow styling (#4036)
- [`40108cfc`](40108cf) Dependency Inject Authz decisions through the provider (#4031)
- [`ea31abca`](ea31abc) Add persistent environment banner with preset colors (#4039)
- [`bd5c6600`](bd5c660) Fix timeline summary typography (#4043)
- [`0ad513c2`](0ad513c) fix(schedules): preserve existing headers when editing (#4051)
- [`7eb3a834`](7eb3a83) Hide focus outline on main content landmark (#4052)
- [`0ee98978`](0ee9897) Add client-side sorting to API-paginated tables (#4037)
- [`c80a75e8`](c80a75e) Wrap long link values in expanded event details (#4053)
- [`51606c50`](51606c5) Remove trailing space inside Link (#4054)
- [`23e6c4d1`](23e6c4d) Improve sorting performance for large workflow tables (#4055)
- [`45015193`](4501519) [FE-1026] Cache immutable self-hosted UI assets (#4011)
- [`25a98476`](25a9847) Upgrade build tooling to Vite 8 (#4038)
- [`b911d0a6`](b911d0a) [FE-1026] Cache immutable 304 assets (#4056)
- [`fa6e6ccc`](fa6e6cc) Bump go.temporal.io/api to v1.64.0 in the server (#4059)
- [`a654962e`](a654962) Bump Node to 22.23.4 and Go to 1.26.10 for security fixes (#4058)

Co-authored-by: rossnelson <146089+rossnelson@users.noreply.github.com>

This branch was successfully deployed

1 active deployment
Preview — e4665a59 Deployed Oct 20, 2026 by vercel[bot]
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants