حزمة Next.js لإدارة مكتبات الجهات الخارجية

في عام 2021، قدّم فريق Chrome Aurora مكوّن Script لتحسين أداء loading للنصوص البرمجية التابعة لجهات خارجية في Next.js. ومنذ إطلاقه، وسّعنا إمكاناته لتسهيل تحميل الموارد التابعة لجهات خارجية على المطوّرين و أسرع.

تقدّم مشاركة المدونة هذه نظرة عامة على الميزات الجديدة التي طرحناها، وأهمها مكتبة @next/third-parties ، بالإضافة إلى مخطّطنا المستقبلي الذي يتضمن مبادرات جديدة.

تأثير النصوص البرمجية التابعة لجهات خارجية في الأداء

41% من جميع طلبات الجهات الخارجية في مواقع Next.js الإلكترونية هي نصوص برمجية. على عكس أنواع المحتوى الأخرى، يمكن أن يستغرق تنزيل النصوص البرمجية وتنفيذها وقتًا طويلاً، ما قد يؤدي إلى حظر العرض وتأخير تفاعل المستخدم. تُظهر بيانات "تقرير تجربة مستخدم Chrome" (CrUX) أنّ المواقع الإلكترونية التي تستخدم Next.js وتحمل المزيد من الرمز البرمجي التابع لجهات خارجية تحقّق معدّلات اجتياز أقل لكل من مدى استجابة الصفحة لتفاعلات المستخدم (INP) وسرعة عرض أكبر محتوى مرئي (LCP) .

رسم بياني شريطي يوضّح انخفاضًا في النسبة المئوية لنقاط Next.js التي تحقّق نتائج جيدة لكلٍّ من INP وLCP بما يتناسب مع عدد الأطراف الثالثة التي تم تحميلها.
تقرير CrUX لشهر كانون الأول (ديسمبر) 2023 (110,823 موقعًا إلكترونيًا)

لا يشير الارتباط الذي لوحظ في هذا الرسم البياني إلى السببية. ومع ذلك، تقدّم التجارب على الويب محلية دليلاً إضافيًا على أنّ النصوص البرمجية التابعة لجهات خارجية تؤثر بشكل كبير في أداء الصفحة. على سبيل المثال، يقارن الرسم البياني التالي بين مقاييس اختبارية مختلفة عند إضافة حاوية من "إدارة العلامات من Google"، تتألف من 18 علامة تم اختيارها عشوائيًا، إلى تصنيف، وهو تطبيق رائج في Next.js.

رسم بياني شريطي يوضّح الفرق في المقاييس الاختبارية المختلفة عند تحميل موقع إلكتروني باستخدام أداة "إدارة العلامات من Google" أو بدونها
WebPageTest (شبكة 4G الجوّالة - فرجينيا، الولايات المتحدة الأمريكية)

تقدّم مستندات WebPageTest تفاصيل حول كيفية قياس هذه الأوقات. من نظرة سريعة، يتضح من الأمر أن جميع هذه المقاييس المعملية تتأثر بحاوية GTM. على سبيل المثال، شهد Total Blocking Time (TBT)، وهو مقياس بديل مفيد في المختبر يقترب من مقياس INP، زيادةً بمقدار 20 ضعفًا تقريبًا.

مكوّن النص البرمجي

عند طرح العنصر <Script> في Next.js، حرصنا على تقديمه من خلال واجهة برمجة تطبيقات سهلة الاستخدام تشبه إلى حد كبير العنصر<script> التقليدي. وباستخدام هذا البرنامج، يمكن للمطوّرين مشاركة مكان نص برمجي تابع لجهة خارجية في أي مكوّن في تطبيقهم، وسيتولى Next.js ترتيب النص البرمجي بعد تحميل الموارد المهمة.

<!-- By default, script will load after page becomes interactive -->
<Script src="https://example.com/sample.js" />

<!-- Script is injected server-side and fetched before any page hydration occurs -->
<Script strategy=”beforeInteractive” src="https://example.com/sample.js" />

<!-- Script is fetched later during browser idle time -->
<Script strategy=”lazyOnload” src="https://example.com/sample.js" />

يستخدم عشرات الآلاف من تطبيقات Next.js، بما في ذلك المواقع الإلكترونية الرائجة مثل Patreon وTarget و Notion، المكوّن <Script>. على الرغم من فعاليته، أعرب بعض المطوّرين عن مخاوفهم بشأن النقاط التالية:

  • مكان وضع مكوّن <Script> في تطبيق Next.js مع الالتزام بتعليمات التثبيت المختلفة لموفّري الخدمات الخارجيين (تجربة المطوّر)
  • استراتيجية التحميل الأمثل لاستخدامها مع مختلف النصوص البرمجية التابعة لجهات خارجية (تجربة المستخدِم)

لحلّ كلتا المشكلتَين، أطلقنا @next/third-parties، وهي مكتبة مخصّصة تقدّم مجموعة من المكوّنات والأدوات المحسّنة المخصّصة للجهات الخارجية الرائجة.

تجربة المطوّرين: تسهيل إدارة المكتبات التابعة لجهات خارجية

يتم استخدام العديد من النصوص البرمجية التابعة لجهات خارجية في نسبة كبيرة من مواقع Next.js الإلكترونية، وتعدّ "إدارة العلامات من Google" الأكثر رواجًا، إذ تستخدمها ‎66% من المواقع الإلكترونية على التوالي. يستند @next/third-parties إلى المكوّن <Script> من خلال تقديم وحدات تغليف ذات مستوى أعلى مصمّمة لتبسيط استخدام حالات الاستخدام الشائعة هذه.

import { GoogleAnalytics } from "@next/third-parties/google";

export default function RootLayout({ children }) {
  return (
    <html lang="en">
      <body>{children}</body>
      <GoogleTagManager gtmId="GTM-XYZ" />
    </html>
  );
}

تتضمّن "إحصاءات Google"، وهي نص برمجي تابع لجهة خارجية يتم استخدامه على نطاق واسع، (‎52% من مواقع Next.js الإلكترونية)، أيضًا مكوّنًا مخصّصًا خاصًا بها.

import { GoogleAnalytics } from "@next/third-parties/google";

export default function RootLayout({ children }) {
  return (
    <html lang="en">
      <body>{children}</body>
      <GoogleAnalytics gaId="G-XYZ" />
    </html>
  );
}

@next/third-parties تعمل على تبسيط عملية تحميل النصوص البرمجية المستخدَمة بشكل شائع، ولكنها تُتيح لنا أيضًا تطوير أدوات لفئات خارجية أخرى، مثل عمليات التضمين. على سبيل المثال، يتم استخدام عمليات تضمين "خرائط Google" وYouTube في ‎8% و ‎4% من مواقع Next.js الإلكترونية على التوالي، وقد طرحنا أيضًا مكوّنات لتسهيل تحميلها.

import { GoogleMapsEmbed } from "@next/third-parties/google";
import { YouTubeEmbed } from "@next/third-parties/google";

export default function Page() {
  return (
    <>
      <GoogleMapsEmbed
        apiKey="XYZ"
        height={200}
        width="100%"
        mode="place"
        q="Brooklyn+Bridge,New+York,NY"
      />
      <YouTubeEmbed videoid="ogfYd705cRs" height={400} params="controls=0" />
    </>
  );
}

تجربة المستخدم: تسريع تحميل المكتبات التابعة لجهات خارجية

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

لنأخذ عمليات تضمين YouTube كمثال. عندما تكون بعض عمليات التنفيذ البديلة أفضل بكثير من الإعلانات المضمّنة في الوقت الحالي، يستخدم <YouTubeEmbed> المكوّن الذي تصدّره أداة @next/third-parties lite-youtube-embed، والذي يتم تحميله بشكلٍ أسرع بكثير عند عرضه في مقارنة "مرحبًا، العالم" Next.js.

ملف GIF يعرض مقارنة تحميل الصفحة بين مكوِّن تضمين YouTube وإطار iframe عادي في YouTube
WebPageTest (شبكة 4G الجوّالة - فرجينيا، الولايات المتحدة الأمريكية)

