Menambahkan notifikasi push ke aplikasi web

1. Ringkasan

Pesan push memberikan cara yang sederhana dan efektif untuk berinteraksi kembali dengan pengguna Anda. Dalam codelab ini, Anda akan mempelajari cara menambahkan notifikasi push ke aplikasi web.

Yang akan Anda pelajari

  • Cara berlangganan dan menghentikan langganan pengguna untuk pengiriman pesan push
  • Cara menangani pesan push yang masuk
  • Cara menampilkan notifikasi
  • Cara merespons klik notifikasi

Yang Anda butuhkan

  • Chrome 52 atau yang lebih baru
  • Server Web untuk Chrome, atau server web pilihan Anda
  • Editor teks
  • Pengetahuan dasar tentang HTML, CSS, JavaScript, dan Chrome DevTools
  • Kode contoh (Lihat penyiapan.)

2. Memulai persiapan

Download kode contoh

Ada dua cara untuk mendapatkan kode contoh untuk codelab ini:

  • Buat clone repositori Git:
git clone https://github.com/GoogleChrome/push-notifications.git
  • Download file ZIP:

Jika Anda mendownload sumber sebagai file ZIP, mengekstraknya akan memberi Anda folder root push-notifications-master.

Menginstal dan memverifikasi server web

Meskipun Anda bebas menggunakan server web sendiri, codelab ini dirancang agar berfungsi dengan baik dengan aplikasi Web Server for Chrome. Jika Anda belum menginstal aplikasi tersebut, Anda bisa mendownloadnya dari Chrome Web Store:

Setelah menginstal aplikasi Server Web untuk Chrome, klik pintasan Aplikasi di kolom bookmark:

946bcaaad66e5c8e.pngS

Di jendela Apps, klik ikon Web Server:

9f3c21b2cf6cbfb5.png

Anda akan melihat dialog ini berikutnya, yang memungkinkan Anda mengonfigurasi server web lokal:

73543edeb27c3d6f.pngS

Klik tombol Choose folder, dan pilih folder app di folder push-notifications yang Anda download. Dengan begitu, Anda dapat menayangkan pekerjaan yang sedang berlangsung melalui URL yang ditampilkan di bagian URL Server Web pada dialog.

Di bagian Options, centang kotak di samping Automatically show index.html, seperti yang ditunjukkan di bawah ini:

5ac11bca86ce7369.pngS

Kemudian, hentikan dan mulai ulang server dengan menggeser tombol Server Web: STARTED ke kiri, lalu kembali ke kanan.

d42f87972f9fec24.png

Klik URL Web Server untuk mengunjungi situs Anda di browser web. Anda akan melihat halaman yang terlihat seperti ini — meskipun versi Anda mungkin menunjukkan 127.0.0.1:8887 sebagai alamatnya:

00-push-codelab.png

Selalu mengupdate pekerja layanan

Selama pengembangan, sebaiknya pastikan pekerja layanan Anda selalu diupdate dan memiliki perubahan terbaru.

Untuk menyiapkannya di Chrome:

  1. Buka tab Push Codelab.
  2. Buka DevTools: Ctrl-Shift-I di Windows dan Linux, Cmd-Option-I di macOS.
  3. Pilih panel Application, klik tab Service Workers, dan centang kotak Update on Reload. Jika kotak centang ini diaktifkan, pekerja layanan akan diperbarui dengan paksa setiap kali halaman dimuat ulang.

e7d384fb77885b99.png

3. Mendaftarkan pekerja layanan

Kode lengkap

Di direktori app, perhatikan bahwa Anda memiliki file kosong bernama sw.js. File ini akan menjadi pekerja layanan Anda. Untuk saat ini, kolom boleh tetap kosong. Anda akan menambahkan kode ke dalamnya nanti.

Pertama, Anda harus mendaftarkan file ini sebagai pekerja layanan Anda.

Halaman app/index.html Anda akan dimuat scripts/main.js. Anda mendaftarkan pekerja layanan dalam file JavaScript ini.

Tambahkan kode berikut ke scripts/main.js:

if ('serviceWorker' in navigator && 'PushManager' in window) {
  console.log('Service Worker and Push are supported');

  navigator.serviceWorker.register('sw.js')
  .then(function(swReg) {
    console.log('Service Worker is registered', swReg);

    swRegistration = swReg;
  })
  .catch(function(error) {
    console.error('Service Worker Error', error);
  });
} else {
  console.warn('Push messaging is not supported');
  pushButton.textContent = 'Push Not Supported';
}

Kode ini memeriksa apakah pekerja layanan dan pesan push didukung oleh browser Anda. Jika didukung, kode akan mendaftarkan file sw.js Anda.

Coba

Periksa perubahan Anda dengan memuat ulang tab Push Codelab di browser.

Periksa konsol di Chrome DevTools untuk menemukan Service Worker is registered message, seperti berikut:

5d7ad383d6f235d5.pngS

Mendapatkan kunci server aplikasi

Untuk menggunakan codelab ini, Anda perlu membuat kunci server aplikasi. Anda dapat melakukannya di situs pendamping: web-push-codelab.glitch.me

Di sini Anda dapat membuat pasangan kunci publik dan pribadi.

push-codelab-04-companion.png

Salin kunci publik Anda ke scripts/main.js, menggantikan nilai <Your Public Key>:

const applicationServerPublicKey = '<Your Public Key>';

Penting: Anda tidak boleh menempatkan kunci pribadi di aplikasi web.

4. Melakukan inisialisasi status

Kode lengkap

Saat ini, tombol Enable pada aplikasi web dinonaktifkan dan tidak dapat diklik. Ini karena praktik yang baik adalah menonaktifkan tombol push secara default dan mengaktifkannya setelah Anda mengetahui bahwa pesan push didukung oleh browser dan Anda dapat memeriksa apakah pengguna saat ini berlangganan pesan atau tidak.

Anda harus membuat dua fungsi di scripts/main.js:

  • initializeUI, untuk memeriksa apakah pengguna saat ini sudah berlangganan
  • updateBtn, untuk mengaktifkan tombol Anda dan mengubah teks bergantung pada apakah pengguna berlangganan atau tidak

Tambahkan fungsi initializeUI ke main.js seperti ini:

function initializeUI() {
  // Set the initial subscription value
  swRegistration.pushManager.getSubscription()
  .then(function(subscription) {
    isSubscribed = !(subscription === null);

    if (isSubscribed) {
      console.log('User IS subscribed.');
    } else {
      console.log('User is NOT subscribed.');
    }

    updateBtn();
  });
}

Metode baru Anda menggunakan swRegistration dari langkah sebelumnya, mendapatkan properti pushManager darinya, dan memanggil getSubscription() pada langkah tersebut.

pushManager. getSubscription() menampilkan promise yang di-resolve dengan langganan saat ini jika ada. Jika tidak, metode ini akan menampilkan null. Dengan ini, Anda dapat memeriksa apakah pengguna sudah berlangganan, menyetel nilai isSubscribed, lalu memanggil updateBtn() untuk memperbarui tombol.

Tambahkan fungsi updateBtn() ke main.js:

function updateBtn() {
  if (isSubscribed) {
    pushButton.textContent = 'Disable Push Messaging';
  } else {
    pushButton.textContent = 'Enable Push Messaging';
  }

  pushButton.disabled = false;
}

Fungsi ini mengaktifkan tombol dan mengubah teks tombol tergantung pada apakah pengguna berlangganan atau tidak.

Hal terakhir yang perlu dilakukan adalah memanggil initializeUI() saat pekerja layanan terdaftar di main.js:

navigator.serviceWorker.register('sw.js')
.then(function(swReg) {
  console.log('Service Worker is registered', swReg);

  swRegistration = swReg;
  initializeUI();
})

Coba

Muat ulang tab Push Codelab. Anda akan melihat bahwa tombol Enable Push Messaging sekarang diaktifkan (Anda dapat mengkliknya) dan Anda akan melihat User is NOT subscribed di konsol.

a1553f4a0483d227.png

Saat melanjutkan progres codelab ini, Anda akan melihat teks tombol berubah setiap kali Anda berlangganan atau berhenti berlangganan.

5. Membuat pengguna berlangganan

Kode lengkap

Saat ini, tombol Enable Push Messaging tidak memiliki banyak fungsi. Ayo perbaiki.

Dalam fungsi initializeUI(), tambahkan pemroses klik untuk tombol Anda:

function initializeUI() {
  pushButton.addEventListener('click', function() {
    pushButton.disabled = true;
    if (isSubscribed) {
      // TODO: Unsubscribe user
    } else {
      subscribeUser();
    }
  });

  // Set the initial subscription value
  swRegistration.pushManager.getSubscription()
  .then(function(subscription) {
    isSubscribed = !(subscription === null);

    updateSubscriptionOnServer(subscription);

    if (isSubscribed) {
      console.log('User IS subscribed.');
    } else {
      console.log('User is NOT subscribed.');
    }

    updateBtn();
  });
}

Ketika pengguna mengeklik tombol itu, Anda menonaktifkan tombol hanya untuk memastikan pengguna tidak dapat mengekliknya untuk kedua kalinya, karena berlangganan pesan push bisa memakan waktu beberapa saat.

Kemudian, panggil subscribeUser() jika pengguna saat ini belum berlangganan. Untuk melakukannya, Anda harus menempelkan kode berikut ke scripts/main.js:

function subscribeUser() {
  const applicationServerKey = urlB64ToUint8Array(applicationServerPublicKey);
  swRegistration.pushManager.subscribe({
    userVisibleOnly: true,
    applicationServerKey: applicationServerKey
  })
  .then(function(subscription) {
    console.log('User is subscribed.');

    updateSubscriptionOnServer(subscription);

    isSubscribed = true;

    updateBtn();
  })
  .catch(function(error) {
    console.error('Failed to subscribe the user: ', error);
    updateBtn();
  });
}

Mari kita telusuri apa yang dilakukan kode ini dan bagaimana kode ini membuat pengguna berlangganan pesan push.

Pertama, Anda mengambil kunci publik server aplikasi, yang dienkode dengan aman URL Base64, dan konversi menjadi UInt8Array, karena ini adalah input yang diharapkan dari panggilan subscribe(). Fungsi urlB64ToUint8Array() berada di bagian atas scripts/main.js.

Setelah mengonversi nilai, Anda memanggil metode subscribe() di pushManager pekerja layanan, yang meneruskan kunci publik server aplikasi Anda dan nilai userVisibleOnly: true.

const applicationServerKey = urlB64ToUint8Array(applicationServerPublicKey);
swRegistration.pushManager.subscribe({
  userVisibleOnly: true,
  applicationServerKey: applicationServerKey
})

Parameter userVisibleOnly adalah jaminan bahwa Anda akan menampilkan notifikasi setiap kali pesan push dikirim. Saat ini, nilai ini wajib diisi dan harus benar.

Memanggil subscribe() akan menampilkan promise yang akan diselesaikan setelah langkah-langkah berikut:

  1. Pengguna telah memberikan izin untuk menampilkan notifikasi.
  2. Browser telah mengirimkan permintaan jaringan ke layanan push guna mendapatkan data yang diperlukan untuk menghasilkan PushSubscription.

Promise subscribe() akan diselesaikan dengan PushSubscription jika langkah-langkah ini berhasil. Jika pengguna tidak memberikan izin atau jika ada masalah dalam membuat pengguna berlangganan, promise akan ditolak dengan error. Hal ini akan memberi Anda rantai promise berikut dalam codelab Anda:

swRegistration.pushManager.subscribe({
  userVisibleOnly: true,
  applicationServerKey: applicationServerKey
})
.then(function(subscription) {
  console.log('User is subscribed.');

  updateSubscriptionOnServer(subscription);

  isSubscribed = true;

  updateBtn();

})
.catch(function(err) {
  console.log('Failed to subscribe the user: ', err);
  updateBtn();
});

Dengan ini, Anda bisa mendapatkan langganan dan memperlakukan pengguna sebagai berlangganan atau menangkap error dan mencatatnya ke konsol. Dalam kedua skenario tersebut, Anda memanggil updateBtn() untuk memastikan tombol diaktifkan kembali dan memiliki teks yang sesuai.

Dalam aplikasi yang sebenarnya, fungsi updateSubscriptionOnServer() adalah tempat Anda mengirimkan data langganan ke backend, tetapi untuk codelab, Anda cukup menampilkan langganan di UI. Tambahkan fungsi berikut ke scripts/main.js:

function updateSubscriptionOnServer(subscription) {
  // TODO: Send subscription to application server

  const subscriptionJson = document.querySelector('.js-subscription-json');
  const subscriptionDetails =
    document.querySelector('.js-subscription-details');

  if (subscription) {
    subscriptionJson.textContent = JSON.stringify(subscription);
    subscriptionDetails.classList.remove('is-invisible');
  } else {
    subscriptionDetails.classList.add('is-invisible');
  }
}

Coba

Buka tab Push Codelab, muat ulang halaman, lalu klik tombol. Anda akan melihat dialog izin seperti ini:

fcc61267a0194e81.png

Jika memberikan izin, Anda akan melihat User is subscribed dicatat dalam log ke konsol. Teks tombol akan berubah menjadi Disable Push Messaging dan Anda dapat melihat langganan sebagai data JSON di bagian bawah halaman.

5c5505f2ead037c.pngS

6. Menangani izin ditolak

Kode lengkap

Satu hal yang belum Anda tangani adalah apa yang terjadi jika pengguna memblokir permintaan izin. Hal ini memerlukan pertimbangan khusus karena jika pengguna memblokir izin tersebut, aplikasi web Anda tidak akan dapat menampilkan kembali dialog izin dan tidak dapat membuat pengguna berlangganan. Anda setidaknya perlu menonaktifkan tombol tekan sehingga pengguna tahu bahwa tombol tidak dapat digunakan.

Tempat yang tepat untuk menangani skenario ini adalah dalam fungsi updateBtn(). Anda hanya perlu memeriksa nilai Notification.permission, seperti ini:

function updateBtn() {
  if (Notification.permission === 'denied') {
    pushButton.textContent = 'Push Messaging Blocked';
    pushButton.disabled = true;
    updateSubscriptionOnServer(null);
    return;
  }

  if (isSubscribed) {
    pushButton.textContent = 'Disable Push Messaging';
  } else {
    pushButton.textContent = 'Enable Push Messaging';
  }

  pushButton.disabled = false;
}

Anda tahu bahwa jika izinnya adalah denied, pengguna tidak dapat berlangganan dan tidak ada lagi yang dapat Anda lakukan, jadi menonaktifkan tombol secara permanen adalah pendekatan terbaik.

Coba

Karena Anda sudah memberikan izin untuk aplikasi web dari langkah sebelumnya, Anda harus mengklik i dalam lingkaran di kolom URL dan mengubah izin Notifications menjadi Use global default (Ask).

54495592074f10ae.pngS

Setelah Anda mengubah setelan ini, muat ulang halaman dan klik tombol Enable Push Messaging, lalu pilih Block pada dialog izin. Tombol akan dinonaktifkan dan menampilkan teks Push Messaging Blocked.

d4cf22468f6defda.png

Dengan perubahan ini, Anda kini dapat membuat pengguna berlangganan, setelah menangani kemungkinan skenario izin.

7. Menangani peristiwa push

Kode lengkap

Sebelum mempelajari cara mengirim pesan push dari backend, Anda perlu mempertimbangkan apa yang sebenarnya akan terjadi ketika pengguna yang berlangganan menerima pesan push.

Saat Anda memicu pesan push, browser akan menerima pesan push tersebut, mencari tahu pekerja layanan yang dipakai push tersebut, membangunkan pekerja layanan tersebut, dan mengirim peristiwa push. Anda perlu memproses peristiwa ini dan menampilkan notifikasi sebagai hasilnya.

Tambahkan kode berikut ke file sw.js Anda:

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

  const title = 'Push Codelab';
  const options = {
    body: 'Yay it works.',
    icon: 'images/icon.png',
    badge: 'images/badge.png'
  };

  event.waitUntil(self.registration.showNotification(title, options));
});

Mari kita pelajari kode ini. Anda memproses peristiwa push di pekerja layanan dengan menambahkan pemroses peristiwa:

self.addEventListener('push', ... );

(Kecuali Anda sudah pernah bermain dengan Web Worker sebelumnya, self mungkin adalah hal baru. Dalam file pekerja layanan, self merujuk ke pekerja layanan itu sendiri.)

Saat pesan push diterima, pemroses peristiwa akan dipanggil, dan Anda membuat notifikasi dengan memanggil showNotification() pada properti registration pekerja layanan. showNotification() memerlukan title; Anda juga dapat memberinya objek options untuk menetapkan pesan isi, ikon, dan badge. (Badge hanya digunakan di Android pada saat penulisan.)

const title = 'Push Codelab';
const options = {
  body: 'Yay it works.',
  icon: 'images/icon.png',
  badge: 'images/badge.png'
};
self.registration.showNotification(title, options);

Hal terakhir yang harus dibahas dalam penanganan peristiwa push Anda adalah event.waitUntil(). Metode ini menggunakan promise untuk mengaktifkan browser agar pekerja layanan Anda tetap aktif dan berjalan hingga promise yang diteruskan telah diselesaikan.

Agar kode di atas lebih mudah dipahami, Anda dapat menulis ulang kode tersebut seperti berikut:

const notificationPromise = self.registration.showNotification(title, options);
event.waitUntil(notificationPromise);

Sekarang setelah Anda melangkah melalui peristiwa push, mari kita uji peristiwa push.

Coba

Dengan penanganan peristiwa push dalam pekerja layanan, Anda dapat memicu peristiwa push palsu untuk menguji apa yang terjadi saat pesan diterima.

Di aplikasi web Anda, berlanggananlah ke pesan push dan pastikan Anda melihat User IS subscribed di konsol. Di panel Application di DevTools, pada tab Service Workers, klik tombol Push:

1ee499267eeccd1c.pngS

Setelah mengklik Push, Anda akan melihat notifikasi seperti ini:

379105dfb0ea56d8.pngS

Catatan: Jika langkah ini tidak berhasil, coba batalkan pendaftaran pekerja layanan dengan link Batalkan pendaftaran di panel Aplikasi DevTools, tunggu hingga pekerja layanan dihentikan, lalu muat ulang halaman.

8. Klik notifikasi

Kode lengkap

Jika Anda mengklik salah satu notifikasi ini, Anda akan melihat bahwa tidak ada yang terjadi. Anda dapat menangani klik notifikasi dengan memproses peristiwa notificationclick di pekerja layanan.

Mulai dengan menambahkan pemroses notificationclick di sw.js:

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

  event.notification.close();

  event.waitUntil(
    clients.openWindow('https://developers.google.com/web')
  );
});

Saat pengguna mengklik notifikasi, pemroses peristiwa notificationclick akan dipanggil.

Kode menutup notifikasi yang diklik terlebih dahulu:

event.notification.close();

Kemudian, jendela atau tab baru akan dibuka, yang memuat URL https://developers.google.com/web. Jangan ragu untuk mengubah ini.

event.waitUntil(
    clients.openWindow('https://developers.google.com/web/')
  );

event.waitUntil() memastikan browser tidak menghentikan pekerja layanan sebelum jendela atau tab baru ditampilkan.

Coba

Coba picu pesan push di DevTools lagi dan klik notifikasi. Sekarang Anda akan melihat notifikasi ditutup dan tab baru terbuka.

9. Kirim pesan push

Anda sudah melihat bahwa aplikasi web mampu menampilkan notifikasi menggunakan DevTools dan melihat cara menutup notifikasi dengan sekali klik. Langkah selanjutnya adalah mengirim pesan push yang sebenarnya.

Biasanya, proses ini memerlukan pengiriman langganan dari halaman web ke backend. Backend kemudian akan memicu pesan push dengan membuat panggilan API ke endpoint dalam langganan.

Hal ini berada di luar cakupan codelab ini, tetapi Anda dapat menggunakan situs pendamping ( web-push-codelab.glitch.me) untuk memicu pesan push yang sebenarnya. Tempelkan langganan di bagian bawah halaman Anda:

bb202867962a0249.png

Kemudian tempel ini ke situs pendamping di area teks Subscription to Send To:

a0dd93bc33a9e8cf.png

Di bagian Text to Send, tambahkan string yang ingin Anda kirim dengan pesan push.

