שתי דרכים לשליפה מראש (prefetch): תגי <link> וכותרות HTTP

Demián Renzulli
Demián Renzulli

ב-codelab הזה נטמיע אחזור מראש בשתי דרכים: באמצעות <link rel="prefetch"> ובאמצעות כותרת HTTP Link.

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

מדידת ביצועים

קודם צריך לקבוע את רמת הביצועים הבסיסית:

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

  3. ברשימה הנפתחת ויסות נתונים (throttle), בוחרים באפשרות 3G מהיר כדי לדמות סוג חיבור איטי.

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

טעינת הדף product-details.html נמשכת כ-600 אלפיות השנייה:

חלונית &#39;רשת&#39; שמוצגים בה זמני הטעינה של product-details.html

כדי לשפר את הניווט, מוסיפים תג prefetch בדף הנחיתה כדי לבצע אחזור מראש של הדף product-details.html:

  • מוסיפים את רכיב <link> הבא ל-head של קובץ views/index.html:
<!doctype html>
  <html>
    <head>
       <meta charset="UTF-8">
      <meta name="viewport" content="width=device-width, initial-scale=1.0">
      <link href="https://fonts.googleapis.com/css?family=Montserrat&display=swap" rel="stylesheet">

      <link rel="prefetch" href="/product-details.html" as="document">
      ...
</head>

המאפיין as הוא אופציונלי אבל מומלץ. הוא עוזר לדפדפן להגדיר את הכותרות הנכונות ולקבוע אם המשאב כבר נמצא במטמון. דוגמאות לערכים במאפיין הזה: document, script, style, font, image ואחרים.

כדי לוודא שהטעינה מראש פועלת:

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

  3. ברשימה הנפתחת ויסות נתונים (throttle), בוחרים באפשרות 3G מהיר כדי לדמות סוג חיבור איטי.

  4. מבטלים את הסימון בתיבת הסימון 'השבתת המטמון'.

  5. טוענים מחדש את האפליקציה.

עכשיו, כשטוענים את דף הנחיתה, גם הדף product-details.html נטען, אבל בעדיפות הנמוכה ביותר:

חלונית הרשת שמציגה את הקובץ product-details.html שבוצעה לו אחזור מראש.

הדף נשמר במטמון HTTP למשך חמש דקות, ואז חלים עליו הכללים הרגילים של Cache-Control לגבי המסמך. במקרה הזה, product-details.html כולל כותרת cache-control עם הערך public, max-age=0, כלומר הדף נשמר למשך חמש דקות.

הערכה מחדש של הביצועים

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

בודקים את החלונית רשת. יש שני הבדלים בהשוואה למעקב הרשת הראשוני:

  • בעמודה גודל מוצג הערך 'מטמון השליפה מראש (prefetch)', כלומר המשאב הזה אוחזר מהמטמון של הדפדפן ולא מהרשת.
  • בעמודה Time (זמן) אפשר לראות שהזמן שנדרש לטעינת המסמך הוא עכשיו כ-10 אלפיות השנייה.

זו ירידה של כ-98% בהשוואה לגרסה הקודמת, שזמן הטעינה שלה היה כ-600 אלפיות השנייה.

חלונית הרשת שמציגה את product-details.html שאוחזר ממטמון השליפה מראש.

נקודות בונוס: שימוש ב-prefetch כשיפור הדרגתי

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

כדי להטמיע אחזור מראש דינמי, קודם מסירים את התג <link rel="prefetch"> מ-views/index.html:

<!doctype html>
  <html>
    <head>
       <meta charset="UTF-8">
       <meta name="viewport" content="width=device-width, initial-scale=1.0">
       <link href="https://fonts.googleapis.com/css?family=Montserrat&display=swap" rel="stylesheet">
       <link rel="prefetch" href="/product-details.html" as="document">
       ...
    </head>

לאחר מכן מוסיפים את הקוד הבא ל-public/script.js כדי להצהיר על פונקציה שמזריקה באופן דינמי את התג prefetch כשהמשתמש מחובר לחיבור מהיר:

function injectLinkPrefetchIn4g(url) {
    if (window.navigator.connection.effectiveType === '4g') {
        //generate link prefetch tag
        const linkTag = document.createElement('link');
        linkTag.rel = 'prefetch';
        linkTag.href = url;
        linkTag.as = 'document';

        //inject tag in the head of the document
        document.head.appendChild(linkTag);
    }
}

הפונקציה פועלת באופן הבא:

  • הסקריפט בודק את המאפיין effectiveType של Network Information API כדי לקבוע אם המשתמש מחובר לרשת 4G (או לרשת מהירה יותר).
  • אם התנאי הזה מתקיים, נוצר תג <link> עם prefetch כסוג הרמז, כתובת ה-URL שתתבצע לגביה אחזור מראש מועברת במאפיין href, ומצוין שהמשאב הוא HTML document במאפיין as.
  • לבסוף, הסקריפט מוזרק באופן דינמי ל-head של הדף.

לאחר מכן מוסיפים את התג script.js ל-views/index.html, ממש לפני תג הסגירה </body>:

<body>
      ...
      <script src="/script.js"></script>
</body>

הוספת התג script.js בסוף הדף מבטיחה שהוא ייטען ויופעל אחרי שהדף ינותח וייטען.

כדי לוודא שהטעינה מראש לא מפריעה למשאבים חיוניים בדף הנוכחי, מוסיפים את קטע הקוד הבא כדי להפעיל את injectLinkPrefetchIn4g() באירוע window.load:

<body>
      ...
      <script src="/script.js"></script>
      <script>
           window.addEventListener('load', () => {
                injectLinkPrefetchIn4g('/product-details.html');
           });
      </script>
</body>

דף הנחיתה מבצע עכשיו אחזור מראש product-details.html רק בחיבורים מהירים. כדי לוודא ש:

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

אמור להופיע product-details.html בחלונית 'רשת':

חלונית הרשת שמציגה את הקובץ product-details.html שבוצעה לו אחזור מראש.

כדי לוודא שדף המוצר לא נטען מראש בחיבורים איטיים:

  1. ברשימה הנפתחת 'ויסות נתונים', בוחרים באפשרות 3G איטי.
  2. טוענים מחדש את האפליקציה.

החלונית רשת צריכה לכלול רק את המשאבים של דף הנחיתה ללא product-details.html:

חלונית הרשת שבה מוצג שלא מתבצע אחזור מראש של product-details.html.

אפשר להשתמש בכותרת ה-HTTP ‏Link כדי לבצע אחזור מראש של משאבים מאותו סוג כמו התג link. ההחלטה מתי להשתמש באפשרות אחת או באפשרות השנייה תלויה בעיקר בהעדפה שלכם, כי ההבדל בביצועים לא משמעותי. במקרה כזה, תשתמשו בו כדי לבצע אחזור מראש של ה-CSS הראשי של דף המוצר, כדי לשפר עוד יותר את העיבוד שלו.

מוסיפים כותרת HTTP‏ Link ל-style-product.css בתגובת השרת לדף הנחיתה:

  1. פותחים את הקובץ server.js ומחפשים את ה-handler של כתובת ה-URL הבסיסית: /.get()
  2. מוסיפים את השורה הבאה בתחילת ה-handler:
app.get('/', function(request, response) {
    response.set('Link', '</style-product.css>; rel=prefetch');
    response.sendFile(__dirname + '/views/index.html');
});
  1. מקישים על Control+Shift+J (או על Command+Option+J ב-Mac) כדי לפתוח את כלי הפיתוח.
  2. לוחצים על הכרטיסייה רשת.
  3. טוענים מחדש את האפליקציה.

ה-style-product.css מאוחזר מראש עכשיו בעדיפות הנמוכה ביותר אחרי טעינת דף הנחיתה:

חלונית הרשת שבה מוצג style-product.css שהובא מראש.

כדי לעבור לדף המוצר, לוחצים על קנייה. כדאי לבדוק את החלונית Network:

חלונית הרשת שבה מוצג style-product.css שאוחזר ממטמון של שליפה מראש.

הקובץ style-product.css נשלף מ'מטמון הטעינה מראש' והטעינה שלו ארכה רק 12 אלפיות השנייה.