@@ -59,6 +59,33 @@ const userConditions = getOptionValue('--conditions');
5959const DEFAULT_CONDITIONS = ObjectFreeze ( [ 'node' , 'import' , ...userConditions ] ) ;
6060const DEFAULT_CONDITIONS_SET = new SafeSet ( DEFAULT_CONDITIONS ) ;
6161
62+ const pendingDeprecation = getOptionValue ( '--pending-deprecation' ) ;
63+ const emittedPackageWarnings = new SafeSet ( ) ;
64+ function emitFolderMapDeprecation ( match , pjsonUrl , isExports , base ) {
65+ const pjsonPath = fileURLToPath ( pjsonUrl ) ;
66+ if ( ! pendingDeprecation ) {
67+ const nodeModulesIndex = pjsonPath . lastIndexOf ( '/node_modules/' ) ;
68+ if ( nodeModulesIndex !== - 1 ) {
69+ const afterNodeModulesPath = pjsonPath . slice ( nodeModulesIndex + 14 , - 13 ) ;
70+ try {
71+ const { packageSubpath } = parsePackageName ( afterNodeModulesPath ) ;
72+ if ( packageSubpath === '.' )
73+ return ;
74+ } catch { }
75+ }
76+ }
77+ if ( emittedPackageWarnings . has ( pjsonPath + '|' + match ) )
78+ return ;
79+ emittedPackageWarnings . add ( pjsonPath + '|' + match ) ;
80+ process . emitWarning (
81+ `Use of deprecated folder mapping "${ match } " in the ${ isExports ?
82+ '"exports"' : '"imports"' } field module resolution of the package at ${
83+ pjsonPath } ${ base ? ` imported from ${ fileURLToPath ( base ) } ` : '' } .\n` +
84+ `Update this package.json to use a subpath pattern like "${ match } *".` ,
85+ 'DeprecationWarning' ,
86+ 'DEP0148'
87+ ) ;
88+ }
6289
6390function getConditionsSet ( conditions ) {
6491 if ( conditions !== undefined && conditions !== DEFAULT_CONDITIONS ) {
@@ -507,6 +534,8 @@ function packageExportsResolve(
507534 conditions ) ;
508535 if ( resolved === null || resolved === undefined )
509536 throwExportsNotFound ( packageSubpath , packageJSONUrl , base ) ;
537+ if ( ! pattern )
538+ emitFolderMapDeprecation ( bestMatch , packageJSONUrl , true , base ) ;
510539 return { resolved, exact : pattern } ;
511540 }
512541
@@ -556,8 +585,11 @@ function packageImportsResolve(name, base, conditions) {
556585 const resolved = resolvePackageTarget (
557586 packageJSONUrl , target , subpath , bestMatch , base , pattern , true ,
558587 conditions ) ;
559- if ( resolved !== null )
588+ if ( resolved !== null ) {
589+ if ( ! pattern )
590+ emitFolderMapDeprecation ( bestMatch , packageJSONUrl , false , base ) ;
560591 return { resolved, exact : pattern } ;
592+ }
561593 }
562594 }
563595 }
@@ -570,13 +602,7 @@ function getPackageType(url) {
570602 return packageConfig . type ;
571603}
572604
573- /**
574- * @param {string } specifier
575- * @param {URL } base
576- * @param {Set<string> } conditions
577- * @returns {URL }
578- */
579- function packageResolve ( specifier , base , conditions ) {
605+ function parsePackageName ( specifier , base ) {
580606 let separatorIndex = StringPrototypeIndexOf ( specifier , '/' ) ;
581607 let validPackageName = true ;
582608 let isScoped = false ;
@@ -610,6 +636,19 @@ function packageResolve(specifier, base, conditions) {
610636 const packageSubpath = '.' + ( separatorIndex === - 1 ? '' :
611637 StringPrototypeSlice ( specifier , separatorIndex ) ) ;
612638
639+ return { packageName, packageSubpath, isScoped } ;
640+ }
641+
642+ /**
643+ * @param {string } specifier
644+ * @param {URL } base
645+ * @param {Set<string> } conditions
646+ * @returns {URL }
647+ */
648+ function packageResolve ( specifier , base , conditions ) {
649+ const { packageName, packageSubpath, isScoped } =
650+ parsePackageName ( specifier , base ) ;
651+
613652 // ResolveSelf
614653 const packageConfig = getPackageScopeConfig ( base ) ;
615654 if ( packageConfig . exists ) {
0 commit comments