推送事件

Matt Gaunt

此時,我們介紹了訂閱使用者及傳送推送訊息。接著是 並在使用者的裝置上接收這則推送訊息,並顯示通知 (亦可進行任何其他操作) 可執行的工作)。

推送事件

收到訊息時,會將推送事件分派到您的 Service Worker 中。

設定推送事件監聽器的程式碼應與其他事件相似 您編寫的接聽程式:

self.addEventListener('push', function(event) {
    if (event.data) {
    console.log('This push event has data: ', event.data.text());
    } else {
    console.log('This push event has no data.');
    }
});

對剛開始接觸服務工作處理程序的開發人員來說,這段程式碼最奇怪的一點就是self 變數。self 經常用於網路工作站,也就是 Service Worker。self 是指 或是全域範圍,類似網頁中中的 window但對於網路工作者和服務工作人員來說 self 是指 worker 本身。

在上例中,self.addEventListener() 可以視為新增事件監聽器至 Service Worker 本身

在推送事件範例中,我們會檢查是否有任何資料,並將內容輸出至控制台。

您還可以透過其他方式剖析推送事件的資料:

// Returns string
event.data.text()

// Parses data as JSON string and returns an Object
event.data.json()

// Returns blob of data
event.data.blob()

// Returns an arrayBuffer
event.data.arrayBuffer()

大多數人都會根據其預期應用程式使用 json()text()

本例示範如何新增推送事件監聽器及如何存取資料 缺少兩項非常重要的功能未顯示通知 並未使用 event.waitUntil()

等到

關於服務工作人員的特色是,您無法掌控 Service Worker 程式碼的更新瀏覽器會自行決定喚醒時間和啟動時機 終止服務您只能告訴瀏覽器:「我非常忙,我很忙! 就是將保證傳遞至 event.waitUntil() 方法。這樣一來,瀏覽器 請保持 Service Worker 持續運作,直到傳入的承諾完成為止。

使用推送事件時,還須先顯示通知, 傳遞的承諾已經解決

以下是顯示通知的基本範例:

self.addEventListener('push', function(event) {
    const promiseChain = self.registration.showNotification('Hello, World.');

    event.waitUntil(promiseChain);
});

呼叫 self.registration.showNotification() 是顯示通知的方法 並傳回會在顯示通知後可解決的承諾。

為求明確,我將這個承諾指派給 名為 promiseChain 的變數。會接著傳遞至 event.waitUntil()。我知道這是 但我發現不少問題都已推動 誤解應傳遞至 waitUntil() 或承諾無效的內容 鏈結。

這個更複雜的範例含有網路要求,以及使用 Analytics 看起來可能會像這樣:

self.addEventListener('push', function(event) {
    const analyticsPromise = pushReceivedTracking();
    const pushInfoPromise = fetch('/api/get-more-data')
    .then(function(response) {
        return response.json();
    })
    .then(function(response) {
        const title = response.data.userName + ' says...';
        const message = response.data.message;

        return self.registration.showNotification(title, {
        body: message
        });
    });

    const promiseChain = Promise.all([
    analyticsPromise,
    pushInfoPromise
    ]);

    event.waitUntil(promiseChain);
});

這裡呼叫了傳回承諾 pushReceivedTracking() 的函式。 在本例中,我們可以假裝發出網路要求 向我們的分析服務供應商提出建議我們也會發出網路要求,取得 回應並顯示通知,並使用 。

我們可以確保 Service Worker 持續運作,同時執行這兩項工作,方法是結合使用 這些承諾。Promise.all()最終的承諾會傳入 event.waitUntil() 這表示瀏覽器會先等待 兩項保證皆完成後,再確認通知 並終止 Service Worker。

我們應該要擔心 waitUntil() 的問題,且如何使用這項服務 開發人員常遇到的問題,就是當承諾鏈不正確 / 毀損時,Chrome 會 顯示這個「預設」通知:

圖片:Chrome 的預設通知

Chrome 只會顯示「這個網站已在背景更新」。通知 接收推送訊息,而 Service Worker 中的推送事件不會顯示 向 event.waitUntil() 發出的承諾使用完畢之後發出的通知。

開發人員遭到攔截的主要原因在於,他們的程式碼會 經常呼叫 self.registration.showNotification(),但他們「並未」這麼做 任何與它有關的保證。系統會間歇性地產生預設通知 。舉例來說,我們可以移除 self.registration.showNotification(),而且我們有可能會看見 通知。

self.addEventListener('push', function(event) {
    const analyticsPromise = pushReceivedTracking();
    const pushInfoPromise = fetch('/api/get-more-data')
    .then(function(response) {
        return response.json();
    })
    .then(function(response) {
        const title = response.data.userName + ' says...';
        const message = response.data.message;

        self.registration.showNotification(title, {
        body: message
        });
    });

    const promiseChain = Promise.all([
    analyticsPromise,
    pushInfoPromise
    ]);

    event.waitUntil(promiseChain);
});

您可以看到有多麼容易被忽略。

請注意,如果看到通知,請檢查你的承諾鏈和 event.waitUntil()

下一節將會說明如何設定通知樣式及 這種廣告會顯示什麼內容

後續步驟

程式碼研究室