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

[Bug]: Inconsistent hybrid module resolution (index.d.mts vs. index.d.cts) between ts-jest and tsc #4221

Open
chriswheeldon-peakon opened this issue Oct 26, 2023 · 3 comments

Comments

@chriswheeldon-peakon
Copy link

chriswheeldon-peakon commented Oct 26, 2023

Version

29.1.1

Steps to reproduce

Clone my repo and follow the instructions in the README: https://github.com/chriswheeldon-peakon/ts-jest-moduleResolution

Expected behavior

I expect ts-jest to resolve hybrid modules, publishing both d.mts and d.cts declaration files, in the same manner as the typescript compiler.

Actual behavior

ts-jest is resolving an imported hybrid module to the d.cts artefact whereas tsc is resolving it to the d.mts artefact.

I'm new to both codebases, but I've been tracing the module resolution locally and found that tsc and ts-jest invoke TypeScript's resolveModuleName function differently. tsc passes ModuleKind.ESNext as the final resolutionMode argument whereas ts-jest does not pass the argument at all.

I'm having some difficulty determining the exact logic that tsc uses to decide the resolutionMode argument but if I force the resolutionMode to ESNext in ts-jest then the tests are built successfully.

Debug log

ts-jest.log

Additional context

No response

Environment

System:
    OS: macOS 13.6
    CPU: (16) x64 Intel(R) Core(TM) i9-9880H CPU @ 2.30GHz
  Binaries:
    Node: 18.18.2 - /var/folders/sb/jdkc4cv91zvgvvzwhq9lyc6w0000gp/T/fnm_multishells/15362_1698336664355/bin/node
    Yarn: 1.22.19 - /usr/local/bin/yarn
    npm: 9.8.1 - /var/folders/sb/jdkc4cv91zvgvvzwhq9lyc6w0000gp/T/fnm_multishells/15362_1698336664355/bin/npm
  npmPackages:
    jest: ^29.6.2 => 29.6.2
@chriswheeldon-peakon chriswheeldon-peakon changed the title [Bug]: Inconsistent hybird module resolution (index.d.mts vs. index.d.cts) between ts-jest and tsc [Bug]: Inconsistent hybrid module resolution (index.d.mts vs. index.d.cts) between ts-jest and tsc Oct 26, 2023
@vekexasia
Copy link

out of curioisty how do you force to esnext?

@chriswheeldon-peakon
Copy link
Author

@vekexasia

diff --git a/src/legacy/compiler/ts-compiler.ts b/src/legacy/compiler/ts-compiler.ts
index 5ef5f3df8..1b65722b0 100644
--- a/src/legacy/compiler/ts-compiler.ts
+++ b/src/legacy/compiler/ts-compiler.ts
@@ -402,6 +402,8 @@ export class TsCompiler implements TsCompilerInstance {
       this._moduleResolutionHost!,
       // eslint-disable-next-line @typescript-eslint/no-non-null-assertion
       this._moduleResolutionCache!,
+      undefined,
+      this._ts.ModuleKind.ESNext,
     )
   }

@chriswheeldon-peakon
Copy link
Author

chriswheeldon-peakon commented Nov 1, 2023

I managed to work around this (without modifying the ts-jest source) by using a local declaration file that forces resolution to the d.mts export from helmet:

/// <reference path="./node_modules/helmet/index.d.mts" />

declare module "helmet" {
  export default helmet;
  export * from "helmet";
}

I've applied to the same kind of workaround successfully to two other hybrid modules that confuse ts-jest.

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

No branches or pull requests

2 participants