איך שליפה מראש (prefetch) עזרה ל-Terra להגדיל את שיעור הקליקים על המודעות ב-30% ולהאיץ את פעולת Largest Contentful Paint (LCP).

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

Guilherme Moser de Souza
Guilherme Moser de Souza

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

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

בניתוח המקרה הזה מתוארת ההטמעה של Terra, שהובילה לעלייה של 11% בשיעור הקליקים (CTR) על מודעות בנייד, לעלייה של 30% בשיעור הקליקים על מודעות במחשב ולירידה של 50% בזמני Largest Contentful Paint‏ (LCP).

אסטרטגיית שליפה מראש (prefetch)

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

  • החשיפה של קישורים למאמרים שנשמרו במטמון: צוות Terra השתמש ב-Intersection Observer API כדי לזהות את החשיפה של הקטע שמכיל את המאמרים שהם רצו לשמור במטמון.
  • תנאים נוחים לשימוש מוגבר בנתונים: כפי שצוין קודם, אחסון נתונים לפני האצווה הוא שיפור ספקולטיבי בביצועים שצורך נתונים נוספים, ויכול להיות שהוא לא רצוי בכל מצב. כדי לצמצם את הסיכוי לבזבוז רוחב פס, Terra משתמשת ב-Network Information API יחד עם Device Memory API כדי לקבוע אם לאחזר את המאמר הבא. Terra מאחזרת את המאמר הבא רק כאשר:
    • מהירות החיבור היא 3G לפחות ולמכשיר יש זיכרון בנפח של 4GB לפחות.
    • או אם המכשיר פועל עם iOS.
  • מעבד (CPU) לא פעיל: לבסוף, Terra בודקת אם המעבד לא פעיל ומסוגל לבצע פעולות נוספות באמצעות הפקודה requestIdleCallback, שמחכה עיבוד של קריאה חוזרת כשה-thread הראשי לא פעיל, או עד תאריך יעד ספציפי (אופציונלי) – המוקדם מביניהם.

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

כשהתנאים האלה מתקיימים, מערכת Terra מבצעת אחסון מראש של המאמרים שמופיעים בקטעים 'תוכן קשור' ו'מומלץ בשבילך', שמודגשים בכחול בהמשך.

צילום מסך של שני הקטעים באתר Terra שבהם בוצע אחזור מראש של קישורים. בצד ימין, הקטע 'תוכן קשור' מודגש, ובצד שמאל, הקטע 'מומלץ בשבילך' מודגש.

ההשפעה על העסק

כדי למדוד את ההשפעה של הטכניקה הזו, התכונה הזו הושקה ב-Terra לראשונה בקטע 'תוכן קשור' בדף המאמר. קוד של מנטר התנועה של Urchin עזר לחברה להבחין בין מאמרים שנשלפו מראש לבין מאמרים שלא נשלפו מראש, למטרות השוואה. אחרי שבועיים של בדיקת A/B מוצלחת, ב-Terra החליטו להוסיף את הפונקציונליות של אחסון נתונים מראש לקטע 'מומלץ בשבילך'.

כתוצאה משליפה מראש של מאמרים, הייתה עלייה כוללת במדדי המודעות וירידה בזמני ה-LCP ו-Time to First Byte (TTFB):

מדד נייד מחשב
שיעור הקליקים ב-Google Ads 11%+ 30%+
הנראות של המודעות ‎+10.5% ‎+6%
LCP 51%- ‎-73%
TTFB -83% ‎-84%

אם משתמשים בטעינה מראש (Pre-fetch) בזהירות, היא משפרת באופן משמעותי את זמן הטעינה של הדפים, משפרת את מדדי המודעות ומקצרת את זמן ה-LCP.

פרטים טכניים

אפשר לבצע אחזור מראש באמצעות רמזים למשאבים כמו rel=prefetch או rel=preload, דרך ספריות כמו quicklink או Guess.js, או באמצעות Speculation Rules API החדש יותר. ב-Terra בחרו להטמיע את הפתרון הזה באמצעות fetch API עם עדיפות נמוכה בשילוב עם מופע של Intersection Observer. ב-Terra בחרו באפשרות הזו כי היא מאפשרת להם לתמוך ב-Safari, שעדיין לא תומך בשיטות אחרות של אחסון נתונים מראש כמו rel=prefetch או Speculation Rules API, וספריית JavaScript עם תכונות מלאות לא הייתה נחוצה לצרכים של Terra.

קוד ה-JavaScript הבא שווה בערך לקוד שבו משתמשת Terra:

function prefetch(nodeLists) {
  // Exclude slow ECTs < 3g
  if (navigator.connection &&
    (navigator.connection.effectiveType === 'slow-2g'
      || navigator.connection.effectiveType === '2g')
  ) {
    return;
  }

  // Exclude low end device which is device with memory <= 2GB
  if (navigator.deviceMemory && navigator.deviceMemory <= 2) {
    return;
  }

  const fetchLinkList = {};

  const observer = new IntersectionObserver(function (entries) {
    entries.forEach(function (entry) {
      if (entry.isIntersecting) {
        if (!fetchLinkList[entry.target.href]) {
          fetchLinkList[entry.target.href] = true;

          fetch(entry.target, {
            priority: 'low'
          });
        }

        observer.unobserve(entry = entry.target);
      }
    });
  });
}

const idleCallback = window.requestIdleCallback || function (cb) {
  let start = Date.now();

  return setTimeout(function () {
    cb({
      didTimeout: false,
      timeRemaining: function () {
        return Math.max(0, 50 - (Date.now() - start));
      }
    });
  }, 1);
}

idleCallback(function () {
  prefetch(nodeLists)
})
  • לפני שמתחילים את האחזור המקדים, הפונקציה prefetch בודקת קודם את איכות החיבור המינימלית ואת נפח הזיכרון במכשיר.
  • אחר כך היא משתמשת ב-IntersectionObserver כדי לעקוב אחרי הזמן שבו רכיבים הופכים לגלויים באזור התצוגה, ואז מוסיפה כתובות URL לרשימה לצורך שליפה מראש.
  • תהליך האחזור מראש מתוזמן באמצעות requestIdleCallback, במטרה להריץ את הפונקציה prefetch כשהשרשור הראשי לא פעיל.

סיכום

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

תודה מיוחדת ל-Gilberto Cocchi, ‏ Harry Theodoulou, ‏ Miguel Carlos Martínez Díaz, ‏ Barry Pollard, ‏ Jeremy Wagner, ‏ Leonardo Bellini ו-Lucca Paradeda מצוות המהנדסים של Terra על התרומה שלהם לעבודה הזו.