שימוש ב-Service Worker לניהול התראות

Kate Jeffreys
Kate Jeffreys

ב-Codelab הזה משתמשים ב-Service Worker כדי לנהל התראות. ההוראות המפורטות כאן מבוססות על ההנחה שאתם כבר מכירים את Service Worker והעקרונות הבסיסיים של בקשת הרשאות לשליחת התראות ושליחת התראות. אם אתם צריכים רענון לגבי התראות, תוכלו להיעזר ב תחילת השימוש ב-Notifications API Codelab. למידע נוסף על Service Worker, כדאי לעיין במאמר מבוא ל-service worker של מאט גונט.

יצירת רמיקס של אפליקציה לדוגמה והצגתה בכרטיסייה חדשה

ההתראות חסומות באופן אוטומטי באפליקציית Glitch המוטמעת, כך שלא ניתן להציג תצוגה מקדימה של האפליקציה בדף הזה. במקום זאת:

  1. לוחצים על רמיקס לעריכה כדי לערוך את הפרויקט.
  2. כדי לראות תצוגה מקדימה של האתר, לוחצים על הצגת האפליקציה. לאחר מכן לוחצים על מסך מלא מסך מלא.

התקלה אמורה להיפתח בכרטיסייה חדשה של Chrome.

במהלך העבודה ב-Codelab הזה, יש לבצע שינויים בקוד ב-Glitch שמוטמע בדף הזה. כדאי לרענן את הכרטיסייה החדשה עם האפליקציה הפעילה כדי לראות את השינויים.

היכרות עם האפליקציה לדוגמה וקוד ההתחלה

בתור התחלה, אפשר לפתוח את האפליקציה הפעילה בכרטיסיית Chrome החדשה:

  1. מקישים על 'Control+Shift+J' (או על 'Command+Option+J' ב-Mac) כדי לפתוח את כלי הפיתוח.
  2. לוחצים על הכרטיסייה מסוף.

  3. מוודאים שהאפשרות מידע נבחרה בתפריט הנפתח רמות. שליד התיבה מסנן.

  4. במסוף כלי הפיתוח של האפליקציה הפעילה, אמורה להופיע הודעה במסוף:

    TODO: Implement getRegistration().

    זוהי הודעה מ-stub של פונקציה שתטמיעו ב-Codelab הזה.

עכשיו נסתכל על הקוד של האפליקציה לדוגמה מתוך תקלה שמוטמעת בדף הזה.

  1. בתקלה המוטמעת, כדאי להציץ ב-public/index.js:

    • יש ארבעה קטעים (stub) לפונקציות שתטמיעו: registerServiceWorker, getRegistration, unRegisterServiceWorker ו-sendNotification.

    • הפונקציה requestPermission מבקשת הרשאה מהמשתמש לשלוח התראות. אם ביצעתם את הפעולות תחילת העבודה עם ה-Codelab של Notification API, רואים שכאן נעשה שימוש בפונקציה requestPermission שלו. ההבדל היחיד הוא שעכשיו הוא גם מעדכן את ממשק המשתמש אחרי הטיפול בבקשת ההרשאה.

    • הפונקציה updateUI מרעננת את כל הלחצנים וההודעות של האפליקציה.

    • הפונקציה initializePage מבצעת זיהוי תכונות של יכולת של Service Worker בדפדפן ומעדכנת את ממשק המשתמש של האפליקציה.

    • הסקריפט ימתין עד שהדף ייטען ואז מאתחל אותו.

  2. בתקלה המוטמעת, פותחים את public/service-worker.js.

    כפי שהשם מרמז, צריך להוסיף קוד לאפליקציה כדי לרשום את הקובץ הזה service worker.

    אמנם האפליקציה עדיין לא משתמשת בקובץ, אבל הוא מכיל קוד התחלה שידפיס הודעה במסוף כאשר ה-Service Worker יופעל.

    צריך להוסיף קוד אל public/service-worker.js כדי לטפל בהתראות כשה-Service Worker מקבל אותן.

רישום קובץ השירות (service worker)

בשלב הזה צריך לכתוב קוד שרץ כשהמשתמש לוחץ על רישום קובץ השירות (service worker) בממשק המשתמש של האפליקציה. הקוד הזה ירשום את public/service-worker.js כ-Service Worker.

  1. בכלי המוטמע של Glitch Editor, פותחים את public/index.js. מחליפים את הפונקציה registerServiceWorker בקוד הבא:

    // Use the Service Worker API to register a service worker.
    async function registerServiceWorker() {
      await navigator.serviceWorker.register('./service-worker.js')
      updateUI();
    }
    

    לתשומת ליבך, מערכת registerServiceWorker משתמשת בהצהרה async function כדי להקל על הטיפול. כך אפשר await את הערך של Promise שטופל. לדוגמה, הפונקציה שלמעלה ממתינה לתוצאה של רישום Service Worker לפני עדכון ממשק המשתמש. מידע נוסף זמין בכתובת await ב-MDN.

  2. עכשיו, שהמשתמש יכול לרשום קובץ שירות (service worker), אפשר לקבל הפניה לאובייקט הרישום של קובץ השירות. ב-public/index.js, מחליפים את הפונקציה getRegistration בקוד הבא:

    // Get the current service worker registration.
    function getRegistration() {
      return navigator.serviceWorker.getRegistration();
    }
    

    הפונקציה שלמעלה משתמשת ממשק Service Worker API כדי לקבל את הרישום הנוכחי של Service Worker, אם קיים. בעקבות זאת, קל יותר לקבל התייחסות לרישום של קובצי שירות (service worker).

  • כדי להשלים את פונקציית הרישום של קובץ השירות, מוסיפים קוד לביטול הרישום של ה-Service Worker. מחליפים את הפונקציה unRegisterServiceWorker בקוד הבא:

    // Unregister a service worker, then update the UI.
    async function unRegisterServiceWorker() {
      // Get a reference to the service worker registration.
      let registration = await getRegistration();
      // Await the outcome of the unregistration attempt
      // so that the UI update is not superceded by a
      // returning Promise.
      await registration.unregister();
      updateUI();
    }
    

בכרטיסייה שבה מוצגת האפליקציה הפעילה, טוענים מחדש את הדף. הלחצנים רישום Service worker וביטול הרישום של ה-service worker אמורים לפעול עכשיו.

שליחת התראות ל-Service Worker

בשלב הזה צריך לכתוב קוד שירוץ כשהמשתמש ילחץ על שליחת התראה בממשק המשתמש של האפליקציה. הקוד הזה ייצור התראה, יבדוק שה-Service Worker רשום ולאחר מכן ישלח את ההתראה ל-Service Worker באמצעות השיטה postMessage שלו.

בעורך Glitch Editor המוטמע, פותחים את public/index.js מחליפים את הפונקציה sendNotification בקוד הבא:

// Create and send a test notification to the service worker.
async function sendNotification() {
  // Use a random number as part of the notification data
  // (so you can tell the notifications apart during testing!)
  let randy = Math.floor(Math.random() * 100);
  let notification = {
    title: 'Test ' + randy,
    options: { body: 'Test body ' + randy }
  };
  // Get a reference to the service worker registration.
  let registration = await getRegistration();
  // Check that the service worker registration exists.
  if (registration) {
    // Check that a service worker controller exists before
    // trying to access the postMessage method.
    if (navigator.serviceWorker.controller) {
      navigator.serviceWorker.controller.postMessage(notification);
    } else {
      console.log('No service worker controller found. Try a soft reload.');
    }
  }
}

הקוד הזה מבצע:

  • sendNotification היא פונקציה אסינכרונית, כך שאפשר להשתמש ב-await כדי לקבל הפניה לרישום של קובץ שירות (service worker).

  • ה-method postMessage של ה-Service Worker שולחת נתונים מהאפליקציה אל ה-Service Worker. מידע נוסף זמין במסמכי התיעוד של MDN בנושא postMessage.

  • הקוד בודק את נוכחות המאפיין navigator.serviceWorker.controller לפני שמנסים לגשת לפונקציה postMessage. הערך של navigator.serviceWorker.controller יהיה null אם אין קובץ שירות (service worker) פעיל, או אם הדף עבר רענון מאולץ (Shift+טעינה מחדש). מידע נוסף זמין במסמכים בנושא בקר של ServiceWorker ב-MDN.

טיפול בהתראות ב-Service Worker

בשלב הזה צריך לכתוב קוד ב-Service Worker שיטפל בהודעות שיפורסמו בו ויציג התראות למשתמש.

בכלי המוטמע של Glitch Editor, פותחים את public/service-worker.js. מוסיפים את הקוד הבא לסוף הקובץ:

// Show notification when received
self.addEventListener('message', (event) => {
  let notification = event.data;
  self.registration.showNotification(
    notification.title,
    notification.options
  ).catch((error) => {
    console.log(error);
  });
});

הנה הסבר קצר:

  • self הוא קובץ עזר של קובץ השירות עצמו.

  • ה-Service Worker מטפל עכשיו בהצגת ההתראות, אבל ממשק המשתמש הראשי של האפליקציה עדיין אחראי לקבל הרשאה לשליחת התראות מהמשתמש. אם לא יוענק אישור, ההבטחה שמוחזרת על ידי showNotification תידחה. הקוד שלמעלה משתמש בבלוק catch כדי להימנע משגיאת דחייה לא מזוהה של Promise ולטפל בשגיאה הזו בצורה קצת יותר חלקה.

אם נתקעת, אפשר להיכנס לאתר glitch.com/edit/#!/codelab-notifications-service-worker-completed כדי לקבל את הקוד לאחר השלמתו.

ממשיכים ל-Codelab הבא בסדרה: פיתוח שרת התראות.