Отправить Push Push с помощью Service Worker

сервер браузер Apple Google
Отправить Push Push с помощью Service Worker

Я был в предыдущем посте"Используйте Service Worker для создания автономного веб-приложения PWA" рассказал, как выполнять кэширование в автономном режиме, в этой статье рассказывается, как использовать Service Worker для отправки push (уведомлений) или веб-push. Веб-пуш очень популярен на зарубежных веб-сайтах, но его редко можно увидеть в Китае, в основном потому, что Google не может получить к нему доступ в Китае, потому что веб-пуш использует канал Google FCM и должен иметь возможность получать сообщения с серверов Google. Однако в обычном сетевом окружении зайти в гугль невозможно, поэтому заниматься этим в Китае особого смысла нет, но ведь это стандарт и тренд, и как техническому человеку вполне полезно его изучить .

1. Отправить push-процесс

Отправьте Push в браузер или клиент пользователя, процесс выглядит следующим образом:

На стороне браузера после регистрации Service Worker будет возвращен зарегистрированный объект, и будет вызван метод pushManager.subscribe этого объекта, чтобы позволить браузеру открыть всплывающее окно, чтобы спросить пользователя, принимать ли уведомления о сообщениях:

Если вы нажмете Разрешить, браузер запросит у FCM информацию о флаге подписки (подписки), а затем отправит подписку на сервер, чтобы сохранить ее для отправки Push текущему пользователю. Сервер использует информацию о подписке для вызова API, предоставляемого веб-push, для отправки сообщения в FCM, а затем FCM отправляет его в соответствующий браузер. Затем браузер вызовет push-событие Service Worker и позволит Service Worker вызвать showNotification для отображения содержимого push-уведомления. Операционная система отобразит этот Push:

Щелкните это поле, чтобы перейти к указанному URL-адресу для просмотра содержимого. Вот и весь процесс, а именно:

(1) браузер для инициирования запросов, создания подписки

После регистрации работника службы вызовите subscribe, чтобы спросить пользователя, разрешать ли уведомления, как показано в следующем коде:

navigator.serviceWorker.register("sw-4.js").then(function(reg){
    console.log("Yes, it did register service worker.");
    if (window.PushManager) {
        reg.pushManager.getSubscription().then(subscription => {
            // 如果用户没有订阅
            if (!subscription) {
                subscribeUser(reg);
            } else {
                console.log("You have subscribed our notification");
            }       
        });     
    }
}).catch(function(err) {
    console.log("No it didn't. This happened: ", err)
});

Приведенный выше код проверяет, была ли на него подписана ранее, прежде чем инициировать подписку, и если нет, инициирует подписку. Реализация subscribeUser, которая инициирует подписку, показана в следующем коде:

function subscribeUser(swRegistration) {
    const applicationServerPublicKey = "BBlY_5OeDkp2zl_Hx9jFxymKyK4kQKZdzoCoe0L5RqpiV2eK0t4zx-d3JPHlISZ0P1nQdSZsxuA5SRlDB0MZWLw";
    const applicationServerKey = urlB64ToUint8Array(applicationServerPublicKey);
    swRegistration.pushManager.subscribe({
        userVisibleOnly: true,
        applicationServerKey: applicationServerKey
    })
    // 用户同意
    .then(function(subscription) {
        console.log('User is subscribed:', JSON.stringify(subscription));
        jQuery.post("/add-subscription.php", {subscription: JSON.stringify(subscription)}, function(result) {
            console.log(result);
        });
    })
    // 用户不同意或者生成失败
    .catch(function(err) {
        console.log('Failed to subscribe the user: ', err);
    });
}

подписка передает два параметра, один из которых userVisibleOnly, который указывает, должно ли сообщение быть видимым.Если оно установлено как невидимое, Chrome сообщит об ошибке:

Chrome currently only supports the Push API for subscriptions that will result in user-visible messages. You can indicate this by calling pushManager.subscribe({userVisibleOnly: true}) instead. See https://goo.gl/yqv4Q4 for more details.

Но на самом деле это не влияет, мы устанавливаем его на true, но после получения сообщения вы можете настроить поспешную почту, чтобы уведомить страницу, чтобы сделать соответствующую операцию.

Второй параметр applicationServerKey — открытый ключ сервера, который можно использоватьПакет узла для веб-пушаСгенерируйте, сначала установите один:

npm install web-push --save

Затем сгенерируйте его с помощью следующего кода:

const webpush = require('web-push');
//VAPID keys should only be generated only once.
const vapidKeys = webpush.generateVAPIDKeys();
console.log(vapidKeys.publicKey, vapidKeys.privateKey);

При каждом запуске будет генерироваться новая пара ключей, например:

publicKey:  BMgkd1qfOfI6vFBbxIFMgdxDGC6-j8NYTwF_MXOIZ-St9lPhhMdPuUyFfwg1DLY59WP0FEaX84ZJRwgztdpfBHs
privateKey: LUeSF8DCv-NBxIfaeWeKTux858H45_V75vT0zZQLEbY

Пока открытый ключ может быть сопоставлен, открытый ключ используется на стороне браузера для создания подписок, а ключ используется на стороне сервера для отправки Push.

Если пользователь соглашается, браузер запросит у службы FCM генерацию подписки, затем выполнит then в цепочке Promise, вернет подписку и отправит подписку на сервер для хранения в then. И наоборот, если пользователь не согласен или не может подключиться к серверу FCM, будет выдано исключение:

DOMException: Registration failed - push service error

Сгенерированная подписка выглядит так:

{"endpoint":"https://fcm.googleapis.com/fcm/send/ci3-kIulf9A:APA91bEaQfDU8zuLSKpjzLfQ8121pNf3Rq7pjomSu4Vg-nMwLGfJSvkOUsJNCyYCOTZgmHDTu9I1xvI-dMVLZm1EgmEH0vDA7QFLjPKShG86W2zwX0IbtBPHEDLO0WgQ8OIhZ6yTnu-S","expirationTime":null,"keys":{"p256dh":"BAdAo6ldzRT5oCN8stqYRemoihPGOEJjrUDL6y8zhdA_swao_q-HlY_69mzIVobWX2MH02TzmtRWj_VeWUFMnXQ=","auth":"SS1PBnGwfMXjpJEfnoUIeQ=="}}

После стольких разговоров о FCM, что такое FCM?

(2) Что такое ФКМ

Официальный ФКМВводится так:

Firebase Cloud Messaging (FCM) — это кроссплатформенное решение для обмена сообщениями, которое позволяет надежно и бесплатно доставлять сообщения.

Используя FCM, вы можете уведомлять клиентские приложения о новой электронной почте или других данных, которые можно синхронизировать. Вы можете отправлять уведомительные сообщения, чтобы повторно привлечь пользователей и увеличить удержание. В таких случаях использования, как обмен мгновенными сообщениями, сообщение может доставлять клиентскому приложению полезную нагрузку размером до 4 КБ.

FCM — это надежная платформа для обмена сообщениями, ее самым большим преимуществом является то, что один и тот же механизм Push можно использовать на трех концах IOS/Android/Web:

Это имеет большое значение, потому что push-уведомления Android всегда были грязными: некоторые отечественные приложения используют сервис Push от Xiaomi, некоторые — Baidu, третьи — почтовый голубь Tencent и т. д. приводит к тому, что многие потоки все еще работают, когда телефон находится в состоянии гибернации, из-за чего телефон быстро потребляет энергию. В конце концов, это напрямую привело к тому, что в этом году Министерство промышленности и информационных технологий объявило о создании единого альянса толчков Android. У Apple единый механизм push: каждый отправляет Push на сервер Apple, а затем Apple отправляет его на соответствующее устройство Apple. Safari сейчас не поддерживает Service Worker, но можно использовать Apple Push.Недостаток в том, что этот вид push нельзя использовать для отправки важных данных, а визуальный осмотр может отображаться только во всплывающем окне. обрабатывать сообщения в фоновом режиме без всплывающих окон.

(3) Отправить толчок

Для отправки push-уведомлений можно использовать библиотеку web-push, предоставляемую FCM, которая поддерживает несколько языков, включая такие версии, как Node.js/PHP. С Node.js вы можете отправлять Push следующим образом:

const webpush = require('web-push');
// 从数据库取出用户的subsciption
const pushSubscription = {"endpoint":"https://fcm.googleapis.com/fcm/send/ci3-kIulf9A:APA91bEaQfDU8zuLSKpjzLfQ8121pNf3Rq7pjomSu4Vg-nMwLGfJSvkOUsJNCyYCOTZgmHDTu9I1xvI-dMVLZm1EgmEH0vDA7QFLjPKShG86W2zwX0IbtBPHEDLO0WgQ8OIhZ6yTnu-S","expirationTime":null,"keys":{"p256dh":"BAdAo6ldzRT5oCN8stqYRemoihPGOEJjrUDL6y8zhdA_swao_q-HlY_69mzIVobWX2MH02TzmtRWj_VeWUFMnXQ=","auth":"SS1PBnGwfMXjpJEfnoUIeQ=="}};

// push的数据
const payload = {
    title: '一篇新的文章',
    body: '点开看看吧',
    icon: '/html/app-manifest/logo_512.png',
    data: {url: "https://www.rrfed.com"}
  //badge: '/html/app-manifest/logo_512.png'
};

webpush.sendNotification(pushSubscription, JSON.stringify(payload));

После экспериментов в большинстве случаев задержка в основном в пределах 1 с.Как только вы нажмете здесь Enter, браузер его получит, но иногда не отправит (проблема с домашней сетью?). Если этот код будет работать на сервере, вам понадобится сервер в Гонконге. Например, автор размещает данные и сервисы для отправки Push на сервер в Гонконге, когда нужно будет отправить Push, сервер в Северном Китае будет обращаться к этому серверу для отправки запроса. Пока пользователь может подключиться к FCM, он может с радостью отправить Push.Если пользователь не может подключиться, нет никакого способа.

(4) Получение push-сообщений

Получение и прослушивание push-событий с помощью Service Worker, работающего в фоновом режиме:

this.addEventListener('push', function(event) {
    console.log('[Service Worker] Push Received.');
    console.log(`[Service Worker] Push had this data: "${event.data.text()}"`);

    let notificationData = event.data.json();
    const title = notificationData.title;
    // 可以发个消息通知页面
    //util.postMessage(notificationData); 
    // 弹消息框
    event.waitUntil(self.registration.showNotification(title, notificationData));
});

В основном это вызов showNotification для всплывающего окна или использование страницы уведомлений postMessage для соответствующей обработки. После экспериментов, если пользователь закрывает браузер, если в период закрытия есть Push, он снова появится, когда пользователь снова откроет браузер. Затем пользователь может щелкнуть всплывающее окно, чтобы открыть указанную страницу, которая должна прослушивать событие notificationclick:

this.addEventListener('notificationclick', function(event) {
    console.log('[Service Worker] Notification click Received.');

    let notification = event.notification;
    notification.close();
    event.waitUntil(
        clients.openWindow(notification.data.url)
    );
});

Позвоните client.openWindow, чтобы открыть новую страницу.

Это в основном завершает построение push-push,


Service Worker позволяет нам иметь push-уведомления, такие как собственные приложения, на веб-стороне, что делает веб-сторону все более и более похожей на нативную сторону приложений.С другими новыми функциями HTML5, такими какWebAssemblyувеличить скорость работы,WebWorkerподдержка многопоточности,база данныхПоддерживает управление и поддержку больших объемов данных,WebsocketДля связи в реальном времени, WebRTC для передачи мультимедиа P2P, а также WebGL, нового WebVR и т. д., все больше и больше вещей можно делать на стороне браузера, и опыт становится все более и более богатым, и это веб-приложение также кроссплатформенный. Быстрое развитие веб-технологий заставляет нас поверить в то, что у Интернета есть преимущество.


Связанное чтение:

  1. Почему вы должны обновить свой сайт до HTTPS
  2. Как обновить сайт до http/2
  3. Как я заставил свой сайт использовать манифест HTML5
  4. Используйте Service Worker для создания автономного веб-приложения PWA