Inizia a utilizzare Firebase Cloud Messaging nelle app Flutter

Seleziona la piattaforma: iOS+ Android Web Flutter Unity C++


Questa guida descrive come iniziare a utilizzare Firebase Cloud Messaging nelle tue app client Flutter in modo da poter inviare messaggi in modo affidabile.

A seconda della piattaforma che hai scelto come target, dovrai eseguire alcuni passaggi di configurazione aggiuntivi.

iOS+

Swizzling del metodo

Per utilizzare il plug-in Flutter FCM sui dispositivi Apple, è necessario lo swizzling del metodo. Senza questa autorizzazione, le funzionalità principali di Firebase, come la gestione della registrazione di FCM, non funzioneranno correttamente.

Android

Google Play Services

I client FCM richiedono dispositivi con Android 7.0 o versioni successive su cui sia installato anche Google Play Services oppure un emulatore con Android 7.0 con le API di Google. Tieni presente che non hai l'obbligo di eseguire il deployment delle tue app per Android tramite il Google Play Store.

Le app che si basano sull'SDK Play Services devono sempre verificare la presenza di un APK Google Play Services compatibile sul dispositivo prima di accedere alle funzionalità di Google Play Services. Ti consigliamo di farlo in due punti: nel metodo onCreate() dell'attività principale e nel relativo metodo onResume(). Il controllo in onCreate() garantisce che l'app non possa essere utilizzata senza un controllo riuscito. Il controllo in onResume() garantisce che, se l'utente torna all'app in esecuzione tramite altri mezzi, ad esempio tramite il pulsante Indietro, il controllo venga comunque eseguito.

Se sul dispositivo non è installata una versione compatibile di Google Play Services, la tua app può chiamare GoogleApiAvailability.makeGooglePlayServicesAvailable() per consentire agli utenti di scaricare Google Play Services dal Play Store.

Web

Configura le credenziali web con FCM

L'interfaccia web di FCM utilizza credenziali web chiamate chiavi VAPID (Voluntary Application Server Identification) per autorizzare le richieste di invio ai servizi di push web supportati. Per iscrivere la tua app alle notifiche push, devi associare una coppia di chiavi al tuo progetto Firebase. Puoi generare una nuova coppia di chiavi o importare la coppia di chiavi esistente tramite la console Firebase.

Installa il plug-in FCM

  1. Se non l'hai ancora fatto, installa e inizializza i plug-in Firebase per Flutter.

  2. Dalla directory principale del progetto Flutter, esegui questo comando per installare il plug-in:

    flutter pub add firebase_messaging
    
  3. Al termine, ricrea l'applicazione Flutter:

    flutter run
    

Richiedi autorizzazione alle notifiche

Per inviare un messaggio di notifica a un dispositivo, devi registrarlo con FCM utilizzando register(). Se l'autorizzazione alle notifiche non è stata concessa, questo metodo la richiederà all'utente. In caso contrario, fornisce l'ID istanza Firebase tramite onRegistered in caso di esito positivo o rifiuta il futuro a causa di un errore.

// You may set the permission requests to "provisional" which allows the user to choose what type
// of notifications they would like to receive once the user receives a notification.
final notificationSettings = await FirebaseMessaging.instance.requestPermission(provisional: true);

// For apple platforms, make sure the APNS token is available before making any FCM plugin API calls
final apnsToken = await FirebaseMessaging.instance.getAPNSToken();
if (apnsToken != null) {
 // APNS token is available, make FCM plugin API requests...
}

Accedi all'ID di installazione Firebase

Abilita la registrazione utilizzando l'ID di installazione Firebase

Per abilitare la registrazione dell'istanza dell'app con FCM utilizzando l'ID installazione di Firebase (FID), devi prima abilitare i FID nella configurazione dell'app per le piattaforme Android e Apple (non è richiesta alcuna configurazione di attivazione statica sul web):

Android

Aggiungi il seguente elemento <meta-data> all'interno dell'elemento <application> del tuo AndroidManifest.xml:

<meta-data android:name="firebase_messaging_installation_id_enabled"
           android:value="true" />

iOS+

Aggiungi la chiave FirebaseMessagingInstallationIdEnabled al tuo Info.plist e impostala su true (YES):

<key>FirebaseMessagingInstallationIdEnabled</key>
<true/>

Iscriviti allo stream onRegistered

Per inviare un messaggio all'istanza dell'app su un dispositivo specifico, devi avere l'ID di installazione Firebase (FID) dell'istanza dell'app dopo che è stata registrata con FCM. Il FID viene fornito in modo asincrono tramite lo stream onRegistered.

Sulle piattaforme Android e Apple, FCM registra automaticamente l'istanza dell'app all'avvio quando l'inizializzazione automatica è abilitata (impostazione predefinita). Tuttavia, è necessaria una chiamata esplicita a register():

  • Sul web. Se vuoi, puoi passare vapidKey e serviceWorkerScriptPath.
  • Sulle piattaforme Android e Apple se l'inizializzazione automatica è disattivata o dopo aver chiamato unregister(). Puoi anche chiamare register() in qualsiasi momento per attivare onRegistered con l'FID già registrato.

Iscriviti sempre a onRegistered prima di chiamare register() in modo che il tuo listener sia attivo quando viene emesso l'evento di registrazione:

final messaging = FirebaseMessaging.instance;

messaging.onRegistered
    .listen((String installationId) {
      // TODO: Send the Firebase Installation ID (FID) to your application server.
    })
    .onError((err) {
      // Error getting Firebase Installation ID.
    });

// Required on Web, and on Android/Apple if auto-initialization is disabled.
await messaging.register(
  // Optional on Web (ignored on Android and Apple platforms)
  vapidKey: "BKagOny0KF_2pCJQ3m....moL0ewzQ8rZu",
);

Lo stream onRegistered emette il FID nei seguenti scenari:

  1. Automaticamente all'avvio iniziale dell'app e alla sincronizzazione di routine sulle piattaforme Android e Apple quando l'inizializzazione automatica è abilitata.
  2. Ogni volta che viene completata una chiamata manuale a register() (anche se l'istanza dell'app è già registrata, onRegistered emette comunque il FID già registrato).
  3. Ogni volta che viene rilevata una modifica dell'ID di installazione Firebase e l'app viene registrata di nuovo con FCM o sul web quando viene attivato un evento pushsubscriptionchange.

Dopo aver ottenuto l'ID installazione di Firebase (FID), invialo al server dell'app e memorizzalo utilizzando il metodo che preferisci.

Accedi al token di registrazione (deprecato)

Per inviare un messaggio a un dispositivo specifico, devi conoscere il token di registrazione del dispositivo. Per recuperare il token di registrazione per un'istanza dell'app, chiama getToken(). Se l'autorizzazione alle notifiche non è stata concessa, questo metodo chiederà all'utente le autorizzazioni alle notifiche. In caso contrario, restituisce un token o rifiuta il future a causa di un errore.

Sulle piattaforme web, passa la tua chiave pubblica VAPID a getToken():

final fcmToken = await FirebaseMessaging.instance.getToken(vapidKey: "BKagOny0KF_2pCJQ3m....moL0ewzQ8rZu");

Per ricevere una notifica ogni volta che il token viene aggiornato, iscriviti allo stream onTokenRefresh:

FirebaseMessaging.instance.onTokenRefresh
    .listen((fcmToken) {
      // TODO: If necessary send token to application server.

      // Note: This callback is fired at each app startup and whenever a new
      // token is generated.
    })
    .onError((err) {
      // Error getting token.
    });

Impedisci l'inizializzazione automatica

Quando viene generata una registrazione FCM, la libreria carica l'identificatore e i dati di configurazione su Firebase. Se preferisci impedire la registrazione automatica, disattiva l'inizializzazione automatica in fase di build.

Quando l'inizializzazione automatica è disattivata, puoi registrare esplicitamente l'istanza dell'app in fase di runtime chiamando register() (assicurati di iscriverti prima a onRegistered per ricevere l'ID di installazione Firebase):

await FirebaseMessaging.instance.register();

iOS

Su iOS, aggiungi un valore dei metadati al tuo Info.plist:

FirebaseMessagingAutoInitEnabled = NO

Android

Su Android, disattiva la raccolta di Analytics e l'inizializzazione automatica di FCM (devi disattivarle entrambe) aggiungendo questi valori dei metadati a AndroidManifest.xml:

<meta-data
    android:name="firebase_messaging_auto_init_enabled"
    android:value="false" />
<meta-data
    android:name="firebase_analytics_collection_enabled"
    android:value="false" />

Riattiva l'inizializzazione automatica di FCM in fase di runtime

Per attivare l'inizializzazione automatica per un'istanza dell'app specifica, chiama setAutoInitEnabled():

await FirebaseMessaging.instance.setAutoInitEnabled(true);

Una volta impostato, questo valore viene mantenuto anche dopo il riavvio dell'app.

Invia un messaggio di notifica di prova

  1. Installa ed esegui l'app sul dispositivo di destinazione. Sui dispositivi Apple, dovrai accettare la richiesta di autorizzazione per ricevere notifiche remote.

  2. Assicurati che l'app sia in background sul dispositivo.

  3. Nella console Firebase, vai a DevOps e coinvolgimento > Messaggistica.

  4. Creare una campagna.

    • Se è il tuo primo messaggio:

      1. Seleziona Crea la tua prima campagna.

      2. Seleziona Messaggi di notifica Firebase e poi Crea.

    • Se hai già creato campagne:

      1. Nella scheda Campagne, seleziona Nuova campagna.

      2. Fai clic su Notifiche.

  5. Inserisci il testo del messaggio.

  6. Seleziona Invia messaggio di prova nel riquadro a destra.

  7. Nel campo Aggiungi un ID di installazione Firebase o un token di registrazione FCM, inserisci l'ID di installazione Firebase o il token di registrazione.

  8. Seleziona Test.

Dopo aver selezionato Test, il dispositivo client scelto come target, con l'app in background, dovrebbe ricevere la notifica.

Per informazioni sulla distribuzione dei messaggi alla tua app, vai alla dashboard DevOps e coinvolgimento > Messaggistica > Report nella console Firebase. Questa dashboard registra il numero di messaggi inviati e aperti su dispositivi Apple e Android, insieme ai dati relativi alle "impressioni" (notifiche visualizzate dagli utenti) per le app per Android.

Gestione dell'interazione

Quando gli utenti toccano una notifica, il comportamento predefinito sia su Android che su iOS è l'apertura dell'applicazione. Se l'applicazione viene terminata, verrà avviata, mentre se è in background, verrà portata in primo piano.

A seconda dei contenuti di una notifica, potresti voler gestire l'interazione dell'utente all'apertura dell'applicazione. Ad esempio, se un nuovo messaggio chat viene inviato utilizzando una notifica e l'utente lo seleziona, potresti voler aprire la conversazione specifica quando si apre l'applicazione.

Il pacchetto firebase-messaging offre due modi per gestire questa interazione:

  1. getInitialMessage(): Se l'applicazione viene aperta da uno stato terminato, questo metodo restituisce un Future contenente un RemoteMessage. Una volta consumato, RemoteMessage verrà rimosso.
  2. onMessageOpenedApp: un Stream che pubblica un RemoteMessage quando l'applicazione viene aperta da uno stato in background.

Per garantire un'esperienza ottimale agli utenti, devi gestire entrambi gli scenari. Il seguente esempio di codice illustra come ottenere questo risultato:

class Application extends StatefulWidget {
  @override
  State createState() => _Application();
}

class _Application extends State {
  // In this example, suppose that all messages contain a data field with the key 'type'.
  Future setupInteractedMessage() async {
    // Get any messages which caused the application to open from
    // a terminated state.
    RemoteMessage? initialMessage =
        await FirebaseMessaging.instance.getInitialMessage();

    // If the message also contains a data property with a "type" of "chat",
    // navigate to a chat screen
    if (initialMessage != null) {
      _handleMessage(initialMessage);
    }

    // Also handle any interaction when the app is in the background using a
    // Stream listener
    FirebaseMessaging.onMessageOpenedApp.listen(_handleMessage);
  }

  void _handleMessage(RemoteMessage message) {
    if (message.data['type'] == 'chat') {
      Navigator.pushNamed(context, '/chat',
        arguments: ChatArguments(message),
      );
    }
  }

  @override
  void initState() {
    super.initState();

    // Run code required to handle interacted messages in an async function
    // as initState() must not be async
    setupInteractedMessage();
  }

  @override
  Widget build(BuildContext context) {
    return Text("...");
  }
}

La gestione dell'interazione dipende dalla configurazione. L'esempio mostrato in precedenza è un esempio di base dell'utilizzo di un StatefulWidget.

Passaggi successivi

Dopo aver completato i passaggi di configurazione, ecco alcune opzioni per procedere con FCM per Flutter: