Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Right-hand side of 'instanceof' is not an object / FailedToResolveUnsupportedError #1393

Open
aldebout opened this issue Nov 19, 2024 · 3 comments

Comments

@aldebout
Copy link

Do you want to request a feature or report a bug?
Bug

What is the current behavior?
When adding unstable_enablePackageExports = true to config and starting the dev server with expo dev, the app crashes and it looks like there's an issue with error reporting inside of metro.

iOS Bundling failed 1871ms node_modules/expo-router/entry.js (4294 modules)
 ERROR  TypeError: Right-hand side of 'instanceof' is not an object
    at ModuleResolver.resolveDependency (/project-path/node_modules/metro/src/node-haste/DependencyGraph/ModuleResolution.js:130:24)
    at DependencyGraph.resolveDependency (/project-path/node_modules/metro/src/node-haste/DependencyGraph.js:235:43)
image

If the current behavior is a bug, please provide the steps to reproduce and a minimal repository on GitHub that we can yarn install and yarn test.

Not sure how to repro since I think there's an underlying issue with my repo but this is about the failure to properly throw the error.

What is the expected behavior?

I get a useful error.

Please provide your exact Metro configuration and mention your Metro, node, yarn/npm version and operating system.

node: 20.16.0
pnpm: 9.6.0
os: macos Sonoma 14.7
metro: 0.81.0
expo: 52.0.7
RN: 0.76.2

Project is in a pnpm + turborepo monorepo.

Full metro config:

let config ={
  resolver: {
    assetExts: [
      'bmp',  'gif',  'jpg',  'jpeg',
      'png',  'psd',  'svg',  'webp',
      'xml',  'm4v',  'mov',  'mp4',
      'mpeg', 'mpg',  'webm', 'aac',
      'aiff', 'caf',  'm4a',  'mp3',
      'wav',  'html', 'pdf',  'yaml',
      'yml',  'otf',  'ttf',  'zip',
      'heic', 'avif', 'db'
    ],
    assetResolutions: [ '1', '1.5', '2', '3', '4' ],
    platforms: [ 'ios', 'android' ],
    sourceExts: [
      'ts',  'tsx',  'mjs',
      'js',  'jsx',  'json',
      'cjs', 'scss', 'sass',
      'css', 'css'
    ],
    blockList: /(\/__tests__\/.*)$/,
    dependencyExtractor: undefined,
    disableHierarchicalLookup: false,
    emptyModulePath: '/project-path/node_modules/metro-runtime/src/modules/empty-module.js',
    enableGlobalPackages: false,
    extraNodeModules: {},
    hasteImplModulePath: undefined,
    nodeModulesPaths: [
      '/project-path/apps/expo/node_modules',
      '/project-path/node_modules'
    ],
    resolveRequest: [Function: resolveRequest],
    resolverMainFields: [ 'react-native', 'browser', 'main' ],
    unstable_conditionNames: [ 'require', 'import' ],
    unstable_conditionsByPlatform: { ios: [Array], android: [Array], web: [Array] },
    unstable_enablePackageExports: true,
    useWatchman: true,
    requireCycleIgnorePatterns: [ /(^|\/|\\)node_modules($|\/|\\)/ ]
  },
  serializer: {
    polyfillModuleNames: [],
    getRunModuleStatement: [Function: getRunModuleStatement],
    getPolyfills: [Function: getPolyfills],
    getModulesRunBeforeMainModule: [Function: getModulesRunBeforeMainModule],
    processModuleFilter: [Function: processModuleFilter],
    createModuleIdFactory: [Function: createNumericModuleIdFactory],
    experimentalSerializerHook: [Function: experimentalSerializerHook],
    customSerializer: [AsyncFunction (anonymous)],
    isThirdPartyModule: [Function: isThirdPartyModule]
  },
  server: {
    enhanceMiddleware: [Function: enhanceMiddleware],
    forwardClientLogs: true,
    port: 8081,
    rewriteRequestUrl: [Function: rewriteExpoRequestUrl],
    unstable_serverRoot: '/project-path',
    useGlobalHotkey: true,
    verifyConnections: false
  },
  symbolicator: {
    customizeFrame: [Function: customizeFrame],
    customizeStack: [AsyncFunction: customizeStack]
  },
  transformer: {
    assetPlugins: [ 'expo-asset/tools/hashAssetFiles' ],
    asyncRequireModulePath: '/project-path/node_modules/metro-runtime/src/modules/asyncRequire.js',
    assetRegistryPath: '@react-native/assets-registry/registry',
    babelTransformerPath: '/project-path/node_modules/@expo/metro-config/build/babel-transformer.js',
    dynamicDepsInPackages: 'throwAtRuntime',
    enableBabelRCLookup: true,
    enableBabelRuntime: true,
    getTransformOptions: [AsyncFunction: getTransformOptions],
    globalPrefix: '',
    hermesParser: false,
    minifierConfig: {
      mangle: [Object],
      output: [Object],
      sourceMap: [Object],
      toplevel: false,
      compress: [Object]
    },
    minifierPath: 'metro-minify-terser',
    optimizationSizeLimit: 153600,
    transformVariants: { default: {} },
    workerPath: 'metro/src/DeltaBundler/Worker',
    publicPath: '/assets',
    allowOptionalDependencies: true,
    unstable_allowRequireContext: true,
    unstable_dependencyMapReservedName: null,
    unstable_disableModuleWrapping: false,
    unstable_disableNormalizePseudoGlobals: false,
    unstable_renameRequire: false,
    unstable_compactOutput: false,
    unstable_memoizeInlineRequires: false,
    unstable_workerThreads: false,
    postcssHash: null,
    browserslistHash: null,
    sassVersion: '1.81.0',
    reanimatedVersion: '3.16.1',
    _expoRelativeProjectRoot: 'apps/expo',
    cssInterop_transformerPath: '/project-path/node_modules/@expo/metro-config/build/transform-worker/transform-worker.js',
    cssInterop_outputDirectory: '../../node_modules/react-native-css-interop/.cache'
  },
  watcher: {
    additionalExts: [ 'env.development.local', 'env.local', 'env.development', 'env' ],
    healthCheck: {
      enabled: false,
      filePrefix: '.metro-health-check',
      interval: 30000,
      timeout: 5000
    },
    unstable_workerThreads: false,
    watchman: { deferStates: [Array] }
  },
  cacheStores: [
    FileStore {
      _root: '/project-path/apps/expo/node_modules/.cache/metro'
    }
  ],
  cacheVersion: '1.0',
  projectRoot: '/project-path/apps/expo',
  stickyWorkers: true,
  watchFolders: [
    '/project-path/node_modules',
    '/project-path/apps/nextjs',
    '/project-path/apps/expo',
    '/project-path/packages/workflows',
    '/project-path/packages/validators',
    '/project-path/packages/utils',
    '/project-path/packages/ui',
    '/project-path/packages/stripe',
    '/project-path/packages/scripts',
    '/project-path/packages/db',
    '/project-path/packages/brevo-client',
    '/project-path/packages/api',
    '/project-path/tooling/typescript',
    '/project-path/tooling/tailwind',
    '/project-path/tooling/prettier',
    '/project-path/tooling/github',
    '/project-path/tooling/eslint'
  ],
  transformerPath: '/project-path/node_modules/react-native-css-interop/dist/metro/transformer.js',
  maxWorkers: 6,
  resetCache: false,
  unstable_perfLoggerFactory: [Function (anonymous)]
}
@robhogan
Copy link
Contributor

Hi @aldebout - the problematic line there is instanceof Resolver.FailedToResolveUnsupportedError, which was a new error type added to [email protected].

That's an explicit dependency of metro, so it's hard to see how that could go wrong unless you have something either monkey-patching metro-resolver or overriding its resolution to a different version. I haven't been able to reproduce by trying to trigger a non-path resolution error (it would fire, for example, on an import foo from 'non-existent')

Could you verify that the version of metro-resolver in your node_modules is 0.81.0?

@robhogan
Copy link
Contributor

(CC @byCedric on the remote possibility that Expo CLI is doing anything funny with metro-resolver's resolution or its exports.)

@aldebout
Copy link
Author

aldebout commented Nov 25, 2024

@robhogan I'm also very confused as to how something this basic can fail, I'll try looking at the local files themselves.


Edit: I checked locally in my node_modules and everything looks fine.

The types for metro-resolver don't really match the js but that should not be a problem.

What I really don't understand is that a few lines above the problematic one is a very similar check:

      if (error instanceof Resolver.FailedToResolvePathError) {
        ...
      } else if (error instanceof Resolver.FailedToResolveUnsupportedError) {

I fail to see a structural difference between FailedToResolvePathError and FailedToResolveUnsupportedError that could explain one working and the other one failing but I'm really not familiar with this codebase.


This is the output of pnpm why metro-resolver, 0.81.0 all around:

dependencies:
@bacons/text-decoder 0.0.0
└─┬ react-native 0.76.2 peer
  └─┬ @react-native/community-cli-plugin 0.76.2
    ├─┬ metro 0.81.0
    │ ├─┬ metro-cache 0.81.0
    │ │ └─┬ metro-core 0.81.0
    │ │   └── metro-resolver 0.81.0
    │ ├─┬ metro-config 0.81.0
    │ │ ├─┬ metro-cache 0.81.0
    │ │ │ └─┬ metro-core 0.81.0
    │ │ │   └── metro-resolver 0.81.0
    │ │ └─┬ metro-core 0.81.0
    │ │   └── metro-resolver 0.81.0
    │ ├─┬ metro-core 0.81.0
    │ │ └── metro-resolver 0.81.0
    │ ├── metro-resolver 0.81.0
    │ └─┬ metro-transform-worker 0.81.0
    │   └─┬ metro-cache 0.81.0
    │     └─┬ metro-core 0.81.0
    │       └── metro-resolver 0.81.0
    ├─┬ metro-config 0.81.0
    │ ├─┬ metro-cache 0.81.0
    │ │ └─┬ metro-core 0.81.0
    │ │   └── metro-resolver 0.81.0
    │ └─┬ metro-core 0.81.0
    │   └── metro-resolver 0.81.0
    └─┬ metro-core 0.81.0
      └── metro-resolver 0.81.0
@gorhom/bottom-sheet 5.0.5
└─┬ @gorhom/portal 1.0.14
  └─┬ react-native 0.76.2 peer
    └─┬ @react-native/community-cli-plugin 0.76.2
      └─┬ metro 0.81.0
        └─┬ metro-cache 0.81.0
          └─┬ metro-core 0.81.0
            └── metro-resolver 0.81.0

devDependencies:
expo-atlas 0.3.27
└─┬ expo 52.0.7 peer
  ├─┬ @expo/metro-runtime 4.0.0 peer
  │ └─┬ react-native 0.76.2 peer
  │   └─┬ @react-native/community-cli-plugin 0.76.2
  │     ├─┬ metro 0.81.0
  │     │ ├─┬ metro-cache 0.81.0
  │     │ │ └─┬ metro-core 0.81.0
  │     │ │   └── metro-resolver 0.81.0
  │     │ ├─┬ metro-config 0.81.0
  │     │ │ ├─┬ metro-cache 0.81.0
  │     │ │ │ └─┬ metro-core 0.81.0
  │     │ │ │   └── metro-resolver 0.81.0
  │     │ │ └─┬ metro-core 0.81.0
  │     │ │   └── metro-resolver 0.81.0
  │     │ ├─┬ metro-core 0.81.0
  │     │ │ └── metro-resolver 0.81.0
  │     │ ├── metro-resolver 0.81.0
  │     │ └─┬ metro-transform-worker 0.81.0
  │     │   └─┬ metro-cache 0.81.0
  │     │     └─┬ metro-core 0.81.0
  │     │       └── metro-resolver 0.81.0
  │     ├─┬ metro-config 0.81.0
  │     │ ├─┬ metro-cache 0.81.0
  │     │ │ └─┬ metro-core 0.81.0
  │     │ │   └── metro-resolver 0.81.0
  │     │ └─┬ metro-core 0.81.0
  │     │   └── metro-resolver 0.81.0
  │     └─┬ metro-core 0.81.0
  │       └── metro-resolver 0.81.0
  ├─┬ expo-asset 11.0.1
  │ ├─┬ expo-constants 17.0.3
  │ │ └─┬ react-native 0.76.2 peer
  │ │   └─┬ @react-native/community-cli-plugin 0.76.2
  │ │     ├─┬ metro 0.81.0
  │ │     │ ├─┬ metro-cache 0.81.0
  │ │     │ │ └─┬ metro-core 0.81.0
  │ │     │ │   └── metro-resolver 0.81.0
  │ │     │ ├─┬ metro-config 0.81.0
  │ │     │ │ ├─┬ metro-cache 0.81.0
  │ │     │ │ │ └─┬ metro-core 0.81.0
  │ │     │ │ │   └── metro-resolver 0.81.0
  │ │     │ │ └─┬ metro-core 0.81.0
  │ │     │ │   └── metro-resolver 0.81.0
  │ │     │ ├─┬ metro-core 0.81.0
  │ │     │ │ └── metro-resolver 0.81.0
  │ │     │ ├── metro-resolver 0.81.0
  │ │     │ └─┬ metro-transform-worker 0.81.0
  │ │     │   └─┬ metro-cache 0.81.0
  │ │     │     └─┬ metro-core 0.81.0
  │ │     │       └── metro-resolver 0.81.0
  │ │     ├─┬ metro-config 0.81.0
  │ │     │ ├─┬ metro-cache 0.81.0
  │ │     │ │ └─┬ metro-core 0.81.0
  │ │     │ │   └── metro-resolver 0.81.0
  │ │     │ └─┬ metro-core 0.81.0
  │ │     │   └── metro-resolver 0.81.0
  │ │     └─┬ metro-core 0.81.0
  │ │       └── metro-resolver 0.81.0
  │ └─┬ react-native 0.76.2 peer
  │   └─┬ @react-native/community-cli-plugin 0.76.2
  │     ├─┬ metro 0.81.0
  │     │ ├─┬ metro-cache 0.81.0
  │     │ │ └─┬ metro-core 0.81.0
  │     │ │   └── metro-resolver 0.81.0
  │     │ ├─┬ metro-config 0.81.0
  │     │ │ ├─┬ metro-cache 0.81.0
  │     │ │ │ └─┬ metro-core 0.81.0
  │     │ │ │   └── metro-resolver 0.81.0
  │     │ │ └─┬ metro-core 0.81.0
  │     │ │   └── metro-resolver 0.81.0
  │     │ ├─┬ metro-core 0.81.0
  │     │ │ └── metro-resolver 0.81.0
  │     │ ├── metro-resolver 0.81.0
  │     │ └─┬ metro-transform-worker 0.81.0
  │     │   └─┬ metro-cache 0.81.0
  │     │     └─┬ metro-core 0.81.0
  │     │       └── metro-resolver 0.81.0
  │     ├─┬ metro-config 0.81.0
  │     │ ├─┬ metro-cache 0.81.0
  │     │ │ └─┬ metro-core 0.81.0
  │     │ │   └── metro-resolver 0.81.0
  │     │ └─┬ metro-core 0.81.0
  │     │   └── metro-resolver 0.81.0
  │     └─┬ metro-core 0.81.0
  │       └── metro-resolver 0.81.0
  ├─┬ expo-constants 17.0.3
  │ └─┬ react-native 0.76.2 peer
  │   └─┬ @react-native/community-cli-plugin 0.76.2
  │     ├─┬ metro 0.81.0
  │     │ ├─┬ metro-cache 0.81.0
  │     │ │ └─┬ metro-core 0.81.0
  │     │ │   └── metro-resolver 0.81.0
  │     │ ├─┬ metro-config 0.81.0
  │     │ │ ├─┬ metro-cache 0.81.0
  │     │ │ │ └─┬ metro-core 0.81.0
  │     │ │ │   └── metro-resolver 0.81.0
  │     │ │ └─┬ metro-core 0.81.0
  │     │ │   └── metro-resolver 0.81.0
  │     │ ├─┬ metro-core 0.81.0
  │     │ │ └── metro-resolver 0.81.0
  │     │ ├── metro-resolver 0.81.0
  │     │ └─┬ metro-transform-worker 0.81.0
  │     │   └─┬ metro-cache 0.81.0
  │     │     └─┬ metro-core 0.81.0
  │     │       └── metro-resolver 0.81.0
  │     ├─┬ metro-config 0.81.0
  │     │ ├─┬ metro-cache 0.81.0
  │     │ │ └─┬ metro-core 0.81.0
  │     │ │   └── metro-resolver 0.81.0
  │     │ └─┬ metro-core 0.81.0
  │     │   └── metro-resolver 0.81.0
  │     └─┬ metro-core 0.81.0
  │       └── metro-resolver 0.81.0
  ├─┬ expo-file-system 18.0.3
  │ └─┬ react-native 0.76.2 peer
  │   └─┬ @react-native/community-cli-plugin 0.76.2
  │     ├─┬ metro 0.81.0
  │     │ ├─┬ metro-cache 0.81.0
  │     │ │ └─┬ metro-core 0.81.0
  │     │ │   └── metro-resolver 0.81.0
  │     │ ├─┬ metro-config 0.81.0
  │     │ │ ├─┬ metro-cache 0.81.0
  │     │ │ │ └─┬ metro-core 0.81.0
  │     │ │ │   └── metro-resolver 0.81.0
  │     │ │ └─┬ metro-core 0.81.0
  │     │ │   └── metro-resolver 0.81.0
  │     │ ├─┬ metro-core 0.81.0
  │     │ │ └── metro-resolver 0.81.0
  │     │ ├── metro-resolver 0.81.0
  │     │ └─┬ metro-transform-worker 0.81.0
  │     │   └─┬ metro-cache 0.81.0
  │     │     └─┬ metro-core 0.81.0
  │     │       └── metro-resolver 0.81.0
  │     ├─┬ metro-config 0.81.0
  │     │ ├─┬ metro-cache 0.81.0
  │     │ │ └─┬ metro-core 0.81.0
  │     │ │   └── metro-resolver 0.81.0
  │     │ └─┬ metro-core 0.81.0
  │     │   └── metro-resolver 0.81.0
  │     └─┬ metro-core 0.81.0
  │       └── metro-resolver 0.81.0
  └─┬ react-native 0.76.2 peer
    └─┬ @react-native/community-cli-plugin 0.76.2
      ├─┬ metro 0.81.0
      │ ├─┬ metro-cache 0.81.0
      │ │ └─┬ metro-core 0.81.0
      │ │   └── metro-resolver 0.81.0
      │ ├─┬ metro-config 0.81.0
      │ │ ├─┬ metro-cache 0.81.0
      │ │ │ └─┬ metro-core 0.81.0
      │ │ │   └── metro-resolver 0.81.0
      │ │ └─┬ metro-core 0.81.0
      │ │   └── metro-resolver 0.81.0
      │ ├─┬ metro-core 0.81.0
      │ │ └── metro-resolver 0.81.0
      │ ├── metro-resolver 0.81.0
      │ └─┬ metro-transform-worker 0.81.0
      │   └─┬ metro-cache 0.81.0
      │     └─┬ metro-core 0.81.0
      │       └── metro-resolver 0.81.0
      ├─┬ metro-config 0.81.0
      │ ├─┬ metro-cache 0.81.0
      │ │ └─┬ metro-core 0.81.0
      │ │   └── metro-resolver 0.81.0
      │ └─┬ metro-core 0.81.0
      │   └── metro-resolver 0.81.0
      └─┬ metro-core 0.81.0
        └── metro-resolver 0.81.0

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants