שליפה מראש (prefetch) של יצירת תגובה באפליקציה באמצעות Quicklink

Addy Osmani
Addy Osmani
Anton Karlovskiy
Anton Karlovskiy
Demián Renzulli
Demián Renzulli

ב-Codelab הזה מוסבר איך להטמיע את ספריית Quicklink בהדגמה של React SPA כדי להדגים איך השליפה מראש מזרזת את הניווטים הבאים.

מדידה

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

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

האתר הוא הדגמה פשוטה שנוצרה באמצעות create-react-app.

בכרטיסייה החדשה שנפתחה עכשיו, מבצעים את ההוראות הבאות:

  1. מקישים על 'Control+Shift+J' (או על 'Command+Option+J' ב-Mac) כדי לפתוח את כלי הפיתוח.
  2. לוחצים על הכרטיסייה רשתות.
  3. מסמנים את התיבה Disable cache (השבתת מטמון).
  4. ברשימה הנפתחת של ויסות נתונים (throttle), בוחרים באפשרות Fast 3G כדי לדמות סוג חיבור איטי.
  5. טוענים מחדש את האפליקציה.
  6. כדי להסתיר משאבים שלא כוללים את chunk בשם, צריך להקליד chunk בתיבת הטקסט של המסנן.

חלונית רשת שבה מוצגים המקטעי דף הבית.

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

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

מקטעי ה-JS וה-CSS של הנתיב החדש נטענים כדי לעבד את הדף.

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

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

כך תוכלו לשלב את היתרונות של שתי הטכניקות:

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

הגדרה של webpack-route-manifest

השלב הראשון הוא להתקין ולהגדיר את webpack-route-manifest, פלאגין של Webpack שמאפשר ליצור קובץ מניפסט שמשייך מסלולים למקטעי הנתונים התואמים.

בדרך כלל צריך להתקין את הספרייה, אבל כבר ביצענו את הפעולה הזו בשבילך. זו הפקודה שצריך להריץ:

npm install webpack-route-manifest --save-dev

config-overrides.js הוא קובץ שממוקם בספריית הבסיס של הפרויקט, שבו אפשר לשנות את ההתנהגות הקיימת של הגדרת ה-webpack בלי להוציא את הפרויקט.

  • כדי להציג את המקור, מקישים על הצגת מקור.

פותחים את config-overrides.js לעריכה ומוסיפים את התלות webpack-route-manifest בתחילת הקובץ:

const path = require('path');
const RouteManifest = require('webpack-route-manifest');

בשלב הבא, צריך להגדיר את הפלאגין webpack-route-manifest על ידי הוספת הקוד הבא קוד עד החלק התחתון של config-overrides.js:

module.exports = function override(config) {
  config.resolve = {
    ...config.resolve,
    alias: {
      '@assets': `${path.resolve(__dirname, 'src/assets')}`,
      '@pages': `${path.resolve(__dirname, 'src/pages')}`,
      '@components': `${path.resolve(__dirname, 'src/components')}`,
    },
  };

  config.plugins.push(
    new RouteManifest({
      minify: true,
      filename: 'rmanifest.json',
      routes(str) {
        let out = str.replace('@pages', '').toLowerCase();
        if (out === '/article') return '/blog/:title';
        if (out === '/home') return '/';
        return out;
      },
    }),
  );

  return config;
};

הקוד החדש מבצע את הפעולות הבאות:

  • config.resolve מצהירה על משתנים עם המסלולים הפנימיים אל דפים, נכסים ורכיבים.
  • config.plugins.push() יוצר אובייקט RouteManifest ומעביר לו את ההגדרות האישיות כדי שיהיה אפשר ליצור את הקובץ rmanifest.json על סמך המסלולים והמקטעי נתונים של האתר.

הקובץ manifest.json ייווצר ויהיה זמין בכתובת https://site_url/rmanifest.json.

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

npm install --save quicklink

צריך לפתוח את src/components/App/index.js לעריכה.

קודם כול, מייבאים את הרכיב מסוג 'קישור מהיר יותר' (HOC):

import React, { lazy, Suspense } from 'react';
import { Route } from 'react-router-dom';

import Footer from '@components/Footer';
import Hero from '@components/Hero';
import style from './index.module.css';
import { withQuicklink } from 'quicklink/dist/react/hoc.js';

const Home = lazy(() => import(/* webpackChunkName: "home" */ '@pages/Home'));
const About = lazy(() => import(/* webpackChunkName: "about" */ '@pages/About'));
const Article = lazy(() => import(/* webpackChunkName: "article" */ '@pages/Article'));
const Blog = lazy(() => import(/* webpackChunkName: "blog" */ '@pages/Blog'));

בשלב הבא, יוצרים אובייקט options אחרי הצהרת המשתנה Blog, שישמש כארגומנט כשקוראים לפונקציה quicklink:

const options = {
    origins: []
};

בשלב האחרון, אורפים כל מסלול עם הרכיב withQuicklink() שבסדר גבוה יותר, מעבירים אליו את הפרמטר options ואת רכיב היעד של המסלול הזה:

const App = () => (
  <div className={style.app}>
    <Hero />
    <main className={style.wrapper}>
      <Suspense fallback={<div>Loading...</div>}>
        <Route path="/" exact component={withQuicklink(Home, options)} />
        <Route path="/blog" exact component={withQuicklink(Blog, options)} />
        <Route
          path="/blog/:title"
          component={withQuicklink(Article, options)}
        />
        <Route path="/about" exact component={withQuicklink(About, options)} />
      </Suspense>
    </main>
    <Footer />
  </div>
);

הקוד הקודם מורה מראש לשלוף מראש מקטעים בשביל מסלולים שארוזים ב-withQuicklink(), כשהקישור נכנס לתצוגה.

מדידה חוזרת

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

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

חלונית רשת שמוצגים בה מקטעי השליפה מראש (prefetch) של דף הבית.

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

הבא:

  1. מנקים שוב את יומן הרשת.
  2. משביתים את תיבת הסימון Disable cache.
  3. לוחצים על הקישור Blogger כדי לעבור לדף הזה.

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

בעמודה גודל מצוין שהמקטעים האלה אוחזרו מה'מטמון מראש', ולא מהרשת. טעינת המקטעים ללא קישור מהיר נמשכה כ-580 אלפיות השנייה. השימוש בספרייה נמשך עכשיו 2 אלפיות השנייה, שמייצג הפחתה של 99% !