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

expect triggers incompatibility with mocha declarations #8570

Closed
cspotcode opened this issue Jun 15, 2019 · 7 comments · Fixed by #9415
Closed

expect triggers incompatibility with mocha declarations #8570

cspotcode opened this issue Jun 15, 2019 · 7 comments · Fixed by #9415

Comments

@cspotcode
Copy link
Contributor

cspotcode commented Jun 15, 2019

🐛 Bug Report

Trying to use the expect assertion library on a mocha project causes TypeScript errors, even though there should not be any incompatibility.

Both @types/mocha and @jest/types try to declare incompatible global TS declarations for it, describe, etc, which causes TS compiler errors. Obviously users should not try to load both of these at once. However, the expect type declarations refer to @jest/types. This means it's impossible to use the expect assertion library in a project that uses mocha as its test runner.

I think the solution is straightforward:

  1. Refactor @jest/types so it's possible to import @jest/types/no-global which will not augment global interfaces.
  2. Refactor expect to import types from @jest/types/no-global instead of @jest/types

This can be fully backwards compatible.

To Reproduce

Steps to reproduce the behavior:

yarn add @types/node expect @types/mocha typescript
echo "import expect from 'expect';" > index.ts
./node_modules/.bin/tsc --init

Set "types": ["mocha"] in the tsconfig file to avoid eagerly loading unrelated @types.

./node_modules/.bin/tsc --build

You'll see the following TypeScript error:

node_modules/@types/node/globals.d.ts:1032:15 - error TS2430: Interface 'Global' incorrectly extends interface 'MochaGlobals'.
  Types of property 'describe' are incompatible.
    Type 'Describe' is not assignable to type 'SuiteFunction'.
      Types of property 'only' are incompatible.
        Type 'DescribeBase' is not assignable to type 'ExclusiveSuiteFunction'.
          Type 'void' is not assignable to type 'Suite'.

1032     interface Global {
                   ~~~~~~


Found 1 error.

Expected behavior

Importing expect in a TS project does not augment global interfaces with Jest-specific type declarations.

Link to repl or repo (highly encouraged)

https://repl.it/repls/SpanishHugeVirus

Run npx envinfo --preset jest

Paste the results here:

 System:
    OS: Linux 4.9 Pengwin undefined
    CPU: (4) x64 Intel(R) Core(TM) i7-6600U CPU @ 2.60GHz
  Binaries:
    Node: 10.15.2 - /usr/bin/node
    Yarn: 1.16.0 - /usr/bin/yarn
    npm: 6.9.0 - ~/n/bin/npm
@SimenB
Copy link
Member

SimenB commented Jan 14, 2020

reopening as per discussion in #9209

@mgrybyk
Copy link

mgrybyk commented Jan 14, 2020

I had to separate expect from jest types manually in my repo. Of course it's an ugly solution but there are no alternatives at this point https://github.com/webdriverio/expect-webdriverio/blob/master/types/jest-expect-clone/jest-expect.d.ts

It's possible to keep jest and expect types in same repo and access types like this @types/jest/expect or have @types/expect separately, then jest types can have expect types as dependency

@cspotcode
Copy link
Contributor Author

cspotcode commented Jan 15, 2020

I think I figured it out.

Jest is not augmenting NodeJS.Globals, which is great!

However, other type declarations might augment NodeJS.Globals in ways that cause problems for Jest. That's what happens with Mocha's declarations, since they need to declare globals for it, describe, etc.

When Jest tries to declare an interface that extends NodeJS.Globals, we get an error that Jest isn't extending the interface correctly, because (unbeknownst to Jest) Mocha has already added conflicting versions of it, describe, etc.

I think this is the solution, which goes in @jest/types/Global.ts. I haven't extensively tested it.

export interface GlobalAdditions {
    it: ItConcurrent;
    test: ItConcurrent;
    fit: ItBase & {
        concurrent?: ItConcurrentBase;
    };
    xit: ItBase;
    xtest: ItBase;
    describe: Describe;
    xdescribe: DescribeBase;
    fdescribe: DescribeBase;
    __coverage__: CoverageMapData;
    jasmine: Jasmine;
    fail: () => void;
    pending: () => void;
    spyOn: () => void;
    spyOnProperty: () => void;
}
export interface Global extends GlobalAdditions, Omit<NodeJS.Global, keyof GlobalAdditions> {
    [extras: string]: any;
}

By using Omit we make sure that Jest internally ignores anything incompatible that might be added to NodeJS.Global by third-party declarations.

If another jest declaration file really does want to declare globals, it should be able to do something like interface NodeJS.Global extends GlobalAdditions {}

@SimenB
Copy link
Member

SimenB commented Jan 16, 2020

That seems reasonable to me - wanna send a PR with it?

cspotcode added a commit to cspotcode/jest that referenced this issue Jan 16, 2020
@cspotcode cspotcode mentioned this issue Jan 16, 2020
@cspotcode
Copy link
Contributor Author

Sure thing; done.

@jdbruijn
Copy link

I have this same issue, but with the latest versions of jest and mocha.

I've created this repository to reproduce the issue: jdbruijn/jest-mocha-conflict.

It looked to be the same issue as reported here, which was presumably fixed. If it is not, I can open a new issue or something like that.

node --version
v13.13.0

@cspotcode @SimenB

@github-actions
Copy link

This issue has been automatically locked since there has not been any recent activity after it was closed. Please open a new issue for related bugs.
Please note this issue tracker is not a help forum. We recommend using StackOverflow or our discord channel for questions.

@github-actions github-actions bot locked as resolved and limited conversation to collaborators May 11, 2021
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Projects
None yet
Development

Successfully merging a pull request may close this issue.

4 participants