diff --git a/src/messaging/messaging-api-request.ts b/src/messaging/messaging-api-request.ts index d9e523aac2..447050bb37 100644 --- a/src/messaging/messaging-api-request.ts +++ b/src/messaging/messaging-api-request.ts @@ -43,9 +43,18 @@ export class FirebaseMessagingRequestHandler { */ private static getErrorCode(response: any): string | null { if (validator.isNonNullObject(response) && 'error' in response) { - if (typeof response.error === 'string') { + if (validator.isString(response.error)) { return response.error; - } else if ('status' in response.error) { + } + if (validator.isArray(response.error.details)) { + const fcmErrorType = 'type.googleapis.com/google.firebase.fcm.v1.FcmErrorCode'; + for (const element of response.error.details) { + if (element['@type'] === fcmErrorType) { + return element.errorCode; + } + } + } + if ('status' in response.error) { return response.error.status; } else { return response.error.message; diff --git a/test/unit/messaging/messaging.spec.ts b/test/unit/messaging/messaging.spec.ts index b848897695..fb92409f7c 100644 --- a/test/unit/messaging/messaging.spec.ts +++ b/test/unit/messaging/messaging.spec.ts @@ -419,6 +419,26 @@ describe('Messaging', () => { .and.have.property('code', 'messaging/invalid-argument'); }); + it('should fail when the backend server returns a detailed error with FCM error code', () => { + const resp = { + error: { + status: 'INVALID_ARGUMENT', + message: 'test error message', + details: [ + { + '@type': 'type.googleapis.com/google.firebase.fcm.v1.FcmErrorCode', + 'errorCode': 'UNREGISTERED', + }, + ], + }, + }; + mockedRequests.push(mockSendError(404, 'json', resp)); + return messaging.send( + {token: 'mock-token'}, + ).should.eventually.be.rejectedWith('test error message') + .and.have.property('code', 'messaging/registration-token-not-registered'); + }); + it('should map server error code to client-side error', () => { const resp = { error: {