Reputation: 155
I have two similar functions to create/remove items in an array, and the unit tests are blowing up once I hit the arrayUnion and arrayRemove functions from firestore. The error seems to indicate that I'm skipping my mock providers and trying to use the real thing. Unfortunately I can't figure out what I need to mock to intercept the arrayUnion and arrayRemove calls so they don't cause the error below.
I noticed that in my service, when I import the functions they come from 2 different places but I couldn't quite figure it out.
import { arrayRemove, arrayUnion } from '@angular/fire/firestore';
import { AngularFirestore } from '@angular/fire/compat/firestore';
Error
Error: Either AngularFireModule has not been provided in your AppModule (this can be done manually or implictly using provideFirebaseApp) or you're calling an AngularFire method outside of an NgModule (which is not supported).
service.ts
createCharacterPartyLink(characters: any[], name: string, partyId: string) {
const characterPartyCollectionRef = this.afs.collection<character>('users/' + this.uid + '/Characters/')
characters.forEach((char: any) => {
characterPartyCollectionRef.doc(char.characterid).update(
{ memberOf: arrayUnion({ partyId: partyId, partyName: name }) }
)})}
service.spec.ts
beforeEach(() => {
TestBed.configureTestingModule({
providers: [
{ provide: AngularFirestore, useValue: AngularFirestoreMock },
{ provide: AngularFireAuth, useValue: AngularFireAuthMock }
]
});
service = TestBed.inject(PartyService);
});
it('createCharacterPartyLink Work as Expected', () => {
const updateObj = {
update: function () {
return {
arrayUnion: ()=> {
}}
},
};
const updateSpy = spyOn(updateObj, 'update');
AngularFirestoreMock.collection.and.returnValue({
doc: () => {
return updateObj
}
}
)
service.createCharacterPartyLink(mockPartyMembers, 'Test Party', '1234')
expect(updateSpy).toHaveBeenCalled()
});
Upvotes: 1
Views: 30
Reputation: 155
After coming back to this a few days later, I realized that it had to do with how I was calling the jasmine.createSpyObj in OTHER tests in my spec file. After cleaning up the mocks, the following tests work great for my original service implementation.
arrayUnion spec
it('createCharacterPartyLink Work as Expected', () => {
const updateObj = {
update: function () {
return {
arrayUnion: ()=> {
}}
},
};
const updateSpy = spyOn(updateObj, 'update');
AngularFirestoreMock.collection.and.returnValue({
doc: () => {
return updateObj
}
}
)
service.createCharacterPartyLink(mockPartyMembers, 'Test Party', '1234')
expect(updateSpy).toHaveBeenCalled()
});
arrayRemove spec
it('removeCharacterPartyLink Work as Expected', () => {
const updateObj = {
update: function () {
return {
arrayRemove: ()=> {
}}
},
};
const updateSpy = spyOn(updateObj, 'update');
AngularFirestoreMock.collection.and.returnValue({
doc: () => {
return updateObj
}
}
)
service.removeCharacterPartylink(mockPartyMembers, 'Test Party', '1234')
expect(updateSpy).toHaveBeenCalled()
});
Upvotes: 0