We started using the very nice ng-mocks for our test, but I have trouble getting the mock injection right for this case:
OurServicethat uses theDatetimeServiceandNumberFormatterService.NumberFormatterServicealso uses theDatetimeService.DatetimeServiceshould be mocked.
Does sound that complicated, or?
Here's the (simplyfied) code:
describe('OurService', () => {
MockInstance.scope();
let service: OurService;
beforeEach(async () => {
MockInstance(DatetimeService, 'locale', () => 'en-US');
await MockBuilder(OurService)
.mock(DatetimeService)
.provide(NumberFormatterService);
service = TestBed.inject(OurService);
});
it('should be created', () => {
expect(service).toBeTruthy();
});
test('test setup is correct', () => {
expect(TestBed.inject(DatetimeService).locale()).toEqual('en-US'); // works
expect(service.datetimeService.locale()).toEqual('en-US'); // works
expect(service.numberFormatter.datetimeService.locale()).toEqual('en-US'); // <== this fails, locale is undefined
});
});
When I debug and have a breakpoint inside locale(), it gets called for the first two expect() lines, but not for the third. In this case simply undefined is returned. Which surprises me, as this must be some plain mock and not the one modified by MockInstance - and also not the original service.
Any idea or suggestion how to get this right?
Of course, I could work around and mock the NumberFormatterService here, but in this case I'd like to keep the original implementation to check that the services work together correctly.
In case it matters: We use jest. And here are the versions we use:
"jest": "^29.7.0",
"jest-preset-angular": "14.0.0",
"@nx/jest": "17.2.8",
"ng-mocks": "^14.12.1",
"@angular/core": "17.1.0",
As noted in the comment, this issue seems to happen only sometimes.