kulshekhar / ts-jest

A Jest transformer with source map support that lets you use Jest to test projects written in TypeScript.

Home Page:https://kulshekhar.github.io/ts-jest

Geek Repo:Geek Repo

Github PK Tool:Github PK Tool

[Bug]: error TS1343: The 'import.meta' meta-property is only allowed when the '--module' option is 'es2020', 'es2022', 'esnext', 'system', 'node16', or 'nodenext'.

broofa opened this issue · comments

[For context, I originally opened this issue in the jest repo, but @SimenB said I should open a ticket here.]

Version

29.0.3

Steps to reproduce

Expected behavior

Test should run w/out errors.

Actual behavior

Test fails with the error shown in the title.

Specifically, here's what I see:
CleanShot 2022-10-26 at 17 17 13@2x

Additional context

You can click "show files" in the repl.it window to see the tsconfig.json and package.json#jest setup.

As you'll see, I have the following configuration, so it's not clear what else I could/should do to work around this error:

{
  "compilerOptions": {
    "module": "es2020",
    "moduleResolution": "node",
    "target": "es2020",
    "esModuleInterop": true,
    "types": [
      "jest"
    ]
  }
}

Environment

~/JestImportMetaTest$ npx envinfo --preset jest.
Need to install the following packages:
  envinfo
Ok to proceed? (y) y

No "jest." preset found.
npm notice 
npm notice New major version of npm available! 7.20.3 -> 8.19.2
npm notice Changelog: https://github.com/npm/cli/releases/tag/v8.19.2
npm notice Run npm install -g npm@8.19.2 to update!
npm notice 
~/JestImportMetaTest$

I'm experiencing this same issue, but having module defined as nodenext in my case.

I have tried to follow every guides relating to the ESM issue and running with
node --experimental-vm-modules

the test should work.

We get this warning obviously "ExperimentalWarning: VM Modules is an experimental feature. This feature could change at any time"
It looks as if the compiler completly ignores the compilerOptions.module. It doesn't matter what module ESxx you put in.

While it makes the errors go away, it does not solve the use of import.meta.

commented

This is related to configuration. Necessary configuration to run with ESM is not there. Please take a look at our example apps https://github.com/kulshekhar/ts-jest/tree/main/examples or documentation https://kulshekhar.github.io/ts-jest/docs/guides/esm-support

@ahnpnl I've just spent the last half-hour reading the docs you linked to and trying every combination of tsconfig and jest.config.js I could find therein. Including ...

  • Moving jest config out of package.json and into jest.config.js
  • Switching from "presets": "ts-jest" to "presets": "ts-jest/presets/default-esm"
  • Removing presets
  • Adding "useESM": true
  • Switching to "module": "CommonJS" in tsconfig
  • Adding/removing tsconfig: 'tsconfig.json', in tsconfig
  • Removing types, target, and moduleResolution in tsconfing

... and nothing helps. I keep getting the same error message.

I apologize for the trouble, but can you please tell me what configuration exactly I should be using here to get this to work?

commented

I’ve linked the example repos. You can check them.

@ahnpnl I've checked the examples. Specifically: I've tried modifying the repl.it code, above, to use the configurations shown in both the ts-only and the type-module examples. I continue to get this error.

Is there a specific example i should be looking at? Within that example, is there specific tsconfig.* and jest.* files I should be using?

Unfortunately there's many examples and, within each example, many configuration files. I've done my best to investigate the various options shown but, based on what I'm seeing, I'm not convinced this is a configuration file issue.

commented

In each example project, there is a jest-esm.config.js which already points to the tsconfig.json it is using. Besides, in package.json, the script to run test already contains the flag to use ESM with NodeJS.

Besides, if you are specifying transform, please remove preset from your Jest config.

The easiest way is you can clone one of the example apps and try out to compare with your repo. These example apps are included in CI so they are a good basic ones to start with.

Okay, I think I have this figured out. Debugging this was complicated by the fact there were two issues, either one of which would result in the same (not-at-all obvious) error message. Leaving breadcrumbs for anyone else who struggles with this...

The two missing pieces (for me) were the following:

  1. jest has to be run with node's --experimental-vm-modules flag. I.e. Invoke jest as NODE_OPTIONS="--experimental-vm-modules" jest.
  2. Configure jest with the ts-jest/presets/default-esm preset:
module.exports = {
  preset: 'ts-jest/presets/default-esm',
}

Sorry for the trouble @ahnpnl . I appreciate your patience. 🙌

@broofa Your first suggestion does not work for me. With that setting I now get the error:

ReferenceError: exports is not defined

so as if jest would try with common js modules, instead of ESM.

@broofa Your first suggestion does not work for me. With that setting I now get the error:

ReferenceError: exports is not defined

so as if jest would try with common js modules, instead of ESM.

I am getting this same error, even with the following:

import { jsWithTsESM } from "ts-jest/presets";

/*
 * For a detailed explanation regarding each configuration property and type check, visit:
 * https://jestjs.io/docs/configuration
 */

export default {
  ...jsWithTsESM,
  transform: {
    "^.+\\.tsx?$": [
      "ts-jest",
      {
        tsconfig: "tsconfig.json",
        useESM: true,
      },
    ],
  },
};

and

    "test": "cross-env NODE_OPTIONS=\"--experimental-vm-modules\" jest",

Configuring jest-ts-webcompat-resolver helped me in the same situation, I have no idea how

Alternatively, you can use ts-jest-mock-import-meta npm package to fix this issue.

Install

npm install -D ts-jest-mock-import-meta

In jest.config.js

{
  // [...]
  transform: {
    '^.+\\.tsx?$': [
      'ts-jest',
      {
        diagnostics: {
          ignoreCodes: [1343]
        },
        astTransformers: {
          before: [
            {
              path: 'node_modules/ts-jest-mock-import-meta',  // or, alternatively, 'ts-jest-mock-import-meta' directly, without node_modules.
              options: { metaObjectReplacement: { url: 'https://www.url.com' } }
            }
          ]
        }
      }
    ]
  }
}

Alternatively, you can use ts-jest-mock-import-meta npm package to fix this issue.

Install

npm install -D ts-jest-mock-import-meta

In jest.config.js

{
  // [...]
  transform: {
    '^.+\\.tsx?$': [
      'ts-jest',
      {
        diagnostics: {
          ignoreCodes: [1343]
        },
        astTransformers: {
          before: [
            {
              path: 'node_modules/ts-jest-mock-import-meta',  // or, alternatively, 'ts-jest-mock-import-meta' directly, without node_modules.
              options: { metaObjectReplacement: { url: 'https://www.url.com' } }
            }
          ]
        }
      }
    ]
  }
}

this did solve the issue. 👌

tried it in an esModule project and the package references above causes an error saying the __filename has already been defined.

There is an open issue on his site with no fix/answer:

ThomZz/ts-jest-mock-import-meta#5

I can't believe after all these years, using modules is still so hard and cumbersome/broken 👎