@@ -161,12 +161,17 @@ type EnvBase = {
161161 // Landed in npm v11.2.0.
162162 npmBuggyOverrides : boolean
163163 }
164+ nodeSupported : boolean
165+ nodeVersion : SemVer
164166 npmExecPath : string
165- pkgSupported : boolean
166167 pkgRequirements : {
167168 agent : string
168169 node : string
169170 }
171+ pkgSupports : {
172+ agent : boolean
173+ node : boolean
174+ }
170175}
171176
172177export type EnvDetails = Readonly <
@@ -262,25 +267,30 @@ export async function detectPackageEnvironment({
262267 // Lazily access constants.minimumVersionByAgent.
263268 const minSupportedAgentVersion = constants . minimumVersionByAgent . get ( agent ) !
264269 const minSupportedNodeVersion = maintainedNodeVersions . last
270+ const nodeVersion = semver . coerce ( process . version ) !
265271 let lockSrc : string | undefined
272+ let pkgAgentRange : string | undefined
273+ let pkgNodeRange : string | undefined
266274 let pkgMinAgentVersion = minSupportedAgentVersion
267275 let pkgMinNodeVersion = minSupportedNodeVersion
268276 if ( pkgJson ) {
269277 const { engines } = pkgJson
270- const agentRange = engines ?. [ agent ]
271- const nodeRange = engines ?. [ 'node' ]
272- if ( isNonEmptyString ( agentRange ) ) {
278+ const engineAgentRange = engines ?. [ agent ]
279+ const engineNodeRange = engines ?. [ 'node' ]
280+ if ( isNonEmptyString ( engineAgentRange ) ) {
281+ pkgAgentRange = engineAgentRange
273282 // Roughly check agent range as semver.coerce will strip leading
274283 // v's, carets (^), comparators (<,<=,>,>=,=), and tildes (~).
275- const coerced = semver . coerce ( agentRange )
284+ const coerced = semver . coerce ( pkgAgentRange )
276285 if ( coerced && semver . lt ( coerced , pkgMinAgentVersion ) ) {
277286 pkgMinAgentVersion = coerced . version
278287 }
279288 }
280- if ( isNonEmptyString ( nodeRange ) ) {
289+ if ( isNonEmptyString ( engineNodeRange ) ) {
290+ pkgNodeRange = engineNodeRange
281291 // Roughly check Node range as semver.coerce will strip leading
282292 // v's, carets (^), comparators (<,<=,>,>=,=), and tildes (~).
283- const coerced = semver . coerce ( nodeRange )
293+ const coerced = semver . coerce ( pkgNodeRange )
284294 if ( coerced && semver . lt ( coerced , pkgMinNodeVersion ) ) {
285295 pkgMinNodeVersion = coerced . version
286296 }
@@ -313,13 +323,11 @@ export async function detectPackageEnvironment({
313323 ! ! agentVersion &&
314324 semver . satisfies ( agentVersion , `>=${ minSupportedAgentVersion } ` )
315325
316- // Does our minimum supported agent version meet the package's requirements?
317- // Does our supported Node versions meet the package's requirements?
318- const pkgSupported =
319- semver . satisfies ( minSupportedAgentVersion , `>=${ pkgMinAgentVersion } ` ) &&
320- maintainedNodeVersions . some ( v =>
321- semver . satisfies ( v , `>=${ pkgMinNodeVersion } ` )
322- )
326+ // Does the system Node version meet our minimum supported Node version?
327+ const nodeSupported = semver . satisfies (
328+ nodeVersion ,
329+ `>=${ minSupportedNodeVersion } `
330+ )
323331
324332 const npmBuggyOverrides =
325333 agent === NPM &&
@@ -335,13 +343,25 @@ export async function detectPackageEnvironment({
335343 lockName,
336344 lockPath,
337345 lockSrc,
346+ nodeSupported,
347+ nodeVersion,
338348 npmExecPath,
339349 pkgJson : editablePkgJson ,
340350 pkgPath,
341- pkgSupported,
342351 pkgRequirements : {
343- agent : `>=${ pkgMinAgentVersion } ` ,
344- node : `>=${ pkgMinNodeVersion } `
352+ agent : pkgAgentRange ?? `>=${ pkgMinAgentVersion } ` ,
353+ node : pkgNodeRange ?? `>=${ pkgMinNodeVersion } `
354+ } ,
355+ pkgSupports : {
356+ // Does our minimum supported agent version meet the package's requirements?
357+ agent : semver . satisfies (
358+ minSupportedAgentVersion ,
359+ `>=${ pkgMinAgentVersion } `
360+ ) ,
361+ // Does our supported Node versions meet the package's requirements?
362+ node : maintainedNodeVersions . some ( v =>
363+ semver . satisfies ( v , `>=${ pkgMinNodeVersion } ` )
364+ )
345365 }
346366 }
347367}
@@ -374,22 +394,42 @@ export async function detectAndValidatePackageEnvironment(
374394 )
375395 }
376396 } )
377- const { agent, agentVersion } = details
397+ const { agent, nodeVersion, pkgRequirements } = details
398+ const agentVersion = details . agentVersion ?? 'unknown'
378399 if ( ! details . agentSupported ) {
379400 const minVersion = constants . minimumVersionByAgent . get ( agent ) !
380401 logger ?. fail (
381402 cmdPrefixMessage (
382403 cmdName ,
383- `Requires ${ agent } >=${ minVersion } . Current version: ${ agentVersion ?? 'unknown' } .`
404+ `Requires ${ agent } >=${ minVersion } . Current version: ${ agentVersion } .`
405+ )
406+ )
407+ return
408+ }
409+ if ( ! details . nodeSupported ) {
410+ const minVersion = constants . maintainedNodeVersions . last
411+ logger ?. fail (
412+ cmdPrefixMessage (
413+ cmdName ,
414+ `Requires Node >=${ minVersion } . Current version: ${ nodeVersion } .`
415+ )
416+ )
417+ return
418+ }
419+ if ( ! details . pkgSupports . agent ) {
420+ logger ?. fail (
421+ cmdPrefixMessage (
422+ cmdName ,
423+ `Package engine "${ agent } " requires ${ pkgRequirements . agent } . Current version: ${ agentVersion } `
384424 )
385425 )
386426 return
387427 }
388- if ( ! details . pkgSupported ) {
428+ if ( ! details . pkgSupports . node ) {
389429 logger ?. fail (
390430 cmdPrefixMessage (
391431 cmdName ,
392- `Package engine "node" or " ${ agent } " range not met `
432+ `Package engine "node" requires ${ pkgRequirements . node } . Current version: ${ nodeVersion } `
393433 )
394434 )
395435 return
0 commit comments