پیکربندی رفتار ذخیره‌سازی موقت HTTP

این codelab به شما نشان می‌دهد که چگونه سراینده‌های ذخیره‌سازی موقت HTTP را که توسط یک سرور وب مبتنی بر Node.js برگردانده شده‌اند، با اجرای چارچوب سرویس‌دهی Express تغییر دهید. همچنین نشان می‌دهد که چگونه بااستفاده از پانل «شبکه» در Chrome DevTools تأیید کنید که رفتار ذخیره‌سازی موردانتظارتان واقعاً اعمال می‌شود.

با پروژه نمونه آشنا شوید

این‌ها فایل‌های کلیدی‌ای هستند که در پروژه نمونه با آن‌ها کار خواهید کرد:

  • server.js حاوی کد Node.js است که محتوای برنامه وب را ارائه می‌دهد. این برنامه از Express برای رسیدگی به درخواست‌ها و پاسخ‌های HTTP استفاده می‌کند. به‌ویژه، express.static() برای ارائه همه فایل‌های محلی در فهرست راهنمای عمومی استفاده می‌شود، بنابراین اسناد serve-static مفید خواهد بود.
  • public/index.html HTML برنامه وب است. مانند اکثر فایل‌های HTML، این فایل نیز هیچ اطلاعات نسخه‌بندی‌ای به‌عنوان بخشی از نشانی وب خود ندارد.
  • public/app.15261a07.js و public/style.391484cf.css دارایی‌های جاوا اسکریپت و CSS برنامه وب هستند. هرکدام از این فایل‌ها حاوی یک درهم‌ساز در نشانی وب خود هستند، که با محتوای آن‌ها مطابقت دارد. index.html مسئول پیگیری این است که کدام نشانی وب نسخه‌دار خاص باید بار شود.

سرصفحه‌های ذخیره‌سازی موقت را برای HTML ما پیکربندی کن

هنگام پاسخ دادن به درخواست‌های نشانی‌های وبی که حاوی اطلاعات نسخه‌بندی نیستند، حتماً Cache-Control: no-cache را به پیام‌های پاسخ خود اضافه کنید. همراه با آن، تنظیم یکی از دو سرایند پاسخ اضافی توصیه می‌شود: یا Last-Modified یا ETag. index.html در این دسته قرار می‌گیرد. می‌توانید این کار را به دو مرحله تقسیم کنید.

ابتدا، سرصفحه‌های Last-Modified و ETag توسط گزینه‌های پیکربندی etag و lastModified کنترل می‌شوند. هر دوی این گزینه‌ها درواقع به‌طور پیش‌فرض روی true برای همه پاسخ‌های HTTP تنظیم شده‌اند، بنابراین در این راه‌اندازی فعلی، برای دریافت این رفتار نیازی به موافقت کردن ندارید. اما درهرصورت می‌توانید در پیکربندی‌تان صریح باشید.

دوم، باید بتوانید در سرصفحه Cache-Control: no-cache اضافه کنید، اما فقط برای اسناد HTML (در این مورد، index.html). آسان‌ترین راه برای تنظیم شرطی این سرصفحه، نوشتن setHeaders function سفارشی و بررسی اینکه آیا درخواست ورودی برای سند HTML است یا نه در آن است.

پیکربندی ارائه ایستا در server.js به این صورت شروع می‌شود:

app.use(express.static('public'));
  • تغییرات شرح‌داده‌شده در بالا را اعمال کنید و درنهایت باید چیزی شبیه به این داشته باشید:
app.use(express.static('public', {
  etag: true, // Just being explicit about the default.
  lastModified: true,  // Just being explicit about the default.
  setHeaders: (res, path) => {
    if (path.endsWith('.html')) {
      // All of the project's HTML files end in .html
      res.setHeader('Cache-Control', 'no-cache');
    }
  },
}));

پیکربندی سرصفحه‌های ذخیره‌سازی موقت برای نشانی‌های وب نسخه‌دار

هنگام پاسخ دادن به درخواست‌های نشانی‌های وبی که حاوی «اثر انگشت» یا اطلاعات نسخه‌بندی هستند و محتوای آن‌ها هرگز قرار نیست تغییر کند، Cache-Control: max-age=31536000 را به پاسخ‌هایتان اضافه کنید. ‫app.15261a07.js و style.391484cf.css در این دسته قرار می‌گیرند.

بااستفاده از setHeaders function که در مرحله آخر استفاده شد، می‌توانید منطق دیگری اضافه کنید تا بررسی شود که آیا درخواست داده‌شده برای نشانی وب نسخه‌دار است یا نه، و اگر بود، سرایند Cache-Control: max-age=31536000 را اضافه کنید.

قوی‌ترین روش برای انجام این کار استفاده از عبارت باقاعده است تا ببینید آیا دارایی درخواست‌شده با الگوی خاصی که می‌دانید درهم‌سازی‌ها در آن قرار می‌گیرند مطابقت دارد یا نه. در این پروژه نمونه، همیشه هشت نویسه از مجموعه ارقام ۰ تا ۹ و حروف کوچک a تا f (یعنی نویسه‌های شانزده‌شانزدهی) است. درهم‌ساز همیشه با نویسه . در هر طرف جدا می‌شود.

عبارت باقاعده‌ای که با این قوانین کلی مطابقت دارد می‌تواند به‌صورت new RegExp('\\.[0-9a-f]{8}\\.') بیان شود.

  • تابع setHeaders را به‌گونه‌ای اصلاح کنید که شبیه این باشد:
app.use(express.static('public', {
  etag: true, // Just being explicit about the default.
  lastModified: true,  // Just being explicit about the default.
  setHeaders: (res, path) => {
    const hashRegExp = new RegExp('\\.[0-9a-f]{8}\\.');

    if (path.endsWith('.html')) {
      // All of the project's HTML files end in .html
      res.setHeader('Cache-Control', 'no-cache');
    } else if (hashRegExp.test(path)) {
      // If the RegExp matched, then we have a versioned URL.
      res.setHeader('Cache-Control', 'max-age=31536000');
    }
  },
}));

تأیید رفتار جدید بااستفاده از DevTools

با اعمال تغییرات در سرور فایل ایستا، می‌توانید با پیش‌دید برنامه زنده درحالی‌که پانل DevTools Network باز است، مطمئن شوید که سرصفحه‌های درست تنظیم شده‌اند.

  • با کلیک راست کردن در سرصفحه ستون، ستون‌هایی را که در پانل «شبکه» نمایش داده می‌شود سفارشی کنید تا مرتبط‌ترین اطلاعات را دربرگیرد:

درحال پیکربندی پانل «شبکه» DevTools.

در اینجا، ستون‌هایی که باید به آن‌ها توجه کنید عبارت‌اند از Name، Status، Cache-Control، ETag، و Last-Modified.

  • درحالی‌که DevTools در پانل «شبکه» باز است، صفحه را بازآوری کنید.

پس‌از بار شدن صفحه، باید ورودی‌هایی را در پانل «شبکه» ببینید که شبیه موارد زیر است:

ستون‌های پانل «شبکه».

ردیف اول مربوط به سند HTML است که به آن پیمایش کرده‌اید. این غذا معمولاً با Cache-Control: no-cache سرو می‌شود. وضعیت پاسخ‌های HTTP برای آن درخواست 304 است. این یعنی مرورگر می‌دانست که نباید فوراً از HTML ذخیره‌شده در حافظه نهان استفاده کند، بلکه درعوض یک درخواست HTTP به سرور وب ارسال کرد و بااستفاده از اطلاعات Last-Modified و ETag بررسی کرد که آیا به‌روزرسانی‌ای برای HTML موجود در حافظه نهانش وجود دارد یا نه. پاسخ HTTP 304 نشان می‌دهد که HTML به‌روزرسانی‌شده‌ای وجود ندارد.

دو ردیف بعدی برای دارایی‌های CSS و JavaScript نسخه‌دار است. باید ببینید که با Cache-Control: max-age=31536000 ارائه می‌شوند و وضعیت HTTP برای هرکدام 200 است. به‌دلیل پیکربندی استفاده‌شده، هیچ درخواست واقعی به سرور Node.js ارسال نمی‌شود و کلیک کردن روی ورودی جزئیات بیشتری را به شما نشان می‌دهد، ازجمله اینکه پاسخ «(از حافظه نهان دیسک)» آمده است.

وضعیت پاسخ شبکه ۲۰۰.

مقادیر واقعی برای ستون‌های ETag و Last-Modified اهمیت چندانی ندارند. نکته مهم این است که مطمئن شوید این کوکی‌ها تنظیم می‌شوند.

درحال جمع‌بندی

پس‌از طی کردن مراحل این codelab، اکنون با نحوه پیکربندی سرصفحه‌های پاسخ HTTP در سرور وب مبتنی بر Node.js بااستفاده از Express برای استفاده بهینه از حافظه پنهان HTTP آشنا شده‌اید. همچنین مراحلی را که باید برای تأیید استفاده از رفتار ذخیره‌سازی موردانتظار ازطریق پانل «شبکه» در DevTools در Chrome دنبال کنید، دراختیار دارید.