सर्विस वर्कर से जुड़े अपडेट तुरंत मैनेज करना

डिफ़ॉल्ट रूप से, सर्विस वर्कर लाइफ़साइकल के लिए यह ज़रूरी है कि अपडेट किया गया सर्विस वर्कर मिलने और इंस्टॉल होने पर, मौजूदा सर्विस वर्कर को कंट्रोल किए जा रहे सभी खुले टैब बंद हों या अपडेट किए गए सर्विस वर्कर के चालू होने और कंट्रोल होने से पहले, नेविगेशन किया जाना हो.

कई मामलों में, आने वाले समय में ऐसा करने की अनुमति दी जा सकती है, लेकिन कुछ मामलों में, हो सकता है कि आप उपयोगकर्ता को सूचित करना चाहें कि सर्विस वर्कर का एक अपडेट अभी बाकी है. इसके बाद, नए सर्विस वर्कर पर स्विच करने की प्रोसेस को ऑटोमेट करना. ऐसा करने के लिए, आपको अपने पेज और अपने सर्विस वर्कर में कुछ कोड जोड़ने होंगे.

आपके पेज पर डाला जाने वाला कोड

यह कोड, इनलाइन <script> एलिमेंट में काम करता है. इसके लिए, workbox-window के सीडीएन से होस्ट किए गए वर्शन से इंपोर्ट किए गए JavaScript मॉड्यूल का इस्तेमाल किया जाता है. यह workbox-window का इस्तेमाल करके सर्विस वर्कर को रजिस्टर करता है. अगर सर्विस वर्कर वेटिंग फ़ेज़ में अटक जाता है, तो यह कार्रवाई करता है. जब वेटिंग सर्विस वर्कर का पता चलता है, तो यह कोड उपयोगकर्ता को साइट का अपडेट किया गया वर्शन उपलब्ध होने के बारे में बताता है. साथ ही, साइट को फिर से लोड करने के लिए कहता है.

<!-- This script tag uses JavaScript modules, so the proper `type` attribute value is required -->
<script type="module">
  // This code sample uses features introduced in Workbox v6.
  import {Workbox} from 'https://storage.googleapis.com/workbox-cdn/releases/6.4.1/workbox-window.prod.mjs';

  if ('serviceWorker' in navigator) {
    const wb = new Workbox('/sw.js');
    let registration;

    const showSkipWaitingPrompt = async (event) => {
      // Assuming the user accepted the update, set up a listener
      // that will reload the page as soon as the previously waiting
      // service worker has taken control.
      wb.addEventListener('controlling', () => {
        // At this point, reloading will ensure that the current
        // tab is loaded under the control of the new service worker.
        // Depending on your web app, you may want to auto-save or
        // persist transient state before triggering the reload.
        window.location.reload();
      });

      // When `event.wasWaitingBeforeRegister` is true, a previously
      // updated service worker is still waiting.
      // You may want to customize the UI prompt accordingly.

      // This code assumes your app has a promptForUpdate() method,
      // which returns true if the user wants to update.
      // Implementing this is app-specific; some examples are:
      // https://open-ui.org/components/alert.research or
      // https://open-ui.org/components/toast.research
      const updateAccepted = await promptForUpdate();

      if (updateAccepted) {
        wb.messageSkipWaiting();
      }
    };

    // Add an event listener to detect when the registered
    // service worker has installed but is waiting to activate.
    wb.addEventListener('waiting', (event) => {
      showSkipWaitingPrompt(event);
    });

    wb.register();
  }
</script>

अगर वे अनुरोध स्वीकार करते हैं, तो messageSkipWaiting() इंतज़ार कर रहे सर्विस वर्कर को self.skipWaiting() को शुरू करने के लिए कहता है. इसका मतलब है कि यह चालू हो जाएगा. चालू होने के बाद, नया सर्विस वर्कर किसी भी मौजूदा क्लाइंट को कंट्रोल कर लेगा. इससे workbox-window में controlling इवेंट ट्रिगर होगा. ऐसा होने पर मौजूदा पेज, पहले से कैश मेमोरी में सेव की गई सभी ऐसेट के सबसे नए वर्शन और अपडेट किए गए सर्विस वर्कर में मिले नए रूटिंग लॉजिक का इस्तेमाल करके, फिर से लोड होता है.

सर्विस वर्कर को दिया जाने वाला कोड

अपने पेज के पिछले सेक्शन से कोड मिलने के बाद, आपको अपने सर्विस वर्कर में कुछ कोड जोड़ना होगा. इससे उन्हें यह पता चलेगा कि वेटिंग फ़ेज़ से कब निकलना है. अगर workbox-build के generateSW का इस्तेमाल किया जा रहा है और आपके पास उसका skipWaiting विकल्प false (डिफ़ॉल्ट) पर सेट है, तो इसका इस्तेमाल करें. इसकी वजह यह है कि यहां दिया गया कोड, जनरेट की गई सर्विस वर्कर फ़ाइल में अपने-आप शामिल हो जाएगा.

अगर आपको अपना सर्विस वर्कर लिखना है, तो यह कोड खुद ही जोड़ना होगा. ऐसा injectManifest मोड में, Workbox के किसी बिल्ड टूल के साथ किया जा सकता है:

addEventListener('message', (event) => {
  if (event.data && event.data.type === 'SKIP_WAITING') {
    self.skipWaiting();
  }
});

यह workbox-window से SKIP_WAITING के type मान वाले सर्विस वर्कर को भेजे गए मैसेज सुनेंगे और जब ऐसा होता है, तो self.skipWaiting() पर कॉल करता है. पिछले कोड सैंपल में दिखाए गए workbox-window में messageSkipWaiting() तरीका, इस मैसेज को भेजने के लिए ज़िम्मेदार है.

क्या आपको प्रॉम्प्ट दिखाना है?

यह ऐसा पैटर्न नहीं है जो सर्विस वर्कर को डिप्लॉय करने वाले हर ऐप्लिकेशन को फ़ॉलो करना पड़ता है. यह उन चुनिंदा स्थितियों के लिए है जहां सर्विस वर्कर अपडेट पर, पेज को फिर से लोड करने का मौका न देने पर, अनचाहे व्यवहार देखने को मिल सकते हैं. आपको फिर से लोड करने का प्रॉम्प्ट दिखाना चाहिए या नहीं, यह तय करने के लिए कोई सख्त और तेज़ नियम नहीं है. हालांकि, यहां कुछ स्थितियों के बारे में बताया गया है, जिनमें यह सही लग सकता है:

  • आपने प्रीकैशिंग का बहुत ज़्यादा इस्तेमाल किया है. जहां स्टैटिक ऐसेट की बात की गई है, वहां नेविगेशन के अनुरोधों के लिए, लेज़ी-लोड स्टैटिक ऐसेट का इस्तेमाल करने पर, बाद में समस्याएं आ सकती हैं. ऐसा तब हो सकता है, जब नेविगेशन के अनुरोधों के लिए, नेटवर्क-फ़र्स्ट या सिर्फ़ नेटवर्क वाली रणनीति का इस्तेमाल किया गया हो. इसकी वजह से ऐसी स्थितियां बन सकती हैं जिनमें वर्शन वाली ऐसेट बदल सकती हैं और किसी सर्विस वर्कर ने उन्हें प्रीकैश नहीं किया है. पेज पर 'फिर से लोड करें' बटन देने से, कुछ अनचाहे व्यवहार से बचा जा सकता है.
  • अगर प्रीकैश मेमोरी में सेव किया गया एचटीएमएल दिखाया जा रहा है. इस स्थिति में, आपको strong को सर्विस वर्कर अपडेट पर 'फिर से लोड करें' बटन ऑफ़र करना चाहिए, क्योंकि उस एचटीएमएल के अपडेट की पहचान तब तक नहीं की जाएगी जब तक कि अपडेट किया गया सर्विस वर्कर कंट्रोल नहीं कर लेता.
  • अगर रनटाइम के दौरान कैश मेमोरी का इस्तेमाल करना ज़्यादा ज़रूरी नहीं है, तो ऐसा हो सकता है. रनटाइम के दौरान संसाधनों को कैश मेमोरी में सेव करते समय, आपको उपयोगकर्ता को यह बताने की ज़रूरत नहीं है कि उन्हें फिर से लोड करना चाहिए. वर्शन वाली ऐसेट में बदलाव होने पर, उन्हें आने वाले समय में रनटाइम कैश मेमोरी में जोड़ दिया जाएगा. ऐसा तब होगा, जब नेविगेशन के अनुरोध सिर्फ़ नेटवर्क को ध्यान में रखकर या सिर्फ़ नेटवर्क से जुड़ी रणनीति का इस्तेमाल करेंगे.
  • फिर से पुष्टि करते समय पुरानी जानकारी वाली रणनीति का इस्तेमाल करते समय, उपयोगकर्ताओं को सर्विस वर्कर के अपडेट होने की सूचना देने के लिए, workbox-broadcast-update मॉड्यूल का इस्तेमाल किया जा सकता है.

आपको सर्विस वर्कर के अपडेट के बारे में उपयोगकर्ता को सूचित करना है या नहीं, यह आपके ऐप्लिकेशन और उसकी खास ज़रूरतों पर निर्भर करता है. अगर आपको लगता है कि किसी नए सर्विस वर्कर को पुश करने पर आपके उपयोगकर्ताओं को अजीब व्यवहार महसूस हो रहा है, तो यह सबसे अच्छा सिग्नल होगा कि आपको उन्हें सूचित करना चाहिए.