如何从请求中检索通知/数据



我正在尝试使用Firebase Cloud Messaging发送基本通知,但我无法为我的生活弄清楚如何在通知中包含任何实际内容。

我基本上是从这里可以找到的一个精简版本开始的。我有三份文件,一份清单。Json,看起来像这样:

{ "gcm_sender_id": "my sender id" }

一个index.html,看起来像这样:

<html>                                                                                                  
  <head><link rel="manifest" href="manifest.json"></head>
  <body>
    <div id="endpoint-show">There doesn't seem to be an endpoint right now</div>
    <script src="https://www.gstatic.com/firebasejs/3.5.0/firebase-app.js"></script>                    
    <script src="https://www.gstatic.com/firebasejs/3.5.0/firebase-messaging.js"></script>              
    <script>                                                                                            
      var config = {apiKey: "my key", authDomain: "my domain", messagingSenderId: "my id"};                                                                                                
      firebase.initializeApp(config);                                                                   
      const messaging = firebase.messaging();                                                           
      messaging.requestPermission()                                                                     
        .then(function() { console.log('Notification permission granted.'); })                          
        .catch(function(err) { console.log('Unable to get permission to notify. ', err); });            
      navigator.serviceWorker.ready.then(function(serviceWorkerRegistration) {                          
        serviceWorkerRegistration.pushManager.subscribe({userVisibleOnly: true})                        
          .then(function(subscription) {                                                                
            document.getElementById("endpoint-show").innerHTML = "<p>" + subscription.endpoint.split('/').slice(-1)[0] + "</p>";                                                                               
          })                                                                                            
        });                                                                                             
      navigator.serviceWorker.register('./service-worker.js')                                           
    </script>                                                                                           
  </body>                                                                                               
<html>

和service-worker.js,如下所示:

self.addEventListener('push', function(event) {
  console.log('Received a push message', event);
  event.waitUntil(self.registration.showNotification("title", { body: "body" }));
});

这似乎是注册推送通知订阅并建立service worker来处理它们所需的最小代码量。

然后使用curl命令发送通知,如下所示。即,POST到https://fcm.googleapis.com/fcm/send与那些特定的头集和一个主体,其中包含一个"太"字段,这是等于我的idex.html显示。这是有效的,只要我在我的计算机上收到标题为"title"和正文为"body"的通知。

但这就是我卡住的地方:似乎我可以通过此请求发送的唯一数据是通知发生的事实,而不是任何其他(实际)数据。我链接的第一个示例只是硬编码通知,就像我自己的代码一样,但我希望能够发送带有任意数据的请求。这里的文档似乎表明,我应该能够设置请求的datanotification字段,并获得具有该数据的通知,但这似乎不起作用。我已经在请求中设置了这两个字段,所以整个事情看起来像这样(我使用postman发送):

POST /fcm/send HTTP/1.1
Host: fcm.googleapis.com
Content-Type: application/json
Authorization: key=my key
Cache-Control: no-cache
Postman-Token: some token
{
    "notification": {
        "body": "notification body",
        "title": "notification title"
    },
    "data": {
        "body": "data body",
        "title": "data title"
    },
    "to" : "my endpoint"
}

但我不知道如何实际检索这些数据。我的service worker捕获的事件不包含任何这些数据。我所看过的文档似乎都没有描述如何通过网络实际获取这些数据,仅在Android或iOS上,但显然这是可能的,因为许多网站实现动态通知。

我怀疑我对这一切是如何工作的有一些根本性的误解,这并不奇怪,因为我对任何类型的web开发都没有什么经验。如果我想做的事情是不可能的,或者可以用完全不同的方法来做,请告诉我。

重申一下,这就是我想要做的:

  1. 发送请求(无论是我写的web服务器还是firebase)

  2. 有一个通知弹出在我的Chrome浏览器从该请求的信息

您似乎将新的firebase消息库与老式的service worker代码混合在一起了。

获得权限后,需要调用getToken API。

  // service.js
  // after request permission is successful
  // Get Instance ID token. Initially this makes a network call, once retrieved
  // subsequent calls to getToken will return from cache.
  messaging.getToken()
    .then(function(currentToken) {
      if (currentToken) {
        sendTokenToServer(currentToken);
        updateUIForPushEnabled(currentToken);
      } else {
        // Show permission request.
        console.log('No Instance ID token available. Request permission to generate one.');
        // Show permission UI.
        updateUIForPushPermissionRequired();
        setTokenSentToServer(false);
      }
   })
   .catch(function(err) {
     console.log('An error occurred while retrieving token. ', err);
     showToken('Error retrieving Instance ID token. ', err);
     setTokenSentToServer(false);
   });

这是有争议的,但你也需要创建一个服务工作,文件名为firebase-messaging-sw.js。参考资料可在此找到。

在这个service worker中,你需要添加这样的内容:

// firebase-messaging-sw.js
'use strict';
console.log('Starting service worker');
if( 'function' === typeof importScripts) {
  importScripts('https://www.gstatic.com/firebasejs/3.5.0/firebase-app.js');
  importScripts('https://www.gstatic.com/firebasejs/3.5.0/firebase-messaging.js');
  importScripts('core/decoder.js');
  // Initialize the Firebase app in the service worker by passing in the
  // messagingSenderId.
  firebase.initializeApp({
    'messagingSenderId': 'YOUR-SENDER-ID'
  });
  // Retrieve an instance of Firebase Messaging so that it can handle background
  // messages.
  const messaging = firebase.messaging();

  messaging.setBackgroundMessageHandler(function(payload) {
    var shinyData = payload || {};
    console.log('[firebase-messaging-sw.js] Received background message ', payload, shinyData);
    return self.registration.showNotification(shinyData.title, {
      body: shinyData.body,
      icon: shinyData.icon,
      data: {url: shinyData.tag}
    })
  });
}

你可能会发现我创建的要点很有用。

最新更新