@@ -92,24 +92,25 @@ const _require = createRequire(import.meta.url)
92
92
93
93
const isSsrExternalCache = new WeakMap <
94
94
ResolvedConfig ,
95
- ( id : string ) => boolean | undefined
95
+ ( id : string , importer ?: string ) => boolean | undefined
96
96
> ( )
97
97
98
98
export function shouldExternalizeForSSR (
99
99
id : string ,
100
+ importer : string | undefined ,
100
101
config : ResolvedConfig ,
101
102
) : boolean | undefined {
102
103
let isSsrExternal = isSsrExternalCache . get ( config )
103
104
if ( ! isSsrExternal ) {
104
105
isSsrExternal = createIsSsrExternal ( config )
105
106
isSsrExternalCache . set ( config , isSsrExternal )
106
107
}
107
- return isSsrExternal ( id )
108
+ return isSsrExternal ( id , importer )
108
109
}
109
110
110
111
export function createIsConfiguredAsSsrExternal (
111
112
config : ResolvedConfig ,
112
- ) : ( id : string ) => boolean {
113
+ ) : ( id : string , importer ?: string ) => boolean {
113
114
const { ssr, root } = config
114
115
const noExternal = ssr ?. noExternal
115
116
const noExternalFilter =
@@ -126,6 +127,7 @@ export function createIsConfiguredAsSsrExternal(
126
127
127
128
const isExternalizable = (
128
129
id : string ,
130
+ importer ?: string ,
129
131
configuredAsExternal ?: boolean ,
130
132
) : boolean => {
131
133
if ( ! bareImportRE . test ( id ) || id . includes ( '\0' ) ) {
@@ -134,7 +136,9 @@ export function createIsConfiguredAsSsrExternal(
134
136
try {
135
137
return ! ! tryNodeResolve (
136
138
id ,
137
- undefined ,
139
+ // Skip passing importer in build to avoid externalizing non-hoisted dependencies
140
+ // unresolveable from root (which would be unresolvable from output bundles also)
141
+ config . command === 'build' ? undefined : importer ,
138
142
resolveOptions ,
139
143
ssr ?. target === 'webworker' ,
140
144
undefined ,
@@ -157,7 +161,7 @@ export function createIsConfiguredAsSsrExternal(
157
161
158
162
// Returns true if it is configured as external, false if it is filtered
159
163
// by noExternal and undefined if it isn't affected by the explicit config
160
- return ( id : string ) => {
164
+ return ( id : string , importer ?: string ) => {
161
165
const { ssr } = config
162
166
if ( ssr ) {
163
167
if (
@@ -169,14 +173,14 @@ export function createIsConfiguredAsSsrExternal(
169
173
}
170
174
const pkgName = getNpmPackageName ( id )
171
175
if ( ! pkgName ) {
172
- return isExternalizable ( id )
176
+ return isExternalizable ( id , importer )
173
177
}
174
178
if (
175
179
// A package name in ssr.external externalizes every
176
180
// externalizable package entry
177
181
ssr . external ?. includes ( pkgName )
178
182
) {
179
- return isExternalizable ( id , true )
183
+ return isExternalizable ( id , importer , true )
180
184
}
181
185
if ( typeof noExternal === 'boolean' ) {
182
186
return ! noExternal
@@ -185,24 +189,24 @@ export function createIsConfiguredAsSsrExternal(
185
189
return false
186
190
}
187
191
}
188
- return isExternalizable ( id )
192
+ return isExternalizable ( id , importer )
189
193
}
190
194
}
191
195
192
196
function createIsSsrExternal (
193
197
config : ResolvedConfig ,
194
- ) : ( id : string ) => boolean | undefined {
198
+ ) : ( id : string , importer ?: string ) => boolean | undefined {
195
199
const processedIds = new Map < string , boolean | undefined > ( )
196
200
197
201
const isConfiguredAsExternal = createIsConfiguredAsSsrExternal ( config )
198
202
199
- return ( id : string ) => {
203
+ return ( id : string , importer ?: string ) => {
200
204
if ( processedIds . has ( id ) ) {
201
205
return processedIds . get ( id )
202
206
}
203
207
let external = false
204
208
if ( id [ 0 ] !== '.' && ! path . isAbsolute ( id ) ) {
205
- external = isBuiltin ( id ) || isConfiguredAsExternal ( id )
209
+ external = isBuiltin ( id ) || isConfiguredAsExternal ( id , importer )
206
210
}
207
211
processedIds . set ( id , external )
208
212
return external
0 commit comments