การใช้งานการนำทางทันใจ

การเสริมเทคนิคการดึงข้อมูลล่วงหน้าแบบดั้งเดิมด้วย Service Worker

การดำเนินการในเว็บไซต์มักมีหลายขั้นตอน ตัวอย่างเช่น การซื้อผลิตภัณฑ์ในเว็บไซต์อีคอมเมิร์ซอาจเกี่ยวข้องกับการค้นหาผลิตภัณฑ์ การเลือกสินค้าจากรายการผลการค้นหา เพิ่มสินค้าลงในรถเข็น และดำเนินการให้เสร็จสมบูรณ์ด้วยการชำระเงิน

ในทางเทคนิคแล้ว การย้ายผ่านหน้าต่างๆ หมายถึงการสร้างคำขอการนำทาง ตามกฎทั่วไป คุณไม่ต้องการใช้ส่วนหัว Cache-Control ที่ใช้ได้นานเพื่อแคชการตอบกลับ HTML สำหรับคำขอการนำทาง โดยปกติแล้วผู้ใช้ควรพอใจผ่านเครือข่ายด้วย Cache-Control: no-cache เพื่อให้มั่นใจว่า HTML รวมถึงเชนของคำขอเครือข่ายที่ตามมามีความใหม่ (อย่างสมเหตุสมผล) การที่ต้องเชื่อมต่อกับเครือข่ายทุกครั้งที่ผู้ใช้ไปยังหน้าใหม่หมายความว่าการนำทางแต่ละครั้งอาจทำได้ช้า และอย่างน้อยที่สุดก็หมายความว่าการนำทางนั้นจะไม่เร็วที่เชื่อถือได้

เพื่อให้คำขอเหล่านี้รวดเร็วขึ้น หากคุณสามารถคาดการณ์การดำเนินการของผู้ใช้ได้ คุณสามารถขอหน้าเว็บและองค์ประกอบเหล่านี้ล่วงหน้า และเก็บไว้ในแคชเป็นระยะเวลาสั้นๆ จนกว่าผู้ใช้จะคลิกลิงก์เหล่านี้ เทคนิคนี้เรียกว่าprefetching และโดยทั่วไปมักจะนำมาใช้โดยการเพิ่มแท็ก <link rel="prefetch"> ลงในหน้าเว็บต่างๆ เพื่อบ่งบอกถึงทรัพยากรที่จะดึงข้อมูลล่วงหน้า

ในคู่มือนี้เราจะสำรวจวิธีต่างๆ ที่คุณจะใช้โปรแกรมทำงานของบริการร่วมกับเทคนิคการดึงข้อมูลล่วงหน้าแบบดั้งเดิมได้

เคสการผลิต

MercadoLibre เป็นเว็บไซต์อีคอมเมิร์ซที่ใหญ่ที่สุดในลาตินอเมริกา บริษัทจะแทรกแท็ก <link rel="prefetch"> แบบไดนามิกในบางส่วนของขั้นตอน เพื่อเพิ่มความเร็วในการไปยังส่วนต่างๆ ตัวอย่างเช่น ในหน้ารายชื่อ ผู้ใช้จะดึงข้อมูลหน้าผลลัพธ์ถัดไปทันทีที่ผู้ใช้เลื่อนลงไปที่ด้านล่างของรายชื่อ

ภาพหน้าจอหน้ารายชื่อ 1 และ 2 ของ MercadoLibre พร้อมแท็กการดึงข้อมูลลิงก์ล่วงหน้าที่เชื่อมต่อทั้ง 2 หน้า

ระบบขอไฟล์ที่ดึงข้อมูลล่วงหน้าได้ที่ระดับ "ต่ำสุด" และจัดเก็บไว้ในแคช HTTP หรือแคชหน่วยความจำ (ขึ้นอยู่กับว่าทรัพยากรดังกล่าวสามารถแคชได้หรือไม่) โดยเป็นระยะเวลาที่แตกต่างกันไปตามเบราว์เซอร์ ตัวอย่างเช่น สำหรับ Chrome 85 ค่านี้คือ 5 นาที ระบบจะเก็บทรัพยากรไว้ประมาณ 5 นาที หลังจากนั้นกฎ Cache-Control ปกติสำหรับทรัพยากรจะมีผลบังคับใช้

การใช้การแคชของ Service Worker จะช่วยยืดอายุการใช้งานของการดึงข้อมูลทรัพยากรล่วงหน้าไปมากกว่ากรอบเวลา 5 นาที

ตัวอย่างเช่น Virgilio Sport ซึ่งเป็นพอร์ทัลกีฬาของอิตาลีจะใช้โปรแกรมทำงานของบริการเพื่อดึงข้อมูลโพสต์ที่ได้รับความนิยมสูงสุดในหน้าแรกล่วงหน้า นอกจากนี้ ยังใช้ Network Information API เพื่อหลีกเลี่ยงการดึงข้อมูลล่วงหน้าสำหรับผู้ใช้ที่ใช้การเชื่อมต่อ 2G ด้วย

โลโก้ Virgilio Sport

ผลที่ตามมาคือจากการสังเกตการณ์ Virgilio Sport เห็นเวลาในการโหลดสำหรับการนำทางไปยังบทความเพิ่มขึ้น 78% และจำนวนการแสดงผลบทความเพิ่มขึ้น 45%

ภาพหน้าจอของหน้าแรกและหน้าบทความของ Virgilio Sport พร้อมเมตริกผลกระทบหลังจากการดึงข้อมูลล่วงหน้า

ใช้การแคชล่วงหน้าด้วย Workbox

ในส่วนต่อไปนี้ เราจะใช้กล่องทำงานเพื่อแสดงวิธีการใช้เทคนิคการแคชต่างๆ ใน Service Worker ที่สามารถใช้เป็นส่วนเสริมของ <link rel="prefetch"> หรือแม้แต่ใช้ทดแทนโดยการมอบสิทธิ์งานนี้ให้กับ Service Worker โดยสมบูรณ์

1. หน้าเว็บแบบคงที่และทรัพยากรย่อยของหน้าเพื่อแคชล่วงหน้า

การแคชล่วงหน้าเป็นความสามารถของโปรแกรมทำงานของบริการเพื่อบันทึกไฟล์ไปยังแคชขณะติดตั้ง

กรณีต่อไปนี้คือการใช้การแคชล่วงหน้าเพื่อให้บรรลุเป้าหมายที่คล้ายกับการดึงข้อมูลล่วงหน้า นั่นคือการทำให้การนำทางรวดเร็วขึ้น

การแคชหน้าเว็บแบบคงที่ล่วงหน้า

สำหรับหน้าเว็บที่สร้างขึ้น ณ เวลาสร้าง (เช่น about.html, contact.html) หรือในเว็บไซต์ที่คงที่โดยสมบูรณ์ หนึ่งเอกสารสามารถเพิ่มเอกสารของเว็บไซต์ไปยังรายการแคชล่วงหน้า เอกสารเหล่านี้จะพร้อมใช้งานในแคชทุกครั้งที่ผู้ใช้เข้าถึงเอกสาร:

workbox.precaching.precacheAndRoute([
  {url: '/about.html', revision: 'abcd1234'},
  // ... other entries ...
]);

ทรัพยากรย่อยของหน้าการแคชล่วงหน้า

การแคชเนื้อหาแบบคงที่ล่วงหน้าซึ่งส่วนต่างๆ ของเว็บไซต์อาจใช้ (เช่น JavaScript, CSS ฯลฯ) เป็นแนวทางปฏิบัติแนะนำทั่วไปและจะช่วยเพิ่มสถานการณ์การดึงข้อมูลล่วงหน้าให้มากขึ้น

หากต้องการเพิ่มความเร็วในการไปยังส่วนต่างๆ ในเว็บไซต์อีคอมเมิร์ซ ให้ใช้แท็ก <link rel="prefetch"> ในหน้าข้อมูลเพื่อดึงข้อมูลหน้ารายละเอียดผลิตภัณฑ์ล่วงหน้าสำหรับผลิตภัณฑ์ 2-3 รายการแรกของหน้าข้อมูล หากคุณแคชทรัพยากรย่อยของหน้าผลิตภัณฑ์ไว้ล่วงหน้าแล้ว ก็จะช่วยให้ไปยังส่วนต่างๆ ได้เร็วขึ้น

หากต้องการดำเนินการดังกล่าว ให้ทำดังนี้

  • เพิ่มแท็ก <link rel="prefetch"> ลงในหน้า
 <link rel="prefetch" href="/phones/smartphone-5x.html" as="document">
  • เพิ่มทรัพยากรย่อยของหน้าลงในรายการแคชล่วงหน้าใน Service Worker ดังนี้
workbox.precaching.precacheAndRoute([
  '/styles/product-page.ac29.css',
  // ... other entries ...
]);

2. ยืดอายุการใช้งานของทรัพยากรสำหรับการดึงข้อมูลล่วงหน้า

ดังที่กล่าวไว้ก่อนหน้านี้ <link rel="prefetch"> จะดึงข้อมูลและเก็บทรัพยากรในแคช HTTP เป็นระยะเวลาหนึ่ง หลังจากนั้นจะมีการใช้กฎ Cache-Control สำหรับทรัพยากร ค่านี้คือ 5 นาทีสำหรับ Chrome 85

Service Worker ช่วยให้คุณยืดอายุการใช้งานของหน้าเว็บที่ดึงข้อมูลล่วงหน้าได้ ขณะเดียวกันก็ให้ประโยชน์เพิ่มเติมในการทำให้ทรัพยากรเหล่านี้พร้อมใช้งานแบบออฟไลน์ด้วย

ในตัวอย่างก่อนหน้านี้ ตัวแปรสามารถเสริม <link rel="prefetch"> ที่ใช้ในการดึงข้อมูลหน้าผลิตภัณฑ์ล่วงหน้าด้วยกลยุทธ์การแคชรันไทม์ของ Workbox

ในการใช้งาน ให้ทำดังนี้

  • เพิ่มแท็ก <link rel="prefetch"> ลงในหน้า
 <link rel="prefetch" href="/phones/smartphone-5x.html" as="document">
  • ใช้กลยุทธ์การแคชรันไทม์ใน Service Worker สำหรับคำขอประเภทต่อไปนี้
new workbox.strategies.StaleWhileRevalidate({
  cacheName: 'document-cache',
  plugins: [
    new workbox.expiration.Plugin({
      maxAgeSeconds: 30 * 24 * 60 * 60, // 30 Days
    }),
  ],
});

ในกรณีนี้ เราเลือกใช้กลยุทธ์ที่ไม่มีการอัปเดตขณะตรวจสอบความถูกต้องอีกครั้ง ในกลยุทธ์นี้ หน้าเว็บสามารถขอได้จากทั้งแคชและเครือข่ายพร้อมกัน การตอบกลับจะมาจากแคช (หากมี) หรือมาจากเครือข่าย แคชจะอัปเดตอยู่เสมอเมื่อมีคำขอที่สำเร็จแต่ละรายการ

3. มอบสิทธิ์การดึงข้อมูลล่วงหน้าให้กับ Service Worker

ในกรณีส่วนใหญ่ วิธีที่ดีที่สุดคือการใช้ <link rel="prefetch"> แท็กนี้เป็นคำแนะนำด้านทรัพยากรที่ออกแบบมาเพื่อทำให้การดึงข้อมูลล่วงหน้ามีประสิทธิภาพมากที่สุดเท่าที่จะเป็นไปได้

แต่ในบางกรณี การมอบสิทธิ์ทำงานนี้ทั้งหมดให้กับโปรแกรมทำงานของบริการอาจเป็นประโยชน์มากกว่า เช่น หากต้องการดึงข้อมูลผลิตภัณฑ์ 2-3 รายการแรกล่วงหน้าในหน้าข้อมูลผลิตภัณฑ์ที่แสดงฝั่งไคลเอ็นต์ ลูกค้าอาจต้องแทรกแท็ก <link rel="prefetch"> หลายรายการแบบไดนามิกในหน้าเว็บตามการตอบกลับของ API ซึ่งอาจใช้เวลานานในเทรดหลักของหน้าและทําให้ติดตั้งใช้งานได้ยากขึ้น

ในกรณีเช่นนี้ ให้ใช้ "กลยุทธ์การสื่อสารของโปรแกรมทำงานของบริการ (Page to Service Worker)" เพื่อมอบหมายงานสำหรับการดึงข้อมูลล่วงหน้าให้แก่ Service Worker โดยสมบูรณ์ คุณสื่อสารประเภทนี้ได้โดยใช้ worker.postMessage():

ไอคอนของหน้าที่เป็นการสื่อสารแบบ 2 ทางกับ Service Worker

แพ็กเกจหน้าต่าง Workbox จะช่วยลดความซับซ้อนของการสื่อสารประเภทนี้ โดยลดรายละเอียดต่างๆ ของการเรียกที่ดำเนินอยู่

การดึงข้อมูลล่วงหน้าด้วยหน้าต่างกล่องงานสามารถใช้วิธีดังต่อไปนี้

  • ในหน้าเว็บ ให้เรียกใช้ Service Worker ผ่านประเภทของข้อความและรายการ URL ที่จะดึงข้อมูลล่วงหน้า ดังนี้
const wb = new Workbox('/sw.js');
wb.register();

const prefetchResponse = await wb.messageSW({type: 'PREFETCH_URLS', urls: []});
  • ในโปรแกรมทำงานของบริการ: ใช้เครื่องจัดการข้อความเพื่อส่งคำขอ fetch() สำหรับ URL แต่ละรายการเพื่อดึงข้อมูลล่วงหน้า
addEventListener('message', (event) => {
  if (event.data.type === 'PREFETCH_URLS') {
    // Fetch URLs and store them in the cache
  }
});