@@ -30,6 +30,7 @@ import {
3030 isPossibleTsOutput ,
3131 isTsRequest ,
3232 isWindows ,
33+ lookupFile ,
3334 nestedResolveFrom ,
3435 normalizePath ,
3536 resolveFrom ,
@@ -44,6 +45,8 @@ import { loadPackageData, resolvePackageData } from '../packages'
4445// special id for paths marked with browser: false
4546// https://github.com/defunctzombie/package-browser-field-spec#ignore-a-module
4647export const browserExternalId = '__vite-browser-external'
48+ // special id for packages that are optional peer deps
49+ export const optionalPeerDepId = '__vite-optional-peer-dep'
4750
4851const isDebug = process . env . DEBUG
4952const debug = createDebugger ( 'vite:resolve-details' , {
@@ -365,6 +368,14 @@ export default new Proxy({}, {
365368})`
366369 }
367370 }
371+ if ( id . startsWith ( optionalPeerDepId ) ) {
372+ if ( isProduction ) {
373+ return `export default {}`
374+ } else {
375+ const [ , peerDep , parentDep ] = id . split ( ':' )
376+ return `throw new Error(\`Could not resolve "${ peerDep } " imported by "${ parentDep } ". Is it installed?\`)`
377+ }
378+ }
368379 }
369380 }
370381}
@@ -618,6 +629,30 @@ export function tryNodeResolve(
618629 } ) !
619630
620631 if ( ! pkg ) {
632+ // if import can't be found, check if it's an optional peer dep.
633+ // if so, we can resolve to a special id that errors only when imported.
634+ if (
635+ basedir !== root && // root has no peer dep
636+ ! isBuiltin ( id ) &&
637+ ! id . includes ( '\0' ) &&
638+ bareImportRE . test ( id )
639+ ) {
640+ // find package.json with `name` as main
641+ const mainPackageJson = lookupFile ( basedir , [ 'package.json' ] , {
642+ predicate : ( content ) => ! ! JSON . parse ( content ) . name
643+ } )
644+ if ( mainPackageJson ) {
645+ const mainPkg = JSON . parse ( mainPackageJson )
646+ if (
647+ mainPkg . peerDependencies ?. [ id ] &&
648+ mainPkg . peerDependenciesMeta ?. [ id ] ?. optional
649+ ) {
650+ return {
651+ id : `${ optionalPeerDepId } :${ id } :${ mainPkg . name } `
652+ }
653+ }
654+ }
655+ }
621656 return
622657 }
623658
0 commit comments