Skip to content

fix(dev_server): keep workspace members out of the SSR dep optimizer - #370

Merged
mikn merged 1 commit into
mainfrom
mikn/dev-server-ssr-optimize-exclude
Oct 27, 2026
Merged

mikn merged 1 commit into
mainfrom
mikn/dev-server-ssr-optimize-exclude

Conversation

@mikn

@mikn mikn commented Oct 26, 2026

Copy link
Copy Markdown
Collaborator

A workspace member imported from server-side code still gets pre-bundled by the ssr (or a worker) environment's dep optimizer, so plugin transforms such as StyleX never run on it and the server render breaks at runtime.

  • Change: the generated ts_dev_server config's member-sources plugin adds the member exclude list to every non-client environment through Vite's configEnvironment hook. The top-level optimizeDeps.exclude stays for the client.
  • Goal: workspace members are served from source in every Vite environment, not only the client.
  • Evidence: with dep discovery on in ssr and a worker environment, the SSR transform of an entry importing a member pointed at vite-cache/deps_ssr/shared.js and deps_worker/shared.js before this change. After it, both point at the member's source file.
  • Risk and rollback: only non-client environments of dev servers with workspace members change; their optimizer cache rebuilds once because the exclude list feeds its hash. Revert the commit to roll back.
  • Merges next: this PR alone, nothing stacked. Once a consumer pins it, its manual ssr exclude line can go.

Problem and change

Vite 8 hands the top-level optimizeDeps to the environment named client only; every other environment starts from defaults. Worker and SSR framework plugins turn on dep discovery there, and a member then resolves to a pre-bundle. The hook returns a partial config, which Vite merges by concatenating arrays, so a consumer's own exclude list for that environment still applies. oj's server-environment pre-optimizer resolves the config through Vite itself, so it reads the same list.

A member that a plugin names in an environment's optimizeDeps.include is still pre-bundled there: Vite does not filter includes by exclude.

Tests

  • server_environment_optimizer_cannot_pre_bundle_a_workspace_member (behaviour test, Vite launcher): with discovery on in ssr and a worker environment, each environment's transform must import the member from source. It fails without the hook.

🤖 Generated with Claude Code

Vite applies the top-level optimizeDeps to the client environment only, so
the ssr environment and worker environments still pre-bundled workspace
members and plugin transforms never ran on them. The member-sources plugin
now adds the member exclude list to every non-client environment through
configEnvironment, which merges with a consumer's own list.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
@mikn
mikn merged commit 29eb8ce into main Oct 27, 2026
17 checks passed
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.

1 participant