【问题标题】:FirebaseError: Messaging: This browser doesn't support the API's required to use the firebase SDK. (messaging/unsupported-browser)FirebaseError:消息:此浏览器不支持使用 firebase SDK 所需的 API。 (消息/不支持的浏览器)
【发布时间】:2020-07-11 16:29:54
【问题描述】:

我正在开发适用于 Android 和 iOS 的 Ionic 5 应用程序。我正在使用 angularfire https://github.com/angular/angularfire/tree/v5 并且遇到了一些问题。特别是,这个库在使用 Firestore 时运行良好,但是当我尝试使用 Cloud Messaging 在我的 Android 设备上接收通知时,它会引发错误:FirebaseError: Messaging: This browser does not support the API's required to use Firebase SDK。 (消息/不支持的浏览器)。我按照此处链接的 GitHub 存储库上提供的教程进行操作,并尝试在浏览器上使用它,它工作正常。我怀疑这个库不能与 Ionic 一起正常工作,因此可以使用某些服务,例如 Firestore,而其他服务则不能。有人有解决这个问题的想法吗?下面是我的服务代码的sn-p:

import { Injectable } from '@angular/core';
import { AngularFireMessaging } from '@angular/fire/messaging';
import { AngularFireFunctions } from '@angular/fire/functions';
import { ToastController } from '@ionic/angular';

/* //Fixing temporary bug in AngularFire - Found on Internet
import * as app from 'firebase';
const _messaging = app.messaging();
_messaging.onTokenRefresh = _messaging.onTokenRefresh.bind(_messaging);
_messaging.onMessage = _messaging.onMessage.bind(_messaging); */

@Injectable({
  providedIn: 'root'
})
export class FcmService {
  token: any; 

  constructor(private toastController: ToastController, private afm: AngularFireMessaging, private aff: AngularFireFunctions) { }

  async makeToast(message: string){
    const toast = await this.toastController.create({
      duration: 5000,
      message: message,
      position: 'top',
      buttons: [
        {
          side: 'end',
          text: 'Close',
          role: 'cancel',
          handler: () => {
            console.log('Favorite clicked');
          }
        }]
    });
    toast.present();
  }

  getPermission(){
    this.afm.requestToken
      .subscribe(
        (token) => { console.log('Permission granted! Save to the server!', token); this.token = token;},
        (error) => { console.error(error); },  
      );
  }

  showMessages(){
    return this.afm.messages
      .subscribe(
        (message) => {console.log(message);}
      );
  }

  subscribe(topic: string){
    this.aff.httpsCallable('subscribeToTopic')({topic: topic, token: this.token})
      .subscribe(
        (_) => {this.makeToast("Notifications about "+topic+" activated.")},
        (error) => {console.log(error)},
      );
  }

  unsubscribe(topic: string){
    this.aff.httpsCallable('unsubscribeFromTopic')({topic: topic, token: this.token})
      .subscribe(
        (_) => {this.makeToast("Notifications about "+topic+" deactivated.")},
        (error) => {console.log(error)},
      );
  }
}

谢谢!

【问题讨论】:

    标签: firebase ionic-framework firebase-cloud-messaging angularfire


    【解决方案1】:

    经过大量研究,我终于找到了解决方案。我在这里发布它,以便将来可以解决类似的问题。这里https://caniuse.com/#feat=push-api,正如Doug Stevenson 所建议的,列出了支持的浏览器。 https://developer.chrome.com/multidevice/webview/overview 在其中一个常见问题解答中指出,Android WebView 基于 Chrome for Android 版本 30.0.0,不受支持。因此,我不得不使用名为 FirebaseX 的 Cordova 插件:

    ionic cordova plugin add cordova-plugin-firebasex
    npm install @ionic-native/firebase-x
    

    这也需要另外两个插件:

    ionic cordova plugin add cordova-plugin-androidx
    ionic cordova plugin add cordova-plugin-androidx-adapter
    

    并且您的应用在 Firebase 控制台中同时注册为 Android 和 iOS,这会为您提供两个要包含在项目根文件夹中的文件:google-services.jsonGoogleService-Info.plist。添加此类插件后,运行以下命令(可能不需要,但建议使用):

    cordova clean
    ionic cordova build android
    

    在最后一个命令中,我遇到了另一个问题:任务':app:transformDexArchiveWithExternalLibsDexMergerForDebug'的执行失败。我按照本指南解决了这个问题:https://developer.android.com/studio/build/multidex#mdex-gradle。 (我刚刚添加了multiDexEnabled true,也许有一种方法可以默认包含它,顺便说一句)。它现在可以工作了,尽管我必须以以下方式调整我的代码以使用 FirebaseX 执行 requestToken 操作:

    import { Injectable } from '@angular/core';
    import { AngularFireMessaging } from '@angular/fire/messaging';
    import { AngularFireFunctions } from '@angular/fire/functions';
    import { ToastController, Platform } from '@ionic/angular';
    import { FirebaseX } from "@ionic-native/firebase-x/ngx";
    
    /* //Fixing temporary bug in AngularFire - Found on Internet
    import * as app from 'firebase';
    const _messaging = app.messaging();
    _messaging.onTokenRefresh = _messaging.onTokenRefresh.bind(_messaging);
    _messaging.onMessage = _messaging.onMessage.bind(_messaging); */
    
    @Injectable({
      providedIn: 'root'
    })
    export class FcmService {
      token: any; 
    
      constructor(private toastController: ToastController, private afm: AngularFireMessaging, private aff: AngularFireFunctions, private platform: Platform,
        private firebase: FirebaseX) { }
    
      async makeToast(message: string){
        const toast = await this.toastController.create({
          duration: 5000,
          message: message,
          position: 'top',
          buttons: [
            {
              side: 'end',
              text: 'Close',
              role: 'cancel',
              handler: () => {
                console.log('Favorite clicked');
              }
            }]
        });
        toast.present();
      }
    
      async getPermission(){
        if (this.platform.is("android")){
          this.firebase.getToken().then(
            (token) => console.log(token)
          );
        } else {
          await this.afm.requestToken
          .subscribe(
            (token) => { console.log('Permission granted! Save to the server!', token); this.token = token;},
            (error) => { console.error(error); },  
          );
        }
      }
    
      showMessages(){
        return this.afm.messages
          .subscribe(
            (message) => {console.log(message);}
          );
      }
    
      subscribe(topic: string){
        this.aff.httpsCallable('subscribeToTopic')({topic: topic, token: this.token})
          .subscribe(
            (_) => {this.makeToast("Notification about "+topic+" activated.")},
            (error) => {console.log(error)},
          );
      }
    
      unsubscribe(topic: string){
        this.aff.httpsCallable('unsubscribeFromTopic')({topic: topic, token: this.token})
          .subscribe(
            (_) => {this.makeToast("Notification about "+topic+" deactivated.")},
            (error) => {console.log(error)},
          );
      }
    }

    谢谢你,Doug,不知何故你帮助我度过了难关!

    【讨论】:

      【解决方案2】:

      main documentation page 上,它声明:

      FCM JavaScript API 可让您在网络中接收通知消息 在支持 Push API 的浏览器中运行的应用程序。这包括 此support matrix 中列出的浏览器版本和 Chrome 扩展 通过 Push API。

      如果您导航到支持矩阵的链接,您会发现您的浏览器是否支持推送 API。如果您尝试在不受支持的浏览器上使用 FCM,您将收到该消息。您需要确定主机操作系统是否支持此 API。

      【讨论】:

      • 我已经检查过了,但 Android WebView 甚至没有列出。也许我应该为推送通知使用不同的插件。
      • 我相信 Android 列在“Android 浏览器”下,但我可能弄错了。请更新您的问题,以更清楚您的具体情况。你是如何使用 Android 的 webview 来实现的?
      • 当您在 Android 上运行 Ionic 应用程序时,它使用 developer.chrome.com/multidevice/webview/overview 来呈现应用程序的内容。在 iOS 上也是类似的。当我在我的 Google Chrome (PC) 上运行 Ionic 应用程序时,它运行良好,在 Opera 和 Firefox 上也是如此,但在 Android 上它会引发上述错误。
      猜你喜欢
      • 2021-04-10
      • 2010-09-25
      • 1970-01-01
      • 2018-03-27
      • 1970-01-01
      • 1970-01-01
      • 2017-07-16
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多