From 8e69a7976379910ea417e6565ca44397e4a3d2e2 Mon Sep 17 00:00:00 2001 From: Charan Rathore <141534082+charan-rathore@users.noreply.github.com> Date: Sat, 26 Sep 2026 13:16:07 +0530 Subject: [PATCH 1/2] fix: keep browser:false modules empty in dependency optimizer --- .../vite/src/node/optimizer/rolldownDepPlugin.ts | 10 ++++++++++ .../optimize-deps/__tests__/optimize-deps.spec.ts | 14 ++++++++++++++ .../optimize-deps/dep-browser-false/index.js | 4 ++++ .../optimize-deps/dep-browser-false/package.json | 9 +++++++++ playground/optimize-deps/index.html | 6 ++++++ playground/optimize-deps/package.json | 1 + pnpm-lock.yaml | 10 ++++++++++ 7 files changed, 54 insertions(+) create mode 100644 playground/optimize-deps/dep-browser-false/index.js create mode 100644 playground/optimize-deps/dep-browser-false/package.json diff --git a/packages/vite/src/node/optimizer/rolldownDepPlugin.ts b/packages/vite/src/node/optimizer/rolldownDepPlugin.ts index 07d8cab4566b40..3ee461584aea35 100644 --- a/packages/vite/src/node/optimizer/rolldownDepPlugin.ts +++ b/packages/vite/src/node/optimizer/rolldownDepPlugin.ts @@ -58,6 +58,7 @@ const externalTypes = [ const optionalPeerDepNamespace = 'optional-peer-dep:' const browserExternalNamespace = 'browser-external:' +const browserExternalEmptyNamespace = 'browser-external-empty:' export function rolldownDepPlugin( environment: Environment, @@ -121,6 +122,11 @@ export function rolldownDepPlugin( } const resolveResult = (id: string, resolved: string, kind: ImportKind) => { + // An exact browser-external id is an explicit browser:false mapping. + // Suffixed ids are unsupported Node builtins and still need the warning. + if (resolved === browserExternalId) { + return { id: browserExternalEmptyNamespace + id } + } if (resolved.startsWith(browserExternalId)) { return { id: browserExternalNamespace + id, @@ -255,11 +261,15 @@ export function rolldownDepPlugin( load: { filter: { id: [ + prefixRegex(browserExternalEmptyNamespace), prefixRegex(browserExternalNamespace), prefixRegex(optionalPeerDepNamespace), ], }, handler(id) { + if (id.startsWith(browserExternalEmptyNamespace)) { + return { code: 'module.exports = {}' } + } if (id.startsWith(browserExternalNamespace)) { const path = id.slice(browserExternalNamespace.length) if (isProduction) { diff --git a/playground/optimize-deps/__tests__/optimize-deps.spec.ts b/playground/optimize-deps/__tests__/optimize-deps.spec.ts index d6febaafad2c17..7754b0e1887e27 100644 --- a/playground/optimize-deps/__tests__/optimize-deps.spec.ts +++ b/playground/optimize-deps/__tests__/optimize-deps.spec.ts @@ -255,6 +255,20 @@ test('non optimized module is not duplicated', async () => { .toBe('from-absolute-path, from-relative-path') }) +test.runIf(isServe)( + 'optimized browser:false is empty without warning', + async () => { + expect(await page.textContent('.browser-false-optimized')).toBe('[success]') + expect(browserLogs).not.toEqual( + expect.arrayContaining([ + expect.stringContaining( + 'Module "browser-false-only" has been externalized for browser compatibility', + ), + ]), + ) + }, +) + test.runIf(isServe)('error on builtin modules usage', () => { expect(browserLogs).toEqual( expect.arrayContaining([ diff --git a/playground/optimize-deps/dep-browser-false/index.js b/playground/optimize-deps/dep-browser-false/index.js new file mode 100644 index 00000000000000..2c7cc4dea71645 --- /dev/null +++ b/playground/optimize-deps/dep-browser-false/index.js @@ -0,0 +1,4 @@ +// An explicit browser:false mapping is an empty module, not a Node builtin warning. +// eslint-disable-next-line n/no-missing-require -- mapped to false by package browser field +const fs = require('browser-false-only') +module.exports = fs.readFileSync === undefined ? '[success]' : '[fail]' diff --git a/playground/optimize-deps/dep-browser-false/package.json b/playground/optimize-deps/dep-browser-false/package.json new file mode 100644 index 00000000000000..57732ee0c5f41c --- /dev/null +++ b/playground/optimize-deps/dep-browser-false/package.json @@ -0,0 +1,9 @@ +{ + "name": "@vitejs/test-dep-browser-false", + "private": true, + "version": "0.0.0", + "main": "index.js", + "browser": { + "browser-false-only": false + } +} diff --git a/playground/optimize-deps/index.html b/playground/optimize-deps/index.html index 2e3b6607dabff7..6f351818c61a1b 100644 --- a/playground/optimize-deps/index.html +++ b/playground/optimize-deps/index.html @@ -336,6 +336,12 @@
[pending]
+ +