Skip to content

Calling a cloud function registers the default service worker for messaging (possibly failing) #5194

Open
@cairomassimo

Description

@cairomassimo

[REQUIRED] Describe your environment

  • Operating System version: Ubuntu
  • Browser version: Google Chrome 91.0.4472.114
  • Firebase SDK version: 8.8.0
  • Firebase Product: functions, messaging (auth, database, storage, etc)

[REQUIRED] Describe the problem

Steps to reproduce:

  1. Initialize messaging
  2. Grant browser notifications permission
  3. Call firebase.functions().httpsCallable('my-function')()
  4. Observe attempted service worker registration (e.g. in devtools)

The first two steps ensure that the following check passes:

if (
!this.messaging ||
!('Notification' in self) ||
Notification.permission !== 'granted'
) {

The third step results in a call to messaging.getToken() which in turn tries to register the default service worker.

try {
return await this.messaging.getToken();
} catch (e) {
// We don't warn on this, because it usually means messaging isn't set up.
// console.warn('Failed to retrieve instance id token.', e);
// If there's any error when trying to get the token, leave it off.
return undefined;
}

Notice that getToken is invoked without arguments, giving no chance to specify the serviceWorkerRegistration parameter.

This is undesirable because:

  • the app may be using a custom service worker for notifications, registered somewhere else,
  • notifications and a service worker may not be needed when the code is run (despite permission granted and library loaded), e.g. during development,
  • the call may log an error on the console, due to the default service worker being unavailable, completely unrelated to the triggering code (e.g. firebase.functions().httpsCallable),
  • in general, the call results in unexpected side effects (e.g., an extra HTTP call), depending on heuristic condititions (the if check above).

All the above apply in my use case.

Invoking messaging.useServiceWorker could mitigate the issue, but it does not cover the case where the service worker is not yet available, or no service worker at all is used (and the method is deprecated).

Possible solutions

  • add an extra option to httpsCallable to specify that the messaging token is not needed in the function context (easy fix?)
  • avoid calling getToken altogether, and only provide the token if a call to getToken was performed explicitly (may break existing code, if it relies on the token being present in the function call context)
  • other options?

Metadata

Metadata

Assignees

No one assigned

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions