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

Angular test with mocked provider throws error "Can't resolve all parameters for mockConstructor(?)." #1227

Closed
artemrudenko opened this issue Sep 13, 2019 · 4 comments

Comments

@artemrudenko
Copy link

artemrudenko commented Sep 13, 2019

Issue

As mentioned in jestjs/jest#8401:

In Angular tests we're using mocks as providers like this:

{ provide: SomeClass, useClass: jest.fn(() => someImplementation) }

Angular creates a new instance of the mock when being asked to provide a SomeClass instance. This used to work fine in jest 23.x but in jest 24.x the mockConstructor now has a parameter. Angular looks at the constructor parameters and tries to inject a value for that parameter which fails with the error Can't resolve all parameters for mockConstructor: (?)..

There are some workarounds for this (like using useValue instead of useClass and create a new instance yourself) but I couldn't find anything about this issue anywhere else and it took quite some time to debug.

After some investigations, we found that this issue isn't reproducible with jest and babel and have place only with the latest jest24 and ts-jest.

Minimal repo

https://github.com/artemrudenko/jest-angular-ts-jest-issue

To Reproduce

Steps to reproduce the behavior:
yarn to install all dependencies
yarn test data to run data.service test

Current output:

Can't resolve all parameters for mockConstructor: (?).
      at syntaxError (../packages/compiler/src/util.ts:100:17)
      at CompileMetadataResolver._getDependenciesMetadata (../packages/compiler/src/metadata_resolver.ts:956:27)
      at CompileMetadataResolver._getTypeMetadata (../packages/compiler/src/metadata_resolver.ts:836:20)
      at CompileMetadataResolver._getInjectableTypeMetadata (../packages/compiler/src/metadata_resolver.ts:1088:17)
      at CompileMetadataResolver.getProviderMetadata (../packages/compiler/src/metadata_resolver.ts:1099:16)
      at ../packages/compiler/src/metadata_resolver.ts:1020:38

Expected behavior

Provide a mock without failing

@wtho
Copy link
Contributor

wtho commented Oct 2, 2019

This is probably not ts-jest-related, see thymikee/jest-preset-angular#288


To give more background: this is related to a missing reflect-metadata polyfill (see packages as core-js/es7/reflect or reflect-metadata) or, if these are included, the missing typescript compile option emitDecoratorMetadata: true. See thymikee/jest-preset-angular#314 for more background.

@artemrudenko
Copy link
Author

@wtho no, unfortunately, this is not related to emitDecorators. Here is an issue of how angular resolving dependencies while building the testing module. What has changed in jest itself is migration to typescript which causes jest-mock module to produce a bit diff output for matchArity. This case is closely related to jestjs/jest#8401

@wtho
Copy link
Contributor

wtho commented Oct 12, 2019

I see. Looking at the Angular docs there is only an example with an TypeScript class being used as useClass argument. I do not think you should use custom functions or functions of third libraries and then expect no changes there, as it is clearly not the recommended way. The way they get provided may clearly differ from the default TS compilation steps and create difficulties.

I recommend you to use useValue or wrap your mocks inside a class as done in the official example.

@ahnpnl
Copy link
Collaborator

ahnpnl commented Feb 3, 2020

I agree with @wtho, useValue or useFactory should be used instead. This is not ts-jest issue but rather than using correctly Angular TestBed.

  • useClass always accepts a class, means it has pure es6 js class with class keyword
  • useValue is usually for pure value like {} or { <mock_classproperty>: <mock_value> }

@ahnpnl ahnpnl closed this as completed Feb 3, 2020
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

3 participants