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

MockedFunction type doesn't overlap the type of generic functions #1781

Open
6 tasks done
danielelkington opened this issue Aug 4, 2022 · 3 comments
Open
6 tasks done
Labels
help wanted Extra attention is needed types

Comments

@danielelkington
Copy link

Describe the bug

Sometimes we need to extend a TypeScript interface, replacing functions with mocked versions (that are eventually created with vi.fn()).
This works with most functions, but not with generic functions. It used to work up until Vitest 0.15.2, but broke in 0.16.0 and is still broken as-of 0.20.3.

Reproduction

import { MockedFunction } from 'vitest'

interface MyInterface {
  someFunction<T>(a: number): T
}

// TS error on the next line from Vitest 0.16.0:
// Interface 'MyMockedInterface' incorrectly extends interface 'MyInterface'.
// The types returned by 'someFunction(...)' are incompatible between these types
interface MyMockedInterface extends MyInterface {
  someFunction: MockedFunction<MyInterface['someFunction']>
}

System Info

System:
    OS: Windows 10 10.0.19044
    CPU: (8) x64 Intel(R) Core(TM) i7-8565U CPU @ 1.80GHz
    Memory: 2.90 GB / 15.81 GB
  Binaries:
    Node: 16.14.2 - C:\Program Files\nodejs\node.EXE
    Yarn: 1.22.18 - C:\Program Files\nodejs\yarn.CMD
    npm: 8.5.0 - C:\Program Files\nodejs\npm.CMD
  Browsers:
    Chrome: 103.0.5060.114
    Edge: Spartan (44.19041.1266.0), Chromium (103.0.1264.77)
    Internet Explorer: 11.0.19041.1566
  npmPackages:
    @vitejs/plugin-vue: ^2.2.0 => 2.2.4
    vite: ^2.9.12 => 2.9.12
    vitest: ^0.16.0 => 0.16.0

Used Package Manager

npm

Validations

@sheremet-va
Copy link
Member

sheremet-va commented Aug 4, 2022

Don't use MockedFunction as a type (it's not a return type for vi.fn). Use Mock/MockInstance. We should remove these types from exports I guess. They are for MaybeMocked.


Hm, I got confused, never mind the above. Still, I don't see types working as you expect in 0.15.2. Are you sure you are not updating typescript at the same time as Vitest?

@danielelkington
Copy link
Author

If I downgrade to Vitest 0.15.2 but leave everything else the same, the code in the reproduction works. Note that I have to restart the TypeScript server or else restart Visual Studio Code to refresh everything after downgrading the Vitest version.

@sheremet-va sheremet-va added types help wanted Extra attention is needed labels Aug 8, 2022
@KevBeltrao
Copy link

This error is because of the mismatch between the return values of both someFunction(). I believe they should have the same return type. I didn't try this code, but have you considered adding the generic to MyMockedInterface's someFunction? It'd look like:

interface MyInterface {
  someFunction<T>(a: number): T;
}

interface MyMockedInterface extends MyInterface {
  someFunction: <T>(...params: Parameters<MyInterface['someFunction']>) => ReturnType<MockedFunction<() => T>>;
}

Notice what I'm doing is, instead of just passing MockedFunction, declaring a function type with its return type being the ReturnType of MockedFunction.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
help wanted Extra attention is needed types
Projects
None yet
Development

No branches or pull requests

3 participants