I've defined a FooService
as follows
import {Injectable} from "@angular/core";
export interface Foo {
Foo(): string;
}
@Injectable()
export class FooService implements Foo {
Foo(): string {
return "Fooey!";
}
}
and a BarComponent
like this
import {Component} from "@angular/core";
import {FooService} from "./foo.service";
@Component({
moduleId: 'module.id',
template: '<h1>Bar Component</h1>'
})
export class BarComponent {
constructor(private fooService: FooService) {}
doFoo(): string {
return(this.fooService.Foo());
}
}
Now I want to test my BarComponent
and I'd like to use TypeMoq
to mock the FooService
, so I did the following
import * as TypeMoq from 'typemoq';
import {Foo, FooService} from "./foo.service";
import {TestBed, async} from "@angular/core/testing";
import {BarComponent} from "./bar.component";
describe('BarComponent', () => {
let component: BarComponent;
let mockFooService: TypeMoq.IMock<Foo>;
beforeEach(async(() => {
mockFooService = TypeMoq.Mock.ofType<Foo>();
TestBed.configureTestingModule({
declarations: [BarComponent],
providers: [{ provide: FooService, useValue: mockFooService.object}]
});
}));
beforeEach(() => {
let fixture = TestBed.createComponent(BarComponent);
component = fixture.componentInstance;
});
it('does something', () => {
mockFooService.setup(x => x.Foo()).returns(() => "FooBar!");
expect(component.doFoo()).toEqual("FooBar!");
});
});
However running the above gives the following error
SyntaxError: Function arg string contains parenthesis
at new Function (<anonymous>)
at evalExpression (webpack:///~/@angular/compiler/@angular/compiler.es5.js:25431:25 <- config/karma-test-shim.js:59412:40)
at jitStatements (webpack:///~/@angular/compiler/@angular/compiler.es5.js:25448:0 <- config/karma-test-shim.js:59429:12)
at JitCompiler._compileModule (webpack:///~/@angular/compiler/@angular/compiler.es5.js:25658:0 <- config/karma-test-shim.js:59639:35)
at createResult (webpack:///~/@angular/compiler/@angular/compiler.es5.js:25613:0 <- config/karma-test-shim.js:59594:106)
at JitCompiler._compileModuleAndAllComponents (webpack:///~/@angular/compiler/@angular/compiler.es5.js:25616:0 <- config/karma-test-shim.js:59597:40)
at JitCompiler.compileModuleAndAllComponentsSync (webpack:///~/@angular/compiler/@angular/compiler.es5.js:25559:0 <- config/karma-test-shim.js:59540:23)
at TestingCompilerImpl.compileModuleAndAllComponentsSync (webpack:///~/@angular/compiler/@angular/compiler/testing.es5.js:475:0 <- config/karma-test-shim.js:68201:31)
at TestBed._initIfNeeded (webpack:///~/@angular/core/@angular/core/testing.es5.js:705:0 <- config/karma-test-shim.js:21376:36)
at TestBed.createComponent (webpack:///~/@angular/core/@angular/core/testing.es5.js:791:0 <- config/karma-test-shim.js:21462:14)
at Function.TestBed.createComponent (webpack:///~/@angular/core/@angular/core/testing.es5.js:610:0 <- config/karma-test-shim.js:21281:29)
at Object.<anonymous> (webpack:///src/app/auth/login/bar.component.spec.ts:19:30 <- config/karma-test-shim.js:99954:41)
at ZoneDelegate.invoke (webpack:///~/zone.js/dist/zone.js:365:0 <- config/karma-test-shim.js:65763:26)
at ProxyZoneSpec.onInvoke (webpack:///~/zone.js/dist/proxy.js:79:0 <- config/karma-test-shim.js:65294:39)
at ZoneDelegate.invoke (webpack:///~/zone.js/dist/zone.js:364:0 <- config/karma-test-shim.js:65762:32)
at Zone.run (webpack:///~/zone.js/dist/zone.js:125:0 <- config/karma-test-shim.js:65523:43)
at Object.<anonymous> (webpack:///~/zone.js/dist/jasmine-patch.js:104:0 <- config/karma-test-shim.js:65010:34)
at webpack:///~/@angular/core/@angular/core/testing.es5.js:96:0 <- config/karma-test-shim.js:20767:17
at ZoneDelegate.invoke (webpack:///~/zone.js/dist/zone.js:365:0 <- config/karma-test-shim.js:65763:26)
at AsyncTestZoneSpec.onInvoke (webpack:///~/zone.js/dist/async-test.js:49:0 <- config/karma-test-shim.js:64605:39)
at ProxyZoneSpec.onInvoke (webpack:///~/zone.js/dist/proxy.js:76:0 <- config/karma-test-shim.js:65291:39)
at ZoneDelegate.invoke (webpack:///~/zone.js/dist/zone.js:364:0 <- config/karma-test-shim.js:65762:32)
at Zone.run (webpack:///~/zone.js/dist/zone.js:125:0 <- config/karma-test-shim.js:65523:43)
at AsyncTestZoneSpec._finishCallback (webpack:///~/@angular/core/@angular/core/testing.es5.js:91:0 <- config/karma-test-shim.js:20762:25)
at webpack:///~/zone.js/dist/async-test.js:38:0 <- config/karma-test-shim.js:64594:31
at ZoneDelegate.invokeTask (webpack:///~/zone.js/dist/zone.js:398:0 <- config/karma-test-shim.js:65796:31)
at Zone.runTask (webpack:///~/zone.js/dist/zone.js:165:0 <- config/karma-test-shim.js:65563:47)
at ZoneTask.invoke (webpack:///~/zone.js/dist/zone.js:460:0 <- config/karma-test-shim.js:65858:38)
at timer (webpack:///~/zone.js/dist/zone.js:1732:0 <- config/karma-test-shim.js:67130:29)
Is it possible to use TypeMoq
's with the angular TestBed
and if so how do you do it correctly?
I was running into this also, it's coming in because of how you're doing your providers.
Change
providers: [{ provide: FooService, useValue: mockFooService.object}]
to
providers: [{ provide: FooService, useFactory: () => { return mockFooService.object } }]
Using the factory function to return got rid of errors for me. If you use useClass you'll get an error about param.map is not a function, and if you use useValue you get an error about unexpected parenthesis. useFactory and just an inline function that returns the moq.object works, though.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With