Açık Web'de Push Bildirimleri

Matt Gaunt

Hangi mobil cihaz özelliklerinin web'de eksik olduğunu sorarsanız push bildirimleri her zaman listenin üst sıralarında yer alır.

Push bildirimleri, kullanıcılarınızın sevdikleri sitelerden zamanında güncellemeler alabilmesini sağlar ve özelleştirilmiş, ilgi çekici içerik sunarak onlarla etkili bir şekilde yeniden etkileşim kurmanıza olanak tanır.

Chrome sürüm 42'den itibaren Push API ve Bildirim API'si geliştiricilerin kullanımına sunulmuştur.

Chrome'daki Push API'si, Web Uygulaması Manifestleri ve Hizmet Çalışanları gibi birkaç farklı teknolojiye dayanır. Bu gönderide bu teknolojilerin her birine değineceğiz, ancak push mesajlarını hazır ve çalışır duruma getirmek için ne kadar asgari düzeyde kullanılması gerekir? Manifestlerin diğer bazı özelliklerini ve Service Worker'ların çevrimdışı özelliklerini daha iyi anlamak için lütfen yukarıdaki bağlantılara göz atın.

Ayrıca, Chrome'un gelecekteki sürümlerinde API'ye nelerin ekleneceğine de bakacağız ve son olarak, bir SSS bölümümüz olacak.

Chrome için Push Mesajlarını Uygulama

Bu bölümde, web uygulamanızda push mesajlarını desteklemek için tamamlamanız gereken her adım açıklanmaktadır.

Hizmet Çalışanı kaydetme

Web için push mesajları uygulamak üzere bir Service Worker'a ihtiyaç duyulur. Bunun nedeni, push mesajı alındığında tarayıcının, sayfa açılmadan arka planda çalışan bir hizmet çalışanı başlatabilmesi ve bu push mesajının nasıl işleneceğine karar verebilmeniz için bir etkinlik gönderebilmesidir.

Aşağıda, web uygulamanızda bir hizmet çalışanının nasıl kaydedileceğine ilişkin bir örnek verilmiştir. Kayıt başarıyla tamamlandığında initialiseState() işlemini çağırırız. Bu konuya birazdan değineceğiz.

var isPushEnabled = false;

…

window.addEventListener('load', function() {
    var pushButton = document.querySelector('.js-push-button');
    pushButton.addEventListener('click', function() {
    if (isPushEnabled) {
        unsubscribe();
    } else {
        subscribe();
    }
    });

    // Check that service workers are supported, if so, progressively
    // enhance and add push messaging support, otherwise continue without it.
    if ('serviceWorker' in navigator) {
    navigator.serviceWorker.register('/service-worker.js')
    .then(initialiseState);
    } else {
    console.warn('Service workers aren\'t supported in this browser.');
    }
});

Düğme tıklama işleyici, mesaj push mesajı göndermek için kullanıcının abone olmasını veya abonelikten çıkmasını sağlar. isPushEnabled, sadece push mesajlaşmaya abone olup olmadığını izleyen genel bir değişkendir. Kod snippet'leri boyunca bunlara referans verilir.

Ardından, push mesajlarını işleme mantığına sahip service-worker.js dosyasını kaydetmeden önce Service Worker'ların desteklenip desteklenmediğini kontrol ederiz. Burada, tarayıcıya bu JavaScript dosyasının sitemizin hizmet çalışanı olduğunu söylememiz yeterli.

İlk Durumu Ayarla

Chrome'daki etkin ve devre dışı push mesajı kullanıcı deneyimini gösteren örnek.

Service Worker kaydedildikten sonra kullanıcı arayüzümüzün durumunu ayarlamamız gerekir.

Kullanıcılar, sitenizde push mesajlarını etkinleştirmek veya devre dışı bırakmak için basit bir kullanıcı arayüzü bekler ve gerçekleşen tüm değişikliklerden haberdar olmak ister. Başka bir deyişle, siteniz için push mesajlarını etkinleştirir, sitenizden ayrılır ve bir hafta sonra geri gelirse kullanıcı arayüzünüz push mesajlarının zaten etkin olduğunu vurgulayacaktır.

Bu belgede bazı kullanıcı deneyimi yönergelerini bulabilirsiniz. Bu makalede teknik noktalara odaklanacağız.

Bu noktada, üzerinde çalışılması gereken, etkin veya devre dışı olması gereken yalnızca iki durum olduğunu düşünebilirsiniz. Bununla birlikte, bildirimlerle ilgili olarak dikkate almanız gereken başka durumlar da vardır.

Chrome'da dikkat edilmesi gereken farklı noktaları ve push durumunu vurgulayan bir şema

Düğmemizi etkinleştirmeden önce kontrol etmemiz gereken birkaç API var. Her şey destekleniyorsa kullanıcı arayüzümüzü etkinleştirebilir ve ilk durumu push mesajlaşmanın abone olup olmadığını belirtecek şekilde ayarlayabiliriz.

Bu denetimlerin çoğu kullanıcı arayüzümüzün devre dışı bırakılmasına neden olduğundan başlangıç durumunu devre dışı olarak ayarlamanız gerekir. Bu, sayfanızın JavaScript'iyle ilgili bir sorun olması, örneğin JS dosyasının indirilmemesi veya kullanıcının JavaScript'i devre dışı bırakmış olması gibi karışıklıkların yaşanmasını da önler.

<button class="js-push-button" disabled>
    Enable Push Messages
</button>

Bu ilk durumla, yukarıda özetlenen kontrolleri initialiseState() yöntemiyle (ör. hizmet çalışanımız kaydedildikten sonra) gerçekleştirebiliriz.

// Once the service worker is registered set the initial state
function initialiseState() {
    // Are Notifications supported in the service worker?
    if (!('showNotification' in ServiceWorkerRegistration.prototype)) {
    console.warn('Notifications aren\'t supported.');
    return;
    }

    // Check the current Notification permission.
    // If its denied, it's a permanent block until the
    // user changes the permission
    if (Notification.permission === 'denied') {
    console.warn('The user has blocked notifications.');
    return;
    }

    // Check if push messaging is supported
    if (!('PushManager' in window)) {
    console.warn('Push messaging isn\'t supported.');
    return;
    }

    // We need the service worker registration to check for a subscription
    navigator.serviceWorker.ready.then(function(serviceWorkerRegistration) {
    // Do we already have a push message subscription?
    serviceWorkerRegistration.pushManager.getSubscription()
        .then(function(subscription) {
        // Enable any UI which subscribes / unsubscribes from
        // push messages.
        var pushButton = document.querySelector('.js-push-button');
        pushButton.disabled = false;

        if (!subscription) {
            // We aren't subscribed to push, so set UI
            // to allow the user to enable push
            return;
        }

        // Keep your server in sync with the latest subscriptionId
        sendSubscriptionToServer(subscription);

        // Set your UI to show they have subscribed for
        // push messages
        pushButton.textContent = 'Disable Push Messages';
        isPushEnabled = true;
        })
        .catch(function(err) {
        console.warn('Error during getSubscription()', err);
        });
    });
}

Bu adımlara kısa bir genel bakış:

  • ServiceWorkerRegistration prototipinde showNotification öğesinin mevcut olup olmadığını kontrol ederiz. Bu olmadan, push mesajı alındığında hizmet çalışanımızdan bildirim gösteremeyiz.
  • Mevcut Notification.permission öğesinin, "denied" olmadığından emin olmak için ne olduğunu kontrol ederiz. Reddedilen izin, kullanıcı tarayıcıda izni manuel olarak değiştirene kadar bildirim gösteremeyeceğiniz anlamına gelir.
  • Push mesajlarının desteklenip desteklenmediğini kontrol etmek için window nesnesinde PushManager olup olmadığını kontrol ederiz.
  • Son olarak, zaten aboneliğimiz olup olmadığını kontrol etmek için pushManager.getSubscription() kullandık. Bu durumda, doğru bilgiye sahip olduğumuzdan emin olmak için abonelik bilgilerini sunucumuza gönderir ve kullanıcı arayüzümüzü, push mesajlarının zaten etkin olup olmadığını belirtecek şekilde ayarlarız. Bu makalenin ilerleyen kısımlarında abonelik nesnesinde hangi ayrıntıların bulunduğuna göz atacağız.

Aboneliği kontrol etmek ve push düğmesini etkinleştirmek için navigator.serviceWorker.ready çözümlenene kadar bekleriz. Çünkü, ancak hizmet çalışanı etkin olduktan sonra push mesajlarına abone olabilirsiniz.

Bir sonraki adım, kullanıcının push mesajlarını etkinleştirmek istemesidir. Ancak bunu yapabilmemiz için önce bir Google Developers Console projesi oluşturmamız ve Firebase Cloud Messaging (FCM)'yi kullanmak üzere manifest'imize bazı parametreler eklememiz gerekir.

Firebase Developer Console'da Proje Oluşturma

Chrome, push mesajlarının gönderilmesi ve teslimi için FCM'yi kullanır. Ancak, FCM API'yi kullanmak için Firebase Developer Console'da bir proje oluşturmanız gerekir.

Aşağıdaki adımlar FCM'nin kullanıldığı Chrome, Android için Opera ve Samsung Tarayıcı'ya özeldir. Bunun diğer tarayıcılarda nasıl çalışacağını makalenin ilerleyen kısımlarında açıklayacağız.

Yeni bir Firebase Geliştirici Projesi oluşturun

Başlamak için https://console.firebase.google.com/ adresinde "Yeni Proje Oluştur"u tıklayarak yeni bir proje oluşturmanız gerekir.

Yeni Firebase Projesi Ekran Görüntüsü

Proje adı ekleyip projeyi oluşturduğunuzda proje kontrol paneline yönlendirilirsiniz:

Firebase Projesi Ana Sayfası

Bu kontrol panelinde, sol üst köşedeki proje adının yanındaki dişliyi ve ardından "Proje Ayarları"nı tıklayın.

Firebase Proje Ayarları Menüsü

Ayarlar sayfasında "Cloud Messaging" sekmesini tıklayın.

Firebase Project Cloud Messaging Menüsü

Bu sayfada, daha sonra kullanacağımız push mesajı için API anahtarı ve bir sonraki bölümde web uygulaması manifest dosyasına koymamız gereken gönderen kimliği yer almaktadır.

Web Uygulaması Manifesti Ekle

Push aboneliğinin başarılı olması için gcm_sender_id alanına sahip bir manifest dosyası eklememiz gerekir. Bu parametre yalnızca Chrome, Android için Opera ve Samsung Tarayıcı tarafından FCM / GCM'yi kullanabilmeleri için gereklidir.

gcm_sender_id bu tarayıcılar tarafından FCM'ye sahip bir kullanıcı cihazına abone olduğunda kullanılır. Bu, FCM'nin kullanıcının cihazını tanımlayabileceği ve gönderen kimliğinizin ilgili API anahtarıyla eşleştiğinden ve kullanıcının, sunucunuzun push mesajları göndermesine izin verdiğinden emin olabileceği anlamına gelir.

Aşağıda son derece basit bir manifest dosyası verilmiştir:

{
    "name": "Push Demo",
    "short_name": "Push Demo",
    "icons": [{
        "src": "images/icon-192x192.png",
        "sizes": "192x192",
        "type": "image/png"
        }],
    "start_url": "/index.html?homescreen=1",
    "display": "standalone",
    "gcm_sender_id": "<Your Sender ID Here>"
}

gcm_sender_id değerini Firebase projenizdeki gönderen kimliğine ayarlamanız gerekir.

Manifest.json dosyanızı projenize kaydettikten sonra (manifest.json iyi bir addır) sayfanızın başlığında, aşağıdaki etiketi kullanarak HTML'nizden bu dosyaya referans verin.

<link rel="manifest" href="/manifest.json">

Bu parametrelerle bir web manifesti eklemezseniz kullanıcıyı mesaj aktarmaya abone olmaya çalıştığınızda "Registration failed - no sender id provided" veya "Registration failed - permission denied" hatasıyla bir istisna alırsınız.

Push Mesajlaşma'ya abone olun

Manifest ayarlarını yaptığınıza göre geri dönüp sitenizin JavaScript'ine dönebilirsiniz.

Abone olmak için ServiceWorkerRegistration aracılığıyla erişebileceğiniz PushManager nesnesinde subscribe() yöntemini çağırmanız gerekir.

Bu işlemde kullanıcıdan kaynağınıza push bildirimleri göndermesine izin vermesi istenir. Bu izin olmadan başarılı bir şekilde abone olamazsınız.

subscribe() yöntemi tarafından döndürülen söz konusu çözümlenirse size uç nokta içeren bir PushSubscription nesnesi verilir.

Uç nokta, ileriki bir tarihte push mesajlarının gönderilmesi gerekeceğinden, her kullanıcı için sunucunuza kaydedilmesi gerekir.

Aşağıdaki kod kullanıcıyı push mesaja abone yapar:

function subscribe() {
    // Disable the button so it can't be changed while
    // we process the permission request
    var pushButton = document.querySelector('.js-push-button');
    pushButton.disabled = true;

    navigator.serviceWorker.ready.then(function(serviceWorkerRegistration) {
    serviceWorkerRegistration.pushManager.subscribe()
        .then(function(subscription) {
        // The subscription was successful
        isPushEnabled = true;
        pushButton.textContent = 'Disable Push Messages';
        pushButton.disabled = false;

        // TODO: Send the subscription.endpoint to your server
        // and save it to send a push message at a later date
        return sendSubscriptionToServer(subscription);
        })
        .catch(function(e) {
        if (Notification.permission === 'denied') {
            // The user denied the notification permission which
            // means we failed to subscribe and the user will need
            // to manually change the notification permission to
            // subscribe to push messages
            console.warn('Permission for Notifications was denied');
            pushButton.disabled = true;
        } else {
            // A problem occurred with the subscription; common reasons
            // include network errors, and lacking gcm_sender_id and/or
            // gcm_user_visible_only in the manifest.
            console.error('Unable to subscribe to push.', e);
            pushButton.disabled = false;
            pushButton.textContent = 'Enable Push Messages';
        }
        });
    });
}

Bu noktada web uygulamanız push mesajı almaya hazırdır, ancak hizmet çalışanı dosyamıza bir push etkinliği işleyici ekleyinceye kadar hiçbir şey olmaz.

Hizmet Çalışanı Aktarma Etkinliği İşleyici

Push mesajı alındığında (bir sonraki bölümde aslında push mesajının nasıl gönderileceğinden bahsedeceğiz), hizmet çalışanınıza bir push etkinliği gönderilir ve bu noktada bir bildirim görüntülemeniz gerekir.

self.addEventListener('push', function(event) {
    console.log('Received a push message', event);

    var title = 'Yay a message.';
    var body = 'We have received a push message.';
    var icon = '/images/icon-192x192.png';
    var tag = 'simple-push-demo-notification-tag';

    event.waitUntil(
    self.registration.showNotification(title, {
        body: body,
        icon: icon,
        tag: tag
    })
    );
});

Bu kod bir push etkinliği işleyici kaydeder ve önceden tanımlanmış başlık, gövde metni, simge ve bildirim etiketi içeren bir bildirim görüntüler. Bu örnekte vurgulanması gereken bir diğer nokta da event.waitUntil() yöntemidir. Bu yöntem bir taahhüt alır ve söz belirlenene kadar bir etkinlik işleyicinin ömrünü uzatır (veya hizmet çalışanının aktif olmasını sağlamak olarak düşünülebilir). Bu durumda, event.waitUntil öğesine iletilen söz showNotification() tarafından döndürülen sözdür.

Bildirim etiketi, benzersiz bildirimler için bir tanımlayıcı görevi görür. İki push mesajını aynı uç noktaya, aralarında kısa bir gecikme olacak şekilde gönderirsek ve bildirimleri aynı etiketle görüntülersek tarayıcı, ilk bildirimi görüntüler ve push mesajı alındığında bunu ikinci bildirimle değiştirir.

Aynı anda birden çok bildirim göstermek istiyorsanız, farklı bir etiket kullanın veya hiç etiket kullanmayın. Bu gönderinin sonraki bölümlerinde, bildirim göstermeyle ilgili daha kapsamlı bir örnek üzerinden bahsedeceğiz. Şimdilik işleri basit tutalım ve push mesajı gönderirken bu bildirimi gösterip göstermediğine bakalım.

Push Mesaj Gönderme

Push mesajlarına abone olduk ve hizmet çalışanımız bir bildirim göstermeye hazır. Dolayısıyla FCM aracılığıyla push mesajı göndermenin zamanı geldi.

Bu, yalnızca FCM kullanan tarayıcılar için geçerlidir.

PushSubscription.endpoint değişkenini sunucunuza gönderdiğinizde FCM uç noktası özel olur. URL'nin sonunda, registration_id olan bir parametre vardır.

Uç nokta örneği şu şekildedir:

https://fcm.googleapis.com/fcm/send/APA91bHPffi8zclbIBDcToXN_LEpT6iA87pgR-J-MuuVVycM0SmptG-rXdCPKTM5pvKiHk2Ts-ukL1KV8exGOnurOAKdbvH9jcvg8h2gSi-zZJyToiiydjAJW6Fa9mE3_7vsNIgzF28KGspVmLUpMgYLBd1rxaVh-L4NDzD7HyTkhFOfwWiyVdKh__rEt15W9n2o6cZ8nxrP

FCM URL'si:

https://fcm.googleapis.com/fcm/send

registration_id şöyle olur:

APA91bHPffi8zclbIBDcToXN_LEpT6iA87pgR-J-MuuVVycM0SmptG-rXdCPKTM5pvKiHk2Ts-ukL1KV8exGOnurOAKdbvH9jcvg8h2gSi-zZJyToiiydjAJW6Fa9mE3_7vsNIgzF28KGspVmLUpMgYLBd1rxaVh-L4NDzD7HyTkhFOfwWiyVdKh__rEt15W9n2o6cZ8nxrP

Bu, FCM'yi kullanan tarayıcılara özeldir. Normal bir tarayıcıda, basit bir şekilde bir uç nokta alırsınız ve bu uç noktayı standart bir şekilde çağırırsınız ve URL'den bağımsız olarak çalışır.

Diğer bir deyişle, sunucunuzda uç noktanın FCM için olup olmadığını kontrol etmeniz ve aksi takdirde kayıt_kimliğini çıkarmanız gerekir. Bunu Python'da yapmak için şuna benzer bir şey yapabilirsiniz:

if endpoint.startswith('https://fcm.googleapis.com/fcm/send'):
    endpointParts = endpoint.split('/')
    registrationId = endpointParts[len(endpointParts) - 1]

    endpoint = 'https://fcm.googleapis.com/fcm/send'

Kayıt kimliğini aldıktan sonra FCM API'ye çağrı yapabilirsiniz. FCM API ile ilgili referans belgeleri burada bulabilirsiniz.

FCM'yi ararken unutulmaması gereken temel özellikler şunlardır:

  • API'yi çağırdığınızda key=&lt;YOUR_API_KEY&gt; değerine sahip bir Yetkilendirme başlığı ayarlanmalıdır. Burada &lt;YOUR_API_KEY&gt;, Firebase projesinin API anahtarıdır.
    • API anahtarı FCM tarafından uygun gönderen kimliğini bulmak, kullanıcının projenize izin verdiğinden emin olmak ve son olarak, sunucunun IP adresinin bu proje için izin verilenler listesine eklendiğinden emin olmak için kullanılır.
  • Verileri JSON veya form verisi olarak göndermenize bağlı olarak application/json veya application/x-www-form-urlencoded;charset=UTF-8 için uygun bir Content-Type üst bilgisi.
  • registration_ids dizisi: Bunlar, kullanıcılarınızdan uç noktalardan çıkardığınız kayıt kimlikleridir.

Lütfen sunucunuzdan push mesaj gönderme hakkındaki dokümanlara göz atın. Ancak hizmet çalışanınızı hızlı bir şekilde kontrol etmek için tarayıcınıza push mesajı göndermek amacıyla cURL'yi kullanabilirsiniz.

Bu cURL komutundaki &lt;YOUR_API_KEY&gt; ve &lt;YOUR_REGISTRATION_ID&gt; değerlerini kendi komutlarınızla değiştirip bir terminalden çalıştırın.

Muhteşem bir bildirim göreceksiniz:

    curl --header "Authorization: key=<YOUR_API_KEY>" --header
    "Content-Type: application/json" https://fcm.googleapis.com/fcm/send -d
    "{\"registration_ids\":[\"<YOUR_REGISTRATION_ID>\"]}"
Android için Chrome&#39;dan push mesajı örneği.

Arka uç mantığınızı geliştirirken, Yetkilendirme üst bilgisinin ve POST gövdesinin biçiminin FCM uç noktasına özgü olduğunu unutmayın. Bu nedenle, uç noktanın FCM için ne zaman olduğunu tespit edin ve koşullu olarak üstbilgiyi ekleyin ve POST gövdesini biçimlendirin. Diğer tarayıcılar (ve ileride Chrome) için Web Push Protokolü'nü uygulamanız gerekecektir.

Push API'nin Chrome'daki mevcut uygulamasının olumsuz bir yönü, push mesajıyla veri gönderememenizdir. Hayır, hiçbir şey. Bunun nedeni, gelecekteki bir uygulamada yük verilerinin push mesajlaşma uç noktasına gönderilmeden önce sunucunuzda şifrelenmesidir. Bu şekilde, uç nokta, hangi push sağlayıcısı olursa olsun push mesajının içeriğini kolayca görüntüleyemez. Bu, HTTPS sertifikalarının yetersiz şekilde doğrulanması ve sunucunuz ile push sağlayıcı arasındaki adam saldırıları gibi diğer güvenlik açıklarına karşı da koruma sağlar. Ancak bu şifreleme henüz desteklenmediğinden bu esnada bildirimi doldurmak için gereken bilgileri almak üzere bir getirme işlemi gerçekleştirmeniz gerekir.

Daha Eksiksiz Bir Aktarma Etkinliği Örneği

Şu ana kadar gördüğümüz bildirim oldukça basit ve örneklere baktığımızda gerçek dünyadaki kullanım alanlarını ele alma konusunda yetersiz kalıyor.

Gerçekçi olmak gerekirse, çoğu kişi bildirimi görüntülemeden önce sunucusundan bazı bilgileri almak ister. Bu veriler, bildirim başlığını ve mesajı belirli bir şeyle doldurmak veya bir adım daha ileri gidip bazı sayfaları ya da verileri önbelleğe almak olabilir. Böylece, kullanıcı bildirimi tıkladığında, ağ o sırada kullanılamıyor olsa bile, tarayıcı açıldığında her şey anında kullanılabilir olur.

Aşağıdaki kodda bir API'den bazı veriler getiriyoruz, yanıtı bir nesneye dönüştürüp bildirimimizi doldurmak için kullanıyoruz.

self.addEventListener('push', function(event) {
    // Since there is no payload data with the first version
    // of push messages, we'll grab some data from
    // an API and use it to populate a notification
    event.waitUntil(
    fetch(SOME_API_ENDPOINT).then(function(response) {
        if (response.status !== 200) {
        // Either show a message to the user explaining the error
        // or enter a generic message and handle the
        // onnotificationclick event to direct the user to a web page
        console.log('Looks like there was a problem. Status Code: ' + response.status);
        throw new Error();
        }

        // Examine the text in the response
        return response.json().then(function(data) {
        if (data.error || !data.notification) {
            console.error('The API returned an error.', data.error);
            throw new Error();
        }

        var title = data.notification.title;
        var message = data.notification.message;
        var icon = data.notification.icon;
        var notificationTag = data.notification.tag;

        return self.registration.showNotification(title, {
            body: message,
            icon: icon,
            tag: notificationTag
        });
        });
    }).catch(function(err) {
        console.error('Unable to retrieve data', err);

        var title = 'An error occurred';
        var message = 'We were unable to get the information for this push message';
        var icon = URL_TO_DEFAULT_ICON;
        var notificationTag = 'notification-error';
        return self.registration.showNotification(title, {
            body: message,
            icon: icon,
            tag: notificationTag
        });
    })
    );
});

event.waitUntil() öğesinin bir vaadi aldığını, bunun da showNotification() tarafından döndürülen sözle sonuçlandığını vurgulamak isteriz. Bunun anlamı, etkinlik işleyicimizin eşzamansız fetch() çağrısı tamamlanana ve bildirim gösterilene kadar çıkış yapmayacağıdır.

Hata olduğunda bile bir bildirim gösterdiğimizi fark edeceksiniz. Bunun nedeni, bunu yapmamamız halinde Chrome'un kendi genel bildirimini göstermesidir.

Kullanıcı Bildirimi Tıklandığında URL açma

Kullanıcı bir bildirimi tıkladığında hizmet çalışanınıza bir notificationclick etkinliği gönderilir. İşleyiciniz içinde, bir sekmeye odaklanma veya belirli bir URL'ye sahip bir pencereyi açma gibi uygun işlemleri yapabilirsiniz.

self.addEventListener('notificationclick', function(event) {
    console.log('On notification click: ', event.notification.tag);
    // Android doesn't close the notification when you click on it
    // See: http://crbug.com/463146
    event.notification.close();

    // This looks to see if the current is already open and
    // focuses if it is
    event.waitUntil(
    clients.matchAll({
        type: "window"
    })
    .then(function(clientList) {
        for (var i = 0; i < clientList.length; i++) {
        var client = clientList[i];
        if (client.url == '/' && 'focus' in client)
            return client.focus();
        }
        if (clients.openWindow) {
        return clients.openWindow('/');
        }
    })
    );
});

Bu örnek, varsa mevcut bir aynı kaynak sekmesine odaklanarak veya yeni bir sekme açarak tarayıcıyı site kaynağının kök dizinine açar.

Buradan Notification API ile yapabileceğiniz bazı şeylere özel bir yayın bulabilirsiniz.

Kullanıcının Cihazı Aboneliğinden Çıkma

Bir kullanıcının cihazına abone oldunuz ve bu kullanıcı push mesajlar alıyor. Peki, bu kullanıcının aboneliğini nasıl iptal edebilirsiniz?

Bir kullanıcı cihazının aboneliğinden çıkmak için yapılması gereken temel işlem, PushSubscription nesnesinde unsubscribe() yöntemini çağırmak ve uç noktayı sunucularınızdan kaldırmaktır (böylece, alınamayacağını bildiğiniz push mesajları göndermezsiniz). Aşağıdaki kod tam olarak bunu yapar:

function unsubscribe() {
    var pushButton = document.querySelector('.js-push-button');
    pushButton.disabled = true;

    navigator.serviceWorker.ready.then(function(serviceWorkerRegistration) {
    // To unsubscribe from push messaging, you need get the
    // subscription object, which you can call unsubscribe() on.
    serviceWorkerRegistration.pushManager.getSubscription().then(
        function(pushSubscription) {
        // Check we have a subscription to unsubscribe
        if (!pushSubscription) {
            // No subscription object, so set the state
            // to allow the user to subscribe to push
            isPushEnabled = false;
            pushButton.disabled = false;
            pushButton.textContent = 'Enable Push Messages';
            return;
        }

        var subscriptionId = pushSubscription.subscriptionId;
        // TODO: Make a request to your server to remove
        // the subscriptionId from your data store so you
        // don't attempt to send them push messages anymore

        // We have a subscription, so call unsubscribe on it
        pushSubscription.unsubscribe().then(function(successful) {
            pushButton.disabled = false;
            pushButton.textContent = 'Enable Push Messages';
            isPushEnabled = false;
        }).catch(function(e) {
            // We failed to unsubscribe, this can lead to
            // an unusual state, so may be best to remove
            // the users data from your data store and
            // inform the user that you have done so

            console.log('Unsubscription error: ', e);
            pushButton.disabled = false;
            pushButton.textContent = 'Enable Push Messages';
        });
        }).catch(function(e) {
        console.error('Error thrown while unsubscribing from push messaging.', e);
        });
    });
}

Aboneliği Güncel Tutma

Abonelikler FCM ile sunucunuz arasında senkronize edilmeyebilir. Sunucunuzun, FCM belgelerinde açıklandığı gibi error:NotRegistered ve canonical_id sonuçlarını arayarak FCM API'nin gönderme POST yanıt gövdesini ayrıştırdığından emin olun.

Abonelikler, hizmet çalışanı ile sunucunuz arasındaki senkronizasyonu da kaybedebilir. Örneğin, başarılı bir şekilde abone olduktan/aboneliği iptal ettikten sonra, kesintili bir ağ bağlantısı sunucunuzu güncellemenizi engelleyebilir veya bir kullanıcı bildirim iznini iptal edip otomatik abonelikten çıkma işlemini tetikleyebilir. serviceWorkerRegistration.pushManager.getSubscription() sonucunu düzenli olarak (ör. sayfa yüklenirken) kontrol ederek ve sunucuyla senkronize ederek bu tür durumları ele alın. Artık aboneliğiniz yoksa ve Notification.permission == 'granted' değerine ayarlanırsa otomatik olarak yeniden abone olmak isteyebilirsiniz.

sendSubscriptionToServer() ürününde endpoint güncellerken başarısız ağ isteklerini nasıl ele alacağınızı göz önünde bulundurmanız gerekir. Uygulayabileceğiniz çözümlerden biri, sunucunuzun en son ayrıntılara ihtiyaç duyup duymadığını belirlemek için bir çerezdeki endpoint durumunu izlemektir.

Yukarıdaki adımların tümü, Chrome 46'ta web'de push mesajlaşmanın tam olarak uygulanmasıyla sonuçlanır. Hala işleri kolaylaştıracak belirli özellikler (push mesajlarını tetiklemek için standart bir API gibi) mevcut ancak bu sürüm web uygulamalarınıza push mesajları oluşturmaya hemen başlayabilmenizi sağlar.

Web Uygulamanızda Hata Ayıklama

Push mesajlarını uygularken hatalar, sayfanız veya hizmet çalışanınız olmak üzere iki yerden birinde görünür.

Sayfadaki hatalar, DevTools kullanılarak hata ayıklama için kullanılabilir. Hizmet çalışanı sorunlarında hata ayıklamak için iki seçeneğiniz vardır:

  1. chrome://inspect > Hizmet çalışanları sayfasına gidin. Bu görünüm, şu anda çalışan hizmet çalışanları dışında çok fazla bilgi sağlamaz.
  2. chrome://serviceworker-internals sayfasına gidin. Buradan hizmet çalışanlarının durumunu görüntüleyebilir ve varsa hataları görebilirsiniz. Bu sayfa, Geliştirici Araçları benzer bir özellik grubuna sahip olana kadar geçicidir.

Service Worker'larla yeni tanışan herkese verebileceğim en iyi ipuçlarından biri, "DevTools penceresini aç ve hata ayıklama için hizmet çalışanı başlangıcında JavaScript yürütmesini duraklat" onay kutusunu kullanmak. Bu onay kutusu, Service Worker'ınızın başına bir ayrılma noktası ekler ve yürütme işlemini duraklatır. Bu sayede, Service Worker komut dosyanızı devam ettirebilir veya bu komut dosyasında herhangi bir sorunla karşılaşıp karşılaşmadığınızı görebilirsiniz.

Serviceworker-internals öğesinde yürütmeyi duraklat onay kutusunun nerede olduğunu gösteren ekran görüntüsü.

FCM ile hizmet çalışanınızın push etkinliği arasında bir sorun varsa Chrome'un herhangi bir şey alıp almadığını görmeniz mümkün olmadığından, sorun gidermek için yapabileceğiniz fazla bir şey yoktur. Dikkat edilmesi gereken en önemli nokta, sunucunuz bir API çağrısı yaptığında FCM'nin yanıtının başarılı olmasıdır. Aşağıdaki gibi bir şey gibi görünür:

{"multicast_id":1234567890,"success":1,"failure":0,"canonical_ids":0,"results":[{"message_id":"0:1234567890"}]}

"success": 1 yanıtına dikkat edin. Bunun yerine bir hata görürseniz bu, FCM kayıt kimliğiyle ilgili bir sorun olduğunu ve push mesajının Chrome'a gönderilmediğini gösterir.

Android için Chrome'da Hizmet Çalışanlarında Hata Ayıklama

Şu an için, Android için Chrome'da hizmet çalışanlarında hata ayıklamak mümkün değildir. chrome://inspect adresine gidip cihazınızı bulmanız ve hizmet çalışanınızın URL'sini içeren "Worker pid:...." adlı bir liste öğesi bulmanız gerekir.

Service Worker&#39;ların Chrome&#39;da yaşadığı yeri denetleyen ekran görüntüsü

Push Bildirimleri için Kullanıcı Deneyimi

Chrome ekibi, push bildirimleri kullanıcı deneyimine ilişkin en iyi uygulamaları içeren bir belgenin yanı sıra push bildirimleriyle çalışırken karşılaşılan bazı uç durumları da kapsayan bir doküman hazırlamaktadır.

Chrome ve Açık Web'de Push Mesajlaşmanın Geleceği

Bu bölümde, bu uygulamanın dikkat etmeniz gereken Chrome'a özel bölümleri ve diğer tarayıcı uygulamalarından ne açıdan farklı olacağıyla ilgili birtakım ayrıntılara değinilmektedir.

Web Aktarma Protokolü ve Uç Noktaları

Push API standardının güzel yanı, uç noktayı alıp sunucunuza iletebilmeniz ve Web Push Protokolü'nü uygulayarak push mesajları gönderebilmenizdir.

Web Push Protokolü, push sağlayıcılarının uygulayabileceği yeni bir standart olup geliştiricilerin push sağlayıcısının kim olduğu konusunda endişe etmelerine gerek kalmaz. Bu standart, API anahtarları için kaydolma ve FCM'de olduğu gibi özel olarak biçimlendirilmiş veriler gönderme ihtiyacını ortadan kaldırmasıdır.

Chrome, Push API'yi uygulayan ilk tarayıcıdır ve FCM Web Push Protokolü'nü desteklemez. Bu nedenle Chrome, gcm_sender_id kullanımını ve FCM için esnek API'yi kullanmanızı gerektirir.

Chrome'un nihai hedefi, Chrome ve FCM ile Web Push Protokolü'nü kullanmaya doğru ilerlemektir.

O zamana kadar "https://fcm.googleapis.com/fcm/send" uç noktasını tespit etmeniz ve bunu diğer uç noktalardan ayrı olarak işlemeniz (ör. yük verilerini belirli bir şekilde biçimlendirmeniz ve yetkilendirme anahtarını eklemeniz) gerekir.

Web Push Protokolü Nasıl Uygulanır?

Firefox Nightly şu anda push işlemi üzerinde çalışıyor ve Web Push Protokolü'nü uygulayan ilk tarayıcı olabilir.

SSS

Teknik özellikler nerede?

https://slightlyoff.github.io/ServiceWorker/spec/service_worker/ https://w3c.github.io/push-api/ https://notifications.spec.whatwg.org/

Web'deki varlığımın birden fazla kaynağı varsa ya da hem web hem de yerel varlığım varsa yinelenen bildirimlerin önüne geçebilir miyim?

Şu anda bu sorun için bir çözüm yok, ancak ilerleme durumunu Chromium'dan takip edebilirsiniz.

İdeal senaryo, kullanıcının cihazı için bir kimliğe sahip olmak, ardından sunucu tarafında yerel uygulama ve web uygulaması abonelik kimliklerini eşleştirip hangisine push mesajı gönderileceğine karar vermektir. Bunu ekran boyutu, cihaz modeli ve web uygulaması ile yerel uygulama arasında oluşturulan bir anahtarı paylaşarak yapabilirsiniz, ancak her yaklaşımın artıları ve eksileri vardır.

Neden bir gcm_sender_id özelliğine ihtiyacım var?

Chrome, Android için Opera ve Samsung Tarayıcı'nın Firebase Cloud Messaging (FCM) API'yi kullanabilmesi için bu gereklidir. Hedef, standart kesinleştiğinde ve FCM tarafından desteklendiğinde Web Push Protokolü'nü kullanmaktır.

Neden Web Yuvaları veya Sunucu Tarafından Gönderilen Etkinlikler (EventSource) kullanılmıyor?

Push mesajlarını kullanmanın avantajı, sayfanız kapalı olsa bile hizmet çalışanınızın uyanık olması ve bir bildirim gösterebilmesidir. Sayfa veya tarayıcı kapatıldığında Web Yuvaları ve EventSource'un bağlantıları da kapatılır.

Arka planda etkinlik teslimine ihtiyacım yoksa ne yapmalıyım?

Arka planda teslime ihtiyacınız yoksa Web Yuvaları mükemmel bir seçenektir.

Push özelliğini hangi durumlarda bildirim göstermeden kullanabilirim (ör. sessiz arka plan push)?

Bu özelliğin ne zaman kullanıma sunulacağına ilişkin bir zaman çizelgesi henüz yoktur ancak arka planda senkronizasyonun uygulanması amacıyla bir amaç mevcuttur. Bu karar verilmemiş veya henüz verilmemiş olsa da, arka plan senkronizasyonu ile sessiz aktarmanın etkinleştirilmesi konusunda bazı tartışmalar yapılmaktadır.

Bunun için neden HTTPS gerekiyor? Geliştirme sırasında bu sorunu nasıl çözebilirim?

Service Worker'lar, hizmet çalışanı komut dosyasının istenen kaynaktan geldiğinden ve ortadaki adam saldırısından gelmediğinden emin olmak için güvenli kaynaklara ihtiyaç duyar. Şu anda bu, canlı sitelerde HTTPS kullanılması anlamına gelir ancak localhost geliştirme sırasında çalışacaktır.

Tarayıcı desteği nasıl görünüyor?

Chrome, kararlı sürümünü destekler ve Mozilla, Firefox Nightly'de push bildirimleri üzerinde çalışmaktadır. Daha fazla bilgi için Push API hatasını uygulama bölümüne bakın. Ayrıca Bildirim uygulamalarını buradan takip edebilirsiniz.

Bildirimi belirli bir süre sonra kaldırabilir miyim?

Şu anda mümkün değil, ancak görünür durumda olan bildirimlerin listesini almak için destek eklemeyi planlıyoruz. Görüntülendikten sonra bir bildirim için süre sonu ayarlamak üzere bir kullanım alanınız varsa, bunun ne olduğunu öğrenmek isteriz. Bu yüzden, lütfen bir yorum ekleyin. Bunu yaptığınızda, Chrome ekibine geri iletiriz.

Kullanıcıya gönderilen push bildiriminin yalnızca belirli bir süre sonunda durdurulması gerekiyorsa ve bildirimin ne kadar süre görünür kalacağı sizin için önemli değilse FCM'nin geçerlilik süresi (ttl) parametresini kullanabilirsiniz. Daha fazla bilgiyi buradan edinebilirsiniz.

Chrome'da push mesajlaşmanın sınırlamaları nelerdir?

Bu gönderide açıklanan birkaç sınırlama vardır:

  • Chrome'un CCM'yi bir push hizmeti olarak kullanması bazı özel gereksinimler oluşturur. Bunlardan bazılarının gelecekte kaldırılıp kaldırılmayacağını görmek için birlikte çalışıyoruz.
  • Push mesajı aldığınızda bir bildirim göstermeniz gerekir.
  • Masaüstündeki Chrome, Chrome çalışmıyorsa push mesajlarının alınmayacağı uyarısına sahiptir. Bu, push mesajlarının her zaman alındığı ChromeOS ve Android'den farklıdır.

Permissions API'yi kullanmamız gerekmez mi?

Permission API Chrome'da kullanıma sunulmuştur, ancak tüm tarayıcılarda kullanılamayabilir. Daha fazla bilgiyi buradan edinebilirsiniz.

Bir bildirimi tıkladığımda Chrome neden önceki sekmeyi açmıyor?

Bu sorun yalnızca şu anda bir hizmet çalışanı tarafından kontrol edilmeyen sayfaları etkilemektedir. Buradan daha fazla bilgi edinebilirsiniz.

Kullanıcının cihazının push bildirimi aldığı zamana kadar bir bildirimin süresi geçmişse ne olur?

Push mesajı aldığınızda her zaman bir bildirim göstermeniz gerekir. Bir bildirim göndermek istediğiniz ancak bunun yalnızca belirli bir süre için yararlı olduğu senaryoda, CCM'de "time_to_live" parametresini kullanabilirsiniz. Böylece FCM, geçerlilik süresinin dolması durumunda push mesajını göndermez.

Daha fazla ayrıntıyı burada bulabilirsiniz.

10 push mesajı gönderip cihazın yalnızca bir push mesajı almasını istersem ne olur?

FCM'nin, aynı "daralt_anahtarı"na sahip bekleyen mesajları yeni mesajla değiştirmesini sağlamak için kullanabileceğiniz bir "Daraltma_anahtarı" parametresi bulunur.

Daha fazla ayrıntıyı burada bulabilirsiniz.