الحفاظ على التجديد من خلال ميزة إعادة التحقق

أداة إضافية لمساعدتك في تحقيق التوازن بين سرعة عرض تطبيق الويب وحداثته

يساعد stale-while-revalidate المطوّرين في تحقيق التوازن بين السرعة، أي تحميل المحتوى المخزّن مؤقتًا على الفور، وحداثة المحتوى، أي ضمان استخدام التعديلات على المحتوى المخزّن مؤقتًا في المستقبل. إذا كانت لديك خدمة ويب أو مكتبة تابعة لجهة خارجية يتم تعديلها بجدول زمني منتظم، أو إذا كانت مواد عرض الطرف الأول تميل إلى أن تكون قصيرة المدة، قد يكون stale-while-revalidate إضافة مفيدة إلى سياسات التخزين المؤقت الحالية.

يمكنك ضبط stale-while-revalidate إلى جانب max-age في عنوان الاستجابة Cache-Control في Chrome 75 وFirefox 68.

ستتجاهل المتصفّحات التي لا تتيح استخدام stale-while-revalidate قيمة الإعداد هذه بصمت، وستستخدم max-age، كما سأوضّح قريبًا…

ما المقصود بذلك؟

لنقسّم stale-while-revalidate إلى جزءَين: فكرة أنّ الردّ المُخزَّن مؤقتًا قد يكون قديمًا وعملية إعادة التحقّق.

أولاً، كيف يعرف المتصفّح ما إذا كانت الاستجابة المخزّنة مؤقتًا "قديمة"؟ إنّ عنوان الاستجابة Cache-Control الذي يتضمّن stale-while-revalidate يجب أن يحتوي أيضًا على max-age، ويحدّد عدد الثواني التي يتم تحديدها من خلال max-age مدى القِدم. يُعتبر أيّ استجابة مخبأة أحدث من max-age حديثة، ويُعتبَر أنّ الاستجابات المخبأة الأقدم قديمة.

إذا كانت الاستجابة المخزّنة مؤقتًا على الجهاز لا تزال جديدة، يمكن استخدامها كما هي ل تلبية طلب المتصفّح. من وجهة نظر stale-while-revalidate، ليس هناك أي إجراء يمكن اتّخاذه في هذا السيناريو.

ولكن إذا كانت الاستجابة المخزّنة مؤقتًا قديمة، يتم إجراء عملية تحقّق أخرى تستند إلى العمر: هل عمر الاستجابة المخزّنة مؤقتًا ضمن الفترة الزمنية الإضافية التي يوفّرها الإعداد stale-while-revalidate؟

إذا كان عمر الردّ القديم يقع ضمن هذه الفترة، سيتم استخدامه للقيام بمعالجة طلب المتصفّح. وفي الوقت نفسه، سيتم إرسال طلب "إعادة التحقّق" إلى الشبكة بطريقة لا تؤخّر استخدام الردّ المُخزَّن مؤقتًا . قد تحتوي الاستجابة المعروضة على نفس المعلومات الموجودة في الرد المخزن مؤقتًا سابقًا، أو قد تكون مختلفة. وفي كلتا الحالتَين، يتم تخزين ردّ الشبكة محليًا، ما يؤدي إلى استبدال أي بيانات كانت محفوظة في ذاكرة التخزين المؤقت في السابق، وإلى إعادة ضبط الموقّت "للحداثة" المستخدَم أثناء أي عمليات مقارنة مستقبلية max-age.

أمّا إذا كانت الاستجابة القديمة المخزّنة مؤقتًا قديمة بما يكفي لتكون خارج الفترة الزمنية المحدّدة لـ stale-while-revalidate، فلن يتم تنفيذ طلب المتصفّح. سيسترجع المتصفّح بدلاً من ذلك ردًا من الشبكة، وسيستخدمه لإكمال الطلب الأوّلي وتعبئة ذاكرة التخزين المؤقت المحلية بردّ جديد.

مثال على بث مباشر

في ما يلي مثال بسيط على واجهة برمجة تطبيقات HTTP لعرض الوقت الحالي، أو بشكل أدق، عدد الدقائق الحالية التي مضت من الساعة.

في هذا السيناريو، يستخدم خادم الويب رأس Cache-Control هذا في استجابة HTTP:

Cache-Control: max-age=1, stale-while-revalidate=59

يعني هذا الإعداد أنّه في حال تكرار طلب بشأن الوقت خلال الثانية التالية، ستظل القيمة المخزَّنة مؤقتًا سابقًا حديثة، وستُستخدم كما هي، بدون أي إعادة تحقُّق.

في حال تكرار الطلب بعد مدة تتراوح بين ثانية واحدة و60 ثانية، ستكون القيمة المخزّنة مؤقتًا قديمة، ولكن سيتم استخدامها لاستيفاء طلب واجهة برمجة التطبيقات. وفي الوقت نفسه، "في الخلفية"، سيتم تقديم طلب إعادة التحقّق من أجل تعبئة ذاكرة التخزين المؤقت بقيمة جديدة لاستخدامها في المستقبل.

في حال تكرار طلب بعد أكثر من 60 ثانية، لن يتم استخدام الردّ القديم على الإطلاق، وسيعتمد تنفيذ طلب المتصفّح وإعادة التحقّق من ذاكرة التخزين المؤقت على الحصول على استجابة من الشبكة.

فيما يلي تقسيم لتلك الحالات الثلاث المختلفة، مع الفترة الزمنية التي يتم فيها تطبيق كل منها على مثالنا:

مخطّط بياني يوضّح المعلومات الواردة في القسم السابق

ما هي حالات الاستخدام الشائعة؟

بالرغم من أنّ المثال أعلاه تم إنشاؤه لخدمة واجهة برمجة التطبيقات "دقائق بعد مرور الساعة"، إلا أنّه يوضّح حالة الاستخدام المتوقّعة، وهي الخدمات التي توفّر معلومات تحتاج إلى إعادة تحميل ولكن يُسمح ببعض التعقيد.

ومن الأمثلة الأقل ابتكارًا واجهة برمجة تطبيقات لأحوال الطقس الحالية أو لأهم عناوين الأخبار التي تمت كتابتها خلال الساعة الماضية.

بشكل عام، أيّ ردّ يتم تعديله على فترات زمنية معروفة، ومن المرجّح أن يتم طلبه عدّة مرات، ويكون ثابتًا خلال تلك الفترة الزمنية، هو مرشح جيد للتخزين المؤقت على المدى القصير من خلال max-age. يؤدي استخدام stale-while-revalidate بالإضافة إلى max-age إلى زيادة احتمالية تلبية الطلبات المستقبلية من الذاكرة المؤقتة التي تتضمّن محتوى أحدث، بدون حظر استجابة الشبكة.

كيف يتفاعل مع خدمات العمل؟

إذا سمعت عن stale-while-revalidate، من المرجّح أنّه كان في سياق الوصفات المستخدَمة ضمن عامل الخدمة.

يتشارك استخدام علامة stale-while-revalidate من خلال عنوان Cache-Control بعضًا من التشابهات مع استخدامه في الخدمة العاملة، وتنطبق العديد من الملاحظات نفسها حول مفاضلات الحداثة والحد الأقصى لمُدد الصلاحية. ومع ذلك، هناك بعض الاعتبارات التي يجب مراعاتها عند تحديد ما إذا كنت تريد تنفيذ نهج يستند إلى مهام الخدمة، أو الاعتماد فقط على إعدادات العنوان Cache-Control.

استخدِم أسلوب عاملي الخدمات في الحالات التالية:

  • إذا كنت تستخدم حاليًا مشغّل خدمات في تطبيق الويب
  • إذا كنت بحاجة إلى التحكّم بشكل دقيق في محتوى ذاكرات التخزين المؤقت، وأردت تنفيذ سياسة مثل سياسة انتهاء الصلاحية الأقل استخدامًا مؤخرًا يمكن أن تساعدك وحدة انتهاء صلاحية ذاكرة التخزين المؤقت في Workbox في حلّ هذه المشكلة.
  • تريد أن يتم إعلامك عندما يتغيّر ردّ قديم في الخلفية أثناء خطوة إعادة التحقّق. يمكن أن تساعدك وحدة تعديل ذاكرة التخزين المؤقت للبث في Workbox في حلّ هذه المشكلة.
  • يجب أن يكون هذا السلوك stale-while-revalidate متاحًا في جميع المتصفحات الحديثة.

يمكنك استخدام أسلوب التحكم في ذاكرة التخزين المؤقت في الحالات التالية:

  • إذا كنت لا تريد التعامل مع النفقات العامة لعملية نشر عامل الخدمة لخدمة تطبيق الويب الخاص بك وصيانتها
  • لا مشكلة في السماح للإدارة التلقائية لذاكرة التخزين المؤقت في المتصفّح بمنع زيادة حجم ذاكرات التخزين المؤقت على الجهاز بشكل كبير جدًا.
  • لا بأس باستخدام نهج غير متاح حاليًا في جميع المتصفّحات الحديثة (اعتبارًا من تموز/يوليو 2019، وقد يصبح متاحًا في المستقبل).

إذا كنت تستخدم عامل خدمة وفعّلت أيضًا stale-while-revalidate لبعض الاستجابات من خلال عنوان Cache-Control، سيحصل عامل الخدمة، بشكل عام، على "المحاولة الأولى" للاستجابة لطلب معيّن. إذا قرر عامل تشغيل الخدمة عدم الاستجابة، أو إذا قدَّم طلب شبكة باستخدام fetch() أثناء عملية إنشاء استجابة، سيتم تنفيذ السلوك الذي تم ضبطه من خلال عنوان Cache-Control.

مزيد من المعلومات

صورة رئيسية من تصميم "صامويل زيلر"