وبالمثل، يتم تضمين loading="lazy" في "خرائط Google" كسمة تلقائية للتضمين لضمان أنّه لا يتم تحميل الخريطة إلا عند بُعد مسافة معيّنة عن إطار العرض. قد تبدو هذه السمة واضحة لتضمينها، خاصةً لأنّ مستندات "خرائط Google" تضمّنها في مثال مقتطف الرمز البرمجي، ولكن لا يستخدم سوى % 45 من المواقع الإلكترونية التي تستخدم Next.js والتي تضمّن "خرائط Google" السمة loading="lazy".

تشغيل نصوص برمجية تابعة لجهات خارجية في Web Worker

من بين التقنيات المتقدّمة التي نستكشفها في @next/third-parties، تسهيل تحميل النصوص البرمجية التابعة لجهات خارجية إلى Web Worker. وبفضل استخدامها من مكتبات مثل Partytown، يمكن أن يؤدي ذلك إلى تقليل تأثير النصوص البرمجية التابعة لجهات خارجية على أداء الصفحة إلى حد كبير من خلال نقلها بالكامل خارج سلسلة المحادثات الرئيسية.

تعرض الصورة المتحرّكة التالية بتنسيق GIF الاختلافات في المهام الطويلة ووقت حظر السلسلة الرئيسية عند تطبيق استراتيجيات <Script> مختلفة على حاوية أداة "إدارة العلامات من Google" ضمن موقع Next.js الإلكتروني. يُرجى العِلم أنّ التبديل بين خيارات الاستراتيجية يؤدي فقط إلى تأخير توقيت تنفيذ النصوص البرمجية هذه، ولكنّ إعادة وضعها في Web Worker يؤدي إلى القضاء تمامًا على وقتها في سلسلة المحادثات الرئيسية.

ملف GIF يعرض الاختلافات في وقت حظر سلسلة المهام الرئيسية لاستراتيجيات النصوص البرمجية المختلفة
WebPageTest (Mobile 4G - فيرجينيا الولايات المتحدة الأمريكية)

في هذا المثال تحديدًا، أدّى نقل تنفيذ حاوية "إدارة العلامات من Google" وملفّات برمجية العلامات المرتبط بها إلى عامل ويب إلى خفض وقت الاستجابة للتحميل بنسبة%92.

تجدر الإشارة إلى أنّ هذه الطريقة يمكن أن تؤدي إلى توقّف العديد من النصوص البرمجية التابعة لجهات خارجية بدون إشعار، ما يجعل تصحيح الأخطاء أمرًا صعبًا، في حال عدم إدارتها بعناية. في الأشهر القادمة، سنتحقّق مما إذا كانت أيّ مكوّنات تابعة لجهات خارجية تقدّمها @next/third-parties تعمل بشكل صحيح عند تشغيلها في Web Worker. إذا كان الأمر كذلك، سنعمل على توفير طريقة سهلة واختيارية للمطورين لاستخدام هذا الأسلوب.

الخطوات التالية

أثناء تطوير هذه الحزمة، تبيّن أنّه هناك حاجة إلى تجميع اقتراحات التحميل التابعة لجهات خارجية كي تتمكّن أيضًا أطر العمل الأخرى من الاستفادة من الأساليب الأساسية نفسها المستخدَمة. وقد أدّى ذلك إلى إنشاء Third Party Capital، وهي مكتبة تستخدم تنسيق JSON لوصف تقنيات التحميل التابعة لجهات خارجية، والتي تُعدّ حاليًا الأساس لميزة @next/third-parties.

في إطار خطواتنا التالية، سنواصل التركيز على تحسين المكوّنات المقدّمة لنظام Next.js، بالإضافة إلى توسيع نطاق جهودنا لتشمل أدوات مماثلة في أنظمة أساسية شائعة أخرى ومنصّات إدارة المحتوى. نحن نتعاون حاليًا مع مشرفي Nuxt ونخطّط لطرح أدوات خارجية مشابهة مخصّصة لمنظومتهم المتكاملة في المستقبل القريب.

إذا كانت إحدى الجهات الخارجية التي تستخدمها في تطبيق Next.js متوافقة مع "@next/third-parties"، يمكنك تثبيت الحزمة وتجربتها. يسرّنا معرفة ملاحظاتك بشأن GitHub.