يشاهد المطورون تطبيقاتهم التي أُطلقت للتو وهي تتعثر في اللحظة التي ينقر فيها بضعة آلاف من المستخدمين على زر "الانطلاق"، ونادراً ما يكون هذا البطء بسبب خطأ في الكود – بل هو صراع بين وحدة المعالجة المركزية (CPU) وذاكرة الوصول العشوائي (RAM) في الخادم على المساحة المتاحة. يظهر عنق الزجاجة هذا في صورة فترات تحميل أطول للصفحات، أو انتهاء مهلة الطلب (time-outs)، أو حتى الانهيار التام، مما يضر بتجربة المستخدم، والإيرادات، وثقة العلامة التجارية.

لماذا يمكن لخادم يعمل بشكل جيد في المختبر أن يتوقف تماماً عند التشغيل الفعلي

خلال مرحلة التطوير، يرسل مطور واحد عدداً قليلاً من الطلبات، لذا تظل موارد الخادم خاملة معظم الوقت. ولكن عندما يصبح التطبيق متاحاً للجمهور، يولد كل زائر طلباً يحتاج إلى عنصرين أساسيين:

  • وحدة المعالجة المركزية (CPU) – المعالج الذي يقوم بتشغيل كل حلقة (loop) ودالة (function) وعملية حسابية. فكر فيها كطاهٍ لا يمكنه تحضير سوى عدد محدود من الأطباق في وقت واحد. طلب واحد يُقدم فوراً؛ أما مائة طلب فتعني أن الطاهي سيظل يعمل بنفس السرعة، لكن الزبائن سينتظرون لفترة أطول.
  • ذاكرة الوصول العشوائي (RAM) – تخزين مؤقت للبيانات التي تحتاجها وحدة المعالجة المركزية أثناء معالجة الطلب. إنها تشبه المكتب الذي يضع عليه الطاهي مكونات كل طبق. إذا امتلأ المكتب، يجب على الطاهي التوقف عن استقبال طلبات جديدة حتى يتم إخلاء مساحة.

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

إغراء "مجرد شراء جهاز أكبر"

رد الفعل الأول الشائع هو ترقية الجهاز – وهي ممارسة تسمى التوسع الرأسي (vertical scaling). إن إضافة المزيد من نوى وحدة المعالجة المركزية أو المزيد من ذاكرة الوصول العشوائي يحسن السعة بالفعل: فمن الانتقال من 4 نوى إلى 16، أو من 8 جيجابايت إلى 64 جيجابايت، يمكن استيعاب تدفق أكبر من حركة المرور دون تغيير أي كود.

ومع ذلك، يصطدم التوسع الرأسي بسقف محدد:

  • الحدود المادية (Physical limits) – لا يمكن لأي لوحة أم استضافة سوى عدد معين من النوى وكمية محدودة من الذاكرة.
  • تناقص العوائد (Diminishing returns) – تكلفة كل نواة أو جيجابايت إضافي تزيد عن سابقتها، بينما تقل مكاسب الأداء.
  • نقطة الفشل الواحدة (Single point of failure) – إذا تعطل الخادم الضخم، ستختفي الخدمة بأكملها.

وبسبب هذه القيود، ابتعدت الشركات الكبرى في هذا المجال – مثل منصات البث، ومحركات البحث، ومواقع التجارة الإلكترونية – عن فكرة الاعتماد على جهاز واحد عملاق.

البديل: توزيع الحمل على العديد من الأجهزة الأصغر حجماً

بدلاً من بناء برج أكثر طولاً، يقوم المشغلون بإضافة المزيد من الخوادم ذات الحجم المتوسط ويتركونها تتشارك في حركة المرور. هذا النهج، المعروف بـ التوسع الأفقي (horizontal scaling)، يحافظ على كل جهاز ضمن نطاق أداء مريح ويتجنب منحنى التكلفة المتزايد للتحديثات الرأسية.

يتطلب تنسيق العديد من الأجهزة وجود موزع أحمال (load balancer) – وهو برنامج أو جهاز يستقبل كل طلب وارد ويوجهه إلى الخادم الذي لديه أكبر قدر من السعة المتاحة. يخفي الموزع التعقيد عن العميل؛ فمن منظور المستخدم، لا يزال الموقع يبدو كنقطة اتصال واحدة.

كما يوفر التوسع الأفقي المرونة أيضاً. فإذا تعطل أحد العقد (nodes)، يقوم الموزع ببساطة بتوجيه حركة المرور إلى العقد السليمة المتبقية، مما يحافظ على استمرارية الخدمة.

أمور يجب مراعاتها عند البدء في إضافة الأجهزة

  • التصميم عديم الحالة (Stateless design) – يجب ألا تعتمد الطلبات على البيانات المخزنة في ذاكرة خادم معين فقط؛ وإلا فقد يتم توجيه المستخدم إلى عقدة تفتقر إلى السياق المطلوب. ويحل استخدام التخزين المؤقت المشترك (shared caches) أو قواعد البيانات هذه المشكلة.
  • فحوصات الحالة (Health checks) – يجب أن يكون الموزع قادراً على اكتشاف الخادم المتعثر بسرعة والتوقف عن إرسال حركة المرور إليه.
  • سياسات التوسع التلقائي (Auto-scaling policies) – تتيح لك العديد من المنصات السحابية تحديد عتبات (مثل استخدام وحدة المعالجة المركزية، أو زمن استجابة الطلب) تقوم تلقائياً بتشغيل أو إيقاف المثيلات (instances)، مما يحافظ على توافق التكاليف مع الطلب.

وجهة نظر مغايرة: التوسع الرأسي لم يمت

بالنسبة للفرق الصغيرة أو التطبيقات ذات حركة المرور المنخفضة، يمكن أن يكون الخادم الواحد القوي هو الحل الأبسط والأرخص. إذا كانت طفرة حركة المرور متوقعة (مثل إطلاق منتج مجدول)، فقد تكون الترقية الرأسية المؤقتة أكثر عملية من توفير أسطول كامل من المثيلات الجديدة.

المفتاح هو إدراك متى تتوقف حيلة "الجهاز الأكبر" عن تقديم قيمة متناسبة، والبدء في التخطيط للتوزيع.

الخلاصة

عادة ما يكون تباطؤ الخادم بعد الإطلاق ناتجاً عن مشكلة تنافس على الموارد، وليس عيباً في الكود. فدورات وحدة المعالجة المركزية (CPU) ومنافذ ذاكرة الوصول العشوائي (RAM) محدودة، وعندما تصل طلبات كثيرة في آن واحد، فإنها تتراكم في طوابير، مما يؤدي إلى إطالة أوقات الاستجابة. يمنحك التوسع الرأسي (Vertical scaling) هامش قدرة إضافي بسيط، لكنه سرعان ما يصطدم بالحدود المادية والاقتصادية. أما التوسع الأفقي (Horizontal scaling) — المتمثل في إضافة المزيد من الخوادم المتواضعة خلف موازن أحمال (load balancer) — فيوفر مساراً أرخص وأكثر مرونة مع نمو حركة المرور. وفي اللحظة التي تلاحظ فيها زيادة طول الطوابير، يحين الوقت لتقييم ما إذا كانت بضع نوى (cores) إضافية ستكفي، أم أنه يجب عليك البدء في توزيع الحمل عبر العديد من الأجهزة.

المصدر: مقال dev.to بعنوان "Why Servers Slow Down – CPU, RAM and the hidden cost of every request."