Klik tombol Kirim pesan push.

a5e8e89411ec034.png

Anda kemudian akan menerima pesan push. Teks yang Anda gunakan akan dicatat ke konsol.

f6815a356d4f9aaa.png

Ini akan memberi Anda kesempatan untuk menguji pengiriman dan penerimaan data, dan memanipulasi notifikasi sebagai akibatnya.

Aplikasi pendamping hanyalah server node yang menggunakan library web-push untuk mengirim pesan. Sebaiknya tinjau web-push-libs org di GitHub untuk melihat library apa saja yang tersedia guna mengirim pesan push untuk Anda. Perintah ini menangani banyak detail untuk memicu pesan push.

Anda dapat melihat semua kode untuk situs pendamping di sini.

10. Menghentikan langganan pengguna

Kode lengkap

Satu hal yang hilang adalah kemampuan untuk menghentikan langganan pengguna dari push. Untuk melakukannya, Anda perlu memanggil unsubscribe() di PushSubscription.

Kembali ke file scripts/main.js Anda, ubah pemroses klik pushButton di initializeUI() menjadi berikut ini:

pushButton.addEventListener('click', function() {
  pushButton.disabled = true;
  if (isSubscribed) {
    unsubscribeUser();
  } else {
    subscribeUser();
  }
});

Perhatikan bahwa Anda sekarang akan memanggil fungsi baru unsubscribeUser(). Dalam fungsi ini, Anda akan mendapatkan langganan saat ini dan memanggil unsubscribe() di langganan tersebut. Tambahkan kode berikut ke scripts/main.js:

function unsubscribeUser() {
  swRegistration.pushManager.getSubscription()
  .then(function(subscription) {
    if (subscription) {
      return subscription.unsubscribe();
    }
  })
  .catch(function(error) {
    console.log('Error unsubscribing', error);
  })
  .then(function() {
    updateSubscriptionOnServer(null);

    console.log('User is unsubscribed.');
    isSubscribed = false;

    updateBtn();
  });
}

Mari kita jelajahi fungsi ini.

Pertama, Anda mendapatkan langganan saat ini dengan memanggil getSubscription():

swRegistration.pushManager.getSubscription()

Tindakan ini akan menampilkan promise yang di-resolve dengan PushSubscription jika ada; jika tidak, kueri akan menampilkan null. Jika ada langganan, Anda memanggil unsubscribe() pada langganan tersebut, yang membuat PushSubscription menjadi tidak valid.

swRegistration.pushManager.getSubscription()
.then(function(subscription) {
  if (subscription) {
    // TODO: Tell application server to delete subscription
    return subscription.unsubscribe();
  }
})
.catch(function(error) {
  console.log('Error unsubscribing', error);
})

Memanggil unsubscribe() akan menampilkan promise, karena proses ini dapat memerlukan waktu beberapa saat. Anda menampilkan promise tersebut sehingga then() berikutnya dalam rantai menunggu unsubscribe() selesai. Anda juga menambahkan pengendali catch jika pemanggilan unsubscribe() menghasilkan error. Setelah ini, Anda dapat mengupdate UI.

.then(function() {
  updateSubscriptionOnServer(null);

  console.log('User is unsubscribed.');
  isSubscribed = false;

  updateBtn();
})

Coba

Anda seharusnya dapat menekan Enable Push Messaging atau Disable Push Messaging di aplikasi web, dan log akan menunjukkan bahwa pengguna tersebut sedang berlangganan dan berhenti berlangganan.

81a07119235b53da.pngS

11. Selesai

Selamat, Anda telah menyelesaikan codelab ini.

Codelab ini telah menunjukkan cara menyiapkan dan menjalankan aplikasi dengan menambahkan notifikasi push ke aplikasi web Anda. Jika Anda ingin mempelajari lebih lanjut apa saja yang dapat dilakukan notifikasi web, lihat dokumen ini.

Jika Anda ingin menerapkan notifikasi push di situs Anda, Anda mungkin tertarik untuk menambahkan dukungan bagi browser lama atau browser yang tidak sesuai standar yang menggunakan GCM. Pelajari lebih lanjut di sini.

Bacaan lebih lanjut

Postingan blog yang relevan