Skip to content

Commit

Permalink
feat(resolve)!: allow removing conditions (#18395)
Browse files Browse the repository at this point in the history
Co-authored-by: Bjorn Lu <[email protected]>
Co-authored-by: patak <[email protected]>
  • Loading branch information
3 people authored Oct 31, 2024
1 parent 887ce8b commit d002e7d
Show file tree
Hide file tree
Showing 23 changed files with 158 additions and 197 deletions.
5 changes: 4 additions & 1 deletion docs/config/shared-options.md
Original file line number Diff line number Diff line change
Expand Up @@ -117,6 +117,7 @@ For SSR builds, deduplication does not work for ESM build outputs configured fro
## resolve.conditions
- **Type:** `string[]`
- **Default:** `['module', 'browser', 'development|production']`
Additional allowed conditions when resolving [Conditional Exports](https://nodejs.org/api/packages.html#packages_conditional_exports) from a package.
Expand All @@ -135,7 +136,9 @@ A package with conditional exports may have the following `exports` field in its

Here, `import` and `require` are "conditions". Conditions can be nested and should be specified from most specific to least specific.

Vite has a list of "allowed conditions" and will match the first condition that is in the allowed list. The default allowed conditions are: `import`, `module`, `browser`, `default`, and `production/development` based on current mode. The `resolve.conditions` config option allows specifying additional allowed conditions.
`development|production` is a special value that is replaced with `production` or `development` depending on the value of `process.env.NODE_ENV`. It is replaced with `production` when `process.env.NODE_ENV === 'production'` and `development` otherwise.

Note that `import`, `require`, `default` conditions are always applied if the requirements are met.

:::warning Resolving subpath exports
Export keys ending with "/" is deprecated by Node and may not work well. Please contact the package author to use [`*` subpath patterns](https://nodejs.org/api/packages.html#package-entry-points) instead.
Expand Down
5 changes: 2 additions & 3 deletions docs/config/ssr-options.md
Original file line number Diff line number Diff line change
Expand Up @@ -34,15 +34,14 @@ Build target for the SSR server.
## ssr.resolve.conditions

- **Type:** `string[]`
- **Default:** `['module', 'node', 'development|production']` (`['module', 'browser', 'development|production']` for `ssr.target === 'webworker'`)
- **Related:** [Resolve Conditions](./shared-options.md#resolve-conditions)

Defaults to the root [`resolve.conditions`](./shared-options.md#resolve-conditions).

These conditions are used in the plugin pipeline, and only affect non-externalized dependencies during the SSR build. Use `ssr.resolve.externalConditions` to affect externalized imports.

## ssr.resolve.externalConditions

- **Type:** `string[]`
- **Default:** `[]`
- **Default:** `['node']`

Conditions that are used during ssr import (including `ssrLoadModule`) of externalized dependencies.
17 changes: 17 additions & 0 deletions docs/guide/migration.md
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,23 @@ The experimental Vite Runtime API evolved into the Module Runner API, released i

## General Changes

### Default value for `resolve.conditions`

This change does not affect users that did not configure [`resolve.conditions`](/config/shared-options#resolve-conditions) / [`ssr.resolve.conditions`](/config/ssr-options#ssr-resolve-conditions) / [`ssr.resolve.externalConditions`](/config/ssr-options#ssr-resolve-externalconditions).

In Vite 5, the default value for `resolve.conditions` was `[]` and some conditions were added internally. The default value for `ssr.resolve.conditions` was the value of `resolve.conditions`.

From Vite 6, some of the conditions are no longer added internally and need to be included in the config values.
The conditions that are no longer added internally for

- `resolve.conditions` are `['module', 'browser', 'development|production']`
- `ssr.resolve.conditions` are `['module', 'node', 'development|production']`

The default values for those options are updated to the corresponding values and `ssr.resolve.conditions` no longer uses `resolve.conditions` as the default value. Note that `development|production` is a special variable that is replaced with `production` or `development` depending on the value of `process.env.NODE_ENV`.

If you specified a custom value for `resolve.conditions` or `ssr.resolve.conditions`, you need to update it to include the new conditions.
For example, if you previously specified `['custom']` for `resolve.conditions`, you need to specify `['custom', 'module', 'browser', 'development|production']` instead.

### JSON stringify

In Vite 5, when [`json.stringify: true`](/config/shared-options#json-stringify) is set, [`json.namedExports`](/config/shared-options#json-namedexports) was disabled.
Expand Down
94 changes: 14 additions & 80 deletions packages/vite/src/node/__tests__/environment.spec.ts
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@ describe('custom environment conditions', () => {
ws: false,
},
environments: {
// no web / default
// default
ssr: {
resolve: {
noExternal,
Expand All @@ -36,9 +36,8 @@ describe('custom environment conditions', () => {
},
},
},
// web / worker
// worker
worker: {
webCompatible: true,
resolve: {
noExternal,
conditions: ['worker'],
Expand All @@ -54,9 +53,8 @@ describe('custom environment conditions', () => {
},
},
},
// web / custom1
// custom1
custom1: {
webCompatible: true,
resolve: {
noExternal,
conditions: ['custom1'],
Expand All @@ -72,54 +70,17 @@ describe('custom environment conditions', () => {
},
},
},
// no web / custom2
custom2: {
webCompatible: false,
// same as custom1
custom1_2: {
resolve: {
noExternal,
conditions: ['custom2'],
externalConditions: ['custom2'],
},
build: {
outDir: path.join(
import.meta.dirname,
'fixtures/test-dep-conditions/dist/custom2',
),
rollupOptions: {
input: { index: '@vitejs/test-dep-conditions' },
},
},
},
// no web / custom3
custom3: {
webCompatible: false,
resolve: {
noExternal,
conditions: ['custom3'],
externalConditions: ['custom3'],
},
build: {
outDir: path.join(
import.meta.dirname,
'fixtures/test-dep-conditions/dist/custom3',
),
rollupOptions: {
input: { index: '@vitejs/test-dep-conditions' },
},
},
},
// same as custom3
custom3_2: {
webCompatible: false,
resolve: {
noExternal,
conditions: ['custom3'],
externalConditions: ['custom3'],
conditions: ['custom1'],
externalConditions: ['custom1'],
},
build: {
outDir: path.join(
import.meta.dirname,
'fixtures/test-dep-conditions/dist/custom3_2',
'fixtures/test-dep-conditions/dist/custom1_2',
),
rollupOptions: {
input: { index: '@vitejs/test-dep-conditions' },
Expand All @@ -135,14 +96,7 @@ describe('custom environment conditions', () => {
onTestFinished(() => server.close())

const results: Record<string, unknown> = {}
for (const key of [
'ssr',
'worker',
'custom1',
'custom2',
'custom3',
'custom3_2',
]) {
for (const key of ['ssr', 'worker', 'custom1', 'custom1_2']) {
const runner = createServerModuleRunner(server.environments[key], {
hmr: {
logger: false,
Expand All @@ -155,9 +109,7 @@ describe('custom environment conditions', () => {
expect(results).toMatchInlineSnapshot(`
{
"custom1": "index.custom1.js",
"custom2": "index.custom2.js",
"custom3": "index.custom3.js",
"custom3_2": "index.custom3.js",
"custom1_2": "index.custom1.js",
"ssr": "index.default.js",
"worker": "index.worker.js",
}
Expand All @@ -169,14 +121,7 @@ describe('custom environment conditions', () => {
onTestFinished(() => server.close())

const results: Record<string, unknown> = {}
for (const key of [
'ssr',
'worker',
'custom1',
'custom2',
'custom3',
'custom3_2',
]) {
for (const key of ['ssr', 'worker', 'custom1', 'custom1_2']) {
const runner = createServerModuleRunner(server.environments[key], {
hmr: {
logger: false,
Expand All @@ -191,9 +136,7 @@ describe('custom environment conditions', () => {
expect(results).toMatchInlineSnapshot(`
{
"custom1": "index.custom1.js",
"custom2": "index.custom2.js",
"custom3": "index.custom3.js",
"custom3_2": "index.custom3.js",
"custom1_2": "index.custom1.js",
"ssr": "index.default.js",
"worker": "index.worker.js",
}
Expand Down Expand Up @@ -222,14 +165,7 @@ describe('custom environment conditions', () => {
test('build', async () => {
const builder = await createBuilder(getConfig({ noExternal: true }))
const results: Record<string, unknown> = {}
for (const key of [
'ssr',
'worker',
'custom1',
'custom2',
'custom3',
'custom3_2',
]) {
for (const key of ['ssr', 'worker', 'custom1', 'custom1_2']) {
const output = await builder.build(builder.environments[key])
const chunk = (output as RollupOutput).output[0]
const mod = await import(
Expand All @@ -245,9 +181,7 @@ describe('custom environment conditions', () => {
expect(results).toMatchInlineSnapshot(`
{
"custom1": "index.custom1.js",
"custom2": "index.custom2.js",
"custom3": "index.custom3.js",
"custom3_2": "index.custom3.js",
"custom1_2": "index.custom1.js",
"ssr": "index.default.js",
"worker": "index.worker.js",
}
Expand Down

This file was deleted.

This file was deleted.

Original file line number Diff line number Diff line change
Expand Up @@ -6,8 +6,6 @@
".": {
"style": "./index.css",
"custom1": "./index.custom1.js",
"custom2": "./index.custom2.js",
"custom3": "./index.custom3.js",
"worker": "./index.worker.js",
"browser": "./index.browser.js",
"default": "./index.default.js"
Expand Down
1 change: 0 additions & 1 deletion packages/vite/src/node/baseEnvironment.ts
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,6 @@ export function getDefaultResolvedEnvironmentOptions(
define: config.define,
resolve: config.resolve,
consumer: 'server',
webCompatible: false,
optimizeDeps: config.optimizeDeps,
dev: config.dev,
build: config.build,
Expand Down
23 changes: 17 additions & 6 deletions packages/vite/src/node/build.ts
Original file line number Diff line number Diff line change
Expand Up @@ -348,6 +348,8 @@ export function resolveBuildEnvironmentOptions(
raw: BuildEnvironmentOptions,
logger: Logger,
consumer: 'client' | 'server' | undefined,
// Backward compatibility
isSsrTargetWebworkerEnvironment?: boolean,
): ResolvedBuildEnvironmentOptions {
const deprecatedPolyfillModulePreload = raw?.polyfillModulePreload
const { polyfillModulePreload, ...rest } = raw
Expand Down Expand Up @@ -444,6 +446,19 @@ export function resolveBuildEnvironmentOptions(
resolved.cssMinify = consumer === 'server' ? 'esbuild' : !!resolved.minify
}

if (isSsrTargetWebworkerEnvironment) {
resolved.rollupOptions ??= {}
resolved.rollupOptions.output ??= {}
const output = resolved.rollupOptions.output
for (const out of arraify(output)) {
out.entryFileNames ??= `[name].js`
out.chunkFileNames ??= `[name]-[hash].js`
const input = resolved.rollupOptions.input
out.inlineDynamicImports ??=
!input || typeof input === 'string' || Object.keys(input).length === 1
}
}

return resolved
}

Expand Down Expand Up @@ -692,7 +707,7 @@ async function buildEnvironment(

const format = output.format || 'es'
const jsExt =
!environment.config.webCompatible || libOptions
environment.config.consumer === 'server' || libOptions
? resolveOutputJsExtension(
format,
findNearestPackageData(root, packageCache)?.data.type,
Expand Down Expand Up @@ -730,11 +745,7 @@ async function buildEnvironment(
? `[name].[ext]`
: path.posix.join(options.assetsDir, `[name]-[hash].[ext]`),
inlineDynamicImports:
output.format === 'umd' ||
output.format === 'iife' ||
(environment.config.consumer === 'server' &&
environment.config.webCompatible &&
(typeof input === 'string' || Object.keys(input).length === 1)),
output.format === 'umd' || output.format === 'iife',
...output,
}
}
Expand Down
Loading

0 comments on commit d002e7d

Please sign in to comment.