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

Unable to compile TypeScript with "moduleResolution": "bundler" option in v5 #27731

Closed
karlhorky opened this issue Sep 1, 2023 · 21 comments · Fixed by #28709
Closed

Unable to compile TypeScript with "moduleResolution": "bundler" option in v5 #27731

karlhorky opened this issue Sep 1, 2023 · 21 comments · Fixed by #28709
Labels
E2E Issue related to end-to-end testing topic: typescript Triaged Issue has been routed to backlog. This is not a commitment to have it prioritized by the team. type: bug

Comments

@karlhorky
Copy link
Contributor

karlhorky commented Sep 1, 2023

Current behavior

Originally reported by @MasonM in #26308 and closed because of Cypress v13.0.0 - but this release does not fix this

cc @jennifer-shehane @lmiller1990 - ideally #26308 would be unlocked and reopened, if you can do that

Copied issue below:


If you have a TypeScript project using the new "moduleResolution": "bundler" setting introduced in TypeScript 5, any attempts to run tests will cause the following error:

TSError: ⨯ Unable to compile TypeScript:
error TS5095: Option 'bundler' can only be used when 'module' is set to 'es2015' or later.

Desired behavior

Tests run successfully

Test code to reproduce

Reproduction 1

Courtesy of @MattyBalaam: https://github.com/MattyBalaam/cypress-ts-import

Reproduction 2

See error message and tsconfig.json below:

Your configFile is invalid: /home/runner/work/project/cypress.config.ts

It threw an error when required, check the stack trace below:

TSError: ⨯ Unable to compile TypeScript:
error TS5095: Option 'bundler' can only be used when 'module' is set to 'es2015' or later.

    at createTSError (/home/runner/.cache/Cypress/13.1.0/Cypress/resources/app/node_modules/ts-node/dist/index.js:311:16)
    at reportTSError (/home/runner/.cache/Cypress/13.1.0/Cypress/resources/app/node_modules/ts-node/dist/index.js:314:23)
    at /home/runner/.cache/Cypress/13.1.0/Cypress/resources/app/node_modules/ts-node/dist/index.js:686:17
    at Object.compile (/home/runner/.cache/Cypress/13.1.0/Cypress/resources/app/node_modules/ts-node/dist/index.js:743:35)
    at Module.m._compile (/home/runner/.cache/Cypress/13.1.0/Cypress/resources/app/node_modules/ts-node/dist/index.js:856:)
    at Module._extensions..js (node:internal/modules/cjs/loader:1252:10)
    at Object.require.extensions.<computed> [as .ts] (/home/runner/.cache/Cypress/13.1.0/Cypress/resources/app/node_modules/ts-node/dist/index.js:859:16)
    at Module.load (node:internal/modules/cjs/loader:1076:32)
    at Function.Module._load (node:internal/modules/cjs/loader:911:12)
    at Module.require (node:internal/modules/cjs/loader:1100:19)
    at require (node:internal/modules/cjs/helpers:108:18)
    at loadFile (/home/runner/.cache/Cypress/13.1.0/Cypress/resources/app/node_modules/@packages/server/lib/plugins/child/run_require_async_child.js:89:14)
    at EventEmitter.<anonymous> (/home/runner/.cache/Cypress/13.1.0/Cypress/resources/app/node_modules/@packages/server/lib/plugins/child/run_require_async_child.js:116:)
    at EventEmitter.emit (node:events:513:28)
    at EventEmitter.emit (node:domain:9:12)
    at process.<anonymous> (/home/runner/.cache/Cypress/13.1.0/Cypress/resources/app/node_modules/@packages/server/lib/plugins/util.js:33:22)
Test run failed, code 1

tsconfig.json

{
  "$schema": "https://json.schemastore.org/tsconfig",
  "display": "UpLeveled Node + React TSConfig",
  "compilerOptions": {
    "lib": ["DOM", "DOM.Iterable", "ESNext"],
    "module": "ESNext",
    "target": "ES2015",
    "moduleResolution": "Bundler",
    "resolveJsonModule": true,
    "esModuleInterop": true,
    "isolatedModules": true,
    "allowJs": true,
    "allowSyntheticDefaultImports": true,
    "downlevelIteration": true,
    "forceConsistentCasingInFileNames": true,
    "jsx": "preserve",
    "noEmit": true,
    "noFallthroughCasesInSwitch": true,
    "skipLibCheck": true,
    "strict": true,
    "incremental": true,
    "noUncheckedIndexedAccess": true
  },
  "include": [
    "**/.eslintrc.cjs",
    "next-env.d.ts",
    "**/*.ts",
    "**/*.tsx",
    "**/*.js",
    "**/*.jsx",
    "**/*.cjs",
    "**/*.mjs"
  ],
  "exclude": ["node_modules", "build", "public", "scripts"]
}

Cypress Version

13.1.0

Node version

v18.17.1

Operating System

macOS Ventura 13.5 (22G74)

Debug Logs

No response

Other

No response

@AdrianAndersen
Copy link

AdrianAndersen commented Sep 4, 2023

+1 on this. I am having the same issue.

@nagash77 nagash77 added type: feature New feature that does not currently exist topic: typescript E2E Issue related to end-to-end testing and removed type: feature New feature that does not currently exist labels Sep 5, 2023
@nagash77
Copy link
Contributor

nagash77 commented Sep 5, 2023

@karlhorky thank you for opening this issue. Internally we still largely use TS4 so there are some scenarios that still popup as problematic. I don't have an ETA on a fix for this, but if folks want to contribute a fix (with tests) we would be happy to review.

@nagash77 nagash77 added the Triaged Issue has been routed to backlog. This is not a commitment to have it prioritized by the team. label Sep 5, 2023
@thejacer87
Copy link

i just read through that closed issue. i am also running into the issue with ^13.1.0

@dotZak
Copy link

dotZak commented Sep 12, 2023

I encountered this problem today while setting up a Next.JS project. To confirm the issue I created a greenfield project to test it.

Workaround

For anyone looking for a workaround who lands here before they see the other related issues (now closed), here is a workaround copied from issue #27448:

{
  // Leave this section as is.
  "compilerOptions": {
    "module": "esnext",
    "moduleResolution": "bundler",
    "plugins": [],
    "paths": {}
  },
  // Add this section.
  "ts-node": {
    "compilerOptions": {
      "module": "ESNext",
      "moduleResolution": "Node"
    }
  },
}

Recreating the issue in a new project

Here are my steps and results. I hope this is helpful for whoever ends up working on a resolution.

System info

OS: macOS 14.0 Beta (23A5337a)
node: v20.6.1 (I first encountered the issue on 18, then upgraded and tried again)
npm: v9.8.1

Steps to reproduce

1. Create a next app using npx

% npx create-next-app@latest --typescript
✔ What is your project named? … next-cypress
✔ Would you like to use ESLint? … No / Yes
✔ Would you like to use Tailwind CSS? … No / Yes
✔ Would you like to use `src/` directory? … No / Yes
✔ Would you like to use App Router? (recommended) … No / Yes
✔ Would you like to customize the default import alias? … No / Yes
Creating a new Next.js app in /Users/…/Developer/next-cypress.

Using npm.

Initializing project with template: app


Installing dependencies:
- react
- react-dom
- next
- typescript
- @types/react
- @types/node
- @types/react-dom
- eslint
- eslint-config-next


added 277 packages, and audited 278 packages in 10s

106 packages are looking for funding
  run `npm fund` for details

found 0 vulnerabilities
Initialized a git repository.

Success! Created next-cypress at /Users/…/Developer/next-cypress

2. Enter the next app and install Cypress via NPM

… Developer % cd next-cypress
… next-cypress % npm i cypress -D

3. Install cypress

% npm run cypress install

> next-cypress@0.1.0 cypress
> cypress install

Installing Cypress (version: 13.1.0)

✔  Downloaded Cypress
✔  Unzipped Cypress
✔  Finished Installation /Users/zakknudsen/Library/Caches/Cypress/13.1.0

You can now open Cypress by running: node_modules/.bin/cypress open

https://on.cypress.io/installing-cypress

4. Run cypress open

% npm run cypress open

> next-cypress@0.1.0 cypress
> cypress open

It looks like this is your first time using Cypress: 13.1.0

✔  Verified Cypress! /Users/…/Library/Caches/Cypress/13.1.0/Cypress.app

Opening Cypress...

DevTools listening on ws://127.0.0.1:49466/devtools/browser/…
2023-09-12 14:25:15.233 Cypress[4606:45143] WARNING: Secure coding is not enabled for restorable state! Enable secure coding by implementing NSApplicationDelegate.applicationSupportsSecureRestorableState: and returning YES.
Missing baseUrl in compilerOptions. tsconfig-paths will be skipped
/Users/…/Library/Caches/Cypress/13.1.0/Cypress.app/Contents/Resources/app/node_modules/ts-node/dist/index.js:311
        return new TSError(diagnosticText, diagnosticCodes, diagnostics);
               ^
TSError: ⨯ Unable to compile TypeScript:
error TS5095: Option 'bundler' can only be used when 'module' is set to 'es2015' or later.

    at createTSError (/Users/…/Library/Caches/Cypress/13.1.0/Cypress.app/Contents/Resources/app/node_modules/ts-node/dist/index.js:311:16)
    at reportTSError (/Users/…/Library/Caches/Cypress/13.1.0/Cypress.app/Contents/Resources/app/node_modules/ts-node/dist/index.js:314:23)
    at /Users/…/Library/Caches/Cypress/13.1.0/Cypress.app/Contents/Resources/app/node_modules/ts-node/dist/index.js:686:17
    at Object.compile (/Users/…/Library/Caches/Cypress/13.1.0/Cypress.app/Contents/Resources/app/node_modules/ts-node/dist/index.js:743:35)
    at Module.m._compile (/Users/…/Library/Caches/Cypress/13.1.0/Cypress.app/Contents/Resources/app/node_modules/ts-node/dist/index.js:856:36)
    at Module._extensions..js (node:internal/modules/cjs/loader:1295:10)
    at Object.require.extensions.<computed> [as .js] (/Users/…/Library/Caches/Cypress/13.1.0/Cypress.app/Contents/Resources/app/node_modules/ts-node/dist/index.js:859:16)
    at Module.load (node:internal/modules/cjs/loader:1091:32)
    at Function.Module._load (node:internal/modules/cjs/loader:938:12)
    at Function.executeUserEntryPoint [as runMain] (node:internal/modules/run_main:83:12) {
  diagnosticCodes: [ 5095 ]
}
[4606:0912/142901.475308:ERROR:devtools_http_handler.cc(426)] GetMimeType doesn't know mime type for: browser/… text/plain will be returned
[4606:0912/142901.475478:ERROR:devtools_http_handler.cc(426)] GetMimeType doesn't know mime type for: browser/… text/plain will be returned
^C✔  Verified Cypress! /Users/…/Library/Caches/Cypress/13.1.0/Cypress.app

System information after installing Cypress

Output from % npm run cypress version:

> next-cypress@0.1.0 cypress
> cypress version

Cypress package version: 13.1.0
Cypress binary version: 13.1.0
Electron version: 21.0.0
Bundled Node version: 16.16.0

Output from npm run cypress --version:

9.8.1

Output from % npm run cypress info:

> next-cypress@0.1.0 cypress
> cypress info


DevTools listening on ws://127.0.0.1:49602/devtools/browser/…
2023-09-12 14:33:32.459 Cypress[5751:51459] WARNING: Secure coding is not enabled for restorable state! Enable secure coding by implementing NSApplicationDelegate.applicationSupportsSecureRestorableState: and returning YES.
Displaying Cypress info...

Detected 2 browsers installed:

1. Chrome
  - Name: chrome
  - Channel: stable
  - Version: 116.0.5845.187
  - Executable: /Applications/Google Chrome.app/Contents/MacOS/Google Chrome

2. Firefox
  - Name: firefox
  - Channel: stable
  - Version: 117.0
  - Executable: /Applications/Firefox.app/Contents/MacOS/firefox

Note: to run these browsers, pass <name>:<channel> to the '--browser' field

Examples:
- cypress run --browser firefox
- cypress run --browser chrome

Learn More: https://on.cypress.io/launching-browsers

Proxy Settings: none detected
Environment Variables: none detected

Application Data: /Users/…/Library/Application Support/cypress/cy/development
Browser Profiles: /Users/…/Library/Application Support/cypress/cy/development/browsers
Binary Caches: /Users/…/Library/Caches/Cypress

Cypress Version: 13.1.0 (stable)
System Platform: darwin (23.0.0)
System Memory: 8.59 GB free 472 MB

@lmiller1990
Copy link
Contributor

I thought I tested this with a brand new Next.js project.

We also have a test for projects using module: bundler: https://github.com/cypress-io/cypress/pull/27484/files#diff-9bb83cb045328bd56f40ad8b34ed1b7ede44bd44ef6191279a1ac0fd3c14bc57R4

What is going on -- is this test not configured correctly?

@scottohara
Copy link

scottohara commented Sep 19, 2023

What is going on -- is this test not configured correctly?

Not sure if this is the issue (as I'm not sure exactly how the system-tests work), but I noticed that the package.json file specifies typescript@4.7.3, but the "bundler" moduleResolution option was only added in typescript@5.0.0.

Would the TS version in that system-test be causing the test to be a false positive?

(For what it's worth, like others here I'm still getting the same error with Cypress 13, so it would seem that the issue is not resolved)

@softcam-henrique
Copy link

I am having the same issue.

@scottohara
Copy link

Not sure if this is the issue (as I'm not sure exactly how the system-tests work), but I noticed that the package.json file specifies typescript@4.7.3, but the "bundler" moduleResolution option was only added in typescript@5.0.0.

Any contributors with a functioning dev environment that can execute yarn test-system want to give this a try?

(I’d be happy to, but reading through CONTRIBUTING.md it seems like a lot of effort to get the environment setup just to test a hypothesis that is quite possibly wrong, so I thought I’d check first)

My hypothesis is that the config-with-module-resolution-bundler test passing is a false positive because moduleResolution: 'bundler' was introduced in Typescript 5, but the package.json file in the test only specifies Typescript 4.7.3. Perhaps it ignores an unrecognised value and falls back to a different default module resolution?

I could be completely wrong on this, hence why I don’t want to go to the trouble of getting the project running locally just to find out I’m wrong, if it would only take someone else a few minutes to verify.

@MikeMcC399
Copy link
Contributor

This needs to be resolved as a fresh default installation of Next.js 14.0.1 with

npx create-next-app

also causes the error

TSError: ⨯ Unable to compile TypeScript:
error TS5095: Option 'bundler' can only be used when 'module' is set to 'es2015' or later.

when running Cypress 13.4.0.

@emilyrohrbough
Copy link
Member

I am able to reproduce this issue error with the slimmed types configuration:

{
  "compilerOptions": {
    "module": "es2015",
    "moduleResolution": "bundler",
  }
}

I have only been able to produce this error when the Cypress configuration is using typescript, i.e. cypress.config.ts. When other files (src, test files) are using .ts it seems to be working as expected.

I do not see this error when the Cypress configuration is cypress.config.js, which is what the config-with-module-resolution-bundler system test project was leveraging.

The config-with-module-resolution-bundler project was not using the correct types version and was testing a .js spec, so it wasn't actually running anything through the ts compiler to indicate the wrong version was installed given the configuration provided. So it was a false-positive test. Sorry guys!

I have been able to make a few tweaks to our setup and it seems resolves the moduleResolution: bundler error with the reproduction I have. I want to do some more testing locally, but hoping to have something ready quick!

@emilyrohrbough
Copy link
Member

Okay - while working through how any changes would impact the existing expectations, I have found a few possible option that may work for a few of you depending on your current setup...

  1. skip the ts-node project check for the Cypress configuration via TS_NODE_SKIP_PROJECT=true

or

  1. override your compile options via the the command line to force commonJS / node resolution for the configuration child process:
TS_NODE_COMPILER_OPTIONS="{\"module\":\"CommonJS\",\"moduleResolution\":\"node\"}"

or

  1. specify ts-node configuration in your typescript configuration file. This options requires updating the generated cypress.config.ts file to be compatible with these compile options. The updates I made actually lost the types from the defineConfig helper we provide.
  "ts-node": {
    "compilerOptions": {
      "esm": true,
      "module": "esnext",
      "moduleResolution": "bundler",
    },
  },
module.exports = {
  e2e: {
    setupNodeEvents(on, config) {
      // implement node event listeners here
    },
  },
};

If anyone tries these options out and they work, that'd be helpful to know if any of these are reasonable paths forward given the various project setups someone can have with various typescript versions & needs.

@emilyrohrbough
Copy link
Member

Spoke with @elevatebart earlier, it sounds we are loading our configuration via ts-node and bundled file should be going through the webpack-processor. He was suggesting we may considering either specifying typescript support OR move towards only generating .js/.cjs cypress configuration files — this is the pattern other frameworks are trending towards.

@LukasLewandowski
Copy link

So in Cypress 13.5.0 we still need to use workaround with ts-node? Cypress complains on usage of
"module": "ESNext",
"moduleResolution": "Bundler",

@arbuznik
Copy link

arbuznik commented Dec 9, 2023

Does this issue means it's not possible to use cypress with Next.js?

Or is there a working workaround?

"next": "13.5.6",
"cypress": "^13.6.1",
"typescript": "^5"

leerob pushed a commit to vercel/next.js that referenced this issue Dec 13, 2023
This PR updates the testing guides to use App Router and TypeScript,
also updates `/examples` to show `app` and `pages` examples.

## Overview

- [x] Create a new "Testing" section that is shared between `app` and
`pages`.
- [x] Explain the differences between E2E, unit testing, component
testing, etc.
- [x] Recommend E2E for `async` components as currently none of the
tools support it.
- [x] Update setup guides for **Cypress**, **Playwright**, and **Jest**
with latest config options, and examples for `app` and `pages`.
- [x] Add new guide for **Vitest**
- [x] Clean up `/examples`: use TS, show `app` and `pages` examples,
match docs config

## Cypress

- [x] E2E Tests
- [x] Component Testing
  - [x] Client Components
  - [x] Server Components
  - [ ] `async` components

**Blockers:** 
- TS: `Option 'bundler' can only be used when 'module' is set to
'es2015' or later`. In **tsconfig.json** compilerOptions, Next.js uses
"moduleResolution": "bundler", changing it to "node" fixes the issue but
it can have repercussions.
  - cypress-io/cypress#27731 
- Version 14 is currently not supported for component testing
  - cypress-io/cypress#28185

## Playwright

- [x] E2E Tests

## Jest

- [x] Unit Testing
   - [x] Client Components
   - [x] Server Components
- [ ] `async` components:
testing-library/react-testing-library#1209
   - [x]  'server-only': #54891
- [x] Snapshot Testing

**Blockers:**
- TS: testing-library/jest-dom#546
- None of the solutions in the issue work with Next.js v14.0.4 and TS v5

## Vitest 

- [x] Unit Testing
  - [x] Client Components
  - [x] Server Components
  - [ ] `async` components
  - [x] 'server-only'
 - [x] Update vitest example
- [x] Handles CSS, and CSS modules imports
- [x] Handles next/image

## Other

- #47448
- #47299
@jennifer-shehane
Copy link
Member

I confirmed that this PR does not fix this. I didn't really expect it to anyway. #28528

@ahmadbilaldev
Copy link

Also facing the same issue on next.js 14. "moduleResolution": "node" fixes it but it can have side effects on Next.js code.

agustints pushed a commit to agustints/next.js that referenced this issue Jan 6, 2024
This PR updates the testing guides to use App Router and TypeScript,
also updates `/examples` to show `app` and `pages` examples.

## Overview

- [x] Create a new "Testing" section that is shared between `app` and
`pages`.
- [x] Explain the differences between E2E, unit testing, component
testing, etc.
- [x] Recommend E2E for `async` components as currently none of the
tools support it.
- [x] Update setup guides for **Cypress**, **Playwright**, and **Jest**
with latest config options, and examples for `app` and `pages`.
- [x] Add new guide for **Vitest**
- [x] Clean up `/examples`: use TS, show `app` and `pages` examples,
match docs config

## Cypress

- [x] E2E Tests
- [x] Component Testing
  - [x] Client Components
  - [x] Server Components
  - [ ] `async` components

**Blockers:** 
- TS: `Option 'bundler' can only be used when 'module' is set to
'es2015' or later`. In **tsconfig.json** compilerOptions, Next.js uses
"moduleResolution": "bundler", changing it to "node" fixes the issue but
it can have repercussions.
  - cypress-io/cypress#27731 
- Version 14 is currently not supported for component testing
  - cypress-io/cypress#28185

## Playwright

- [x] E2E Tests

## Jest

- [x] Unit Testing
   - [x] Client Components
   - [x] Server Components
- [ ] `async` components:
testing-library/react-testing-library#1209
   - [x]  'server-only': vercel#54891
- [x] Snapshot Testing

**Blockers:**
- TS: testing-library/jest-dom#546
- None of the solutions in the issue work with Next.js v14.0.4 and TS v5

## Vitest 

- [x] Unit Testing
  - [x] Client Components
  - [x] Server Components
  - [ ] `async` components
  - [x] 'server-only'
 - [x] Update vitest example
- [x] Handles CSS, and CSS modules imports
- [x] Handles next/image

## Other

- vercel#47448
- vercel#47299
@AtofStryker
Copy link
Contributor

@ahmadbilaldev @arbuznik can either of you try TS_NODE_COMPILER=1 npx cypress open as a workaround?

@AtofStryker
Copy link
Contributor

I believe I have a fix for this in #28709. Would anyone like to additionally try the binaries build on 0481c7a to confirm? If you scroll down the page there should be npm install instructions for your system.

@karlhorky
Copy link
Contributor Author

karlhorky commented Jan 12, 2024

@AtofStryker I upgraded to https://cdn.cypress.io/beta/npm/13.6.3/linux-x64/fix/set_module_resolution_with_commonjs-0481c7af5d4085004b91dd644d7a4c8d97ea1b00/cypress.tgz (linux x64 version from the commit) and can confirm that this is allowing moduleResolution: "Bundler" in our tsconfig.json 🎉

package.json

{
  "devDependencies": {
    "cypress": "https://cdn.cypress.io/beta/npm/13.6.3/linux-x64/fix/set_module_resolution_with_commonjs-0481c7af5d4085004b91dd644d7a4c8d97ea1b00/cypress.tgz"
  }
}

I was able to remove my workaround lines below from tsconfig.json:

tsconfig.json

{
-  // Old "moduleResolution": "Node" option required for Cypress
-  // https://github.com/cypress-io/cypress/issues/26308#issuecomment-1663592648
-  //
-  // TODO: Remove this when Cypress supports "moduleResolution": "Bundler"
-  // https://github.com/cypress-io/cypress/issues/27448
-  // https://github.com/cypress-io/cypress/issues/27731
-  "ts-node": {
-    "compilerOptions": {
-      "module": "es2015",
-      "moduleResolution": "node"
-    }
-  },
  "compilerOptions": {
    "module": "ESNext",
    "moduleResolution": "Bundler"
  }
}

@tonytino
Copy link

@ahmadbilaldev @arbuznik can either of you try TS_NODE_COMPILER=1 npx cypress open as a workaround?

@AtofStryker FYI, I gave this a try and it resolved the issue for me.

@cypress-bot
Copy link
Contributor

cypress-bot bot commented Jan 17, 2024

Released in 13.6.3.

This comment thread has been locked. If you are still experiencing this issue after upgrading to
Cypress v13.6.3, please open a new issue.

@cypress-bot cypress-bot bot locked as resolved and limited conversation to collaborators Jan 17, 2024
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
E2E Issue related to end-to-end testing topic: typescript Triaged Issue has been routed to backlog. This is not a commitment to have it prioritized by the team. type: bug
Projects
None yet