Menu
العربية

الوضع الصارم في JavaScript: ما الذي يفعله 'use strict'؟

تعرّف على ما يغيّره الوضع الصارم في JavaScript، وكيف تفعّله، ولماذا يعمل تلقائياً داخل الوحدات (modules) والـ classes في الكود الحديث.

الوضع الصارم: نسخة أكثر انضباطاً من جافا سكريبت

تمتلك جافا سكريبت تاريخاً طويلاً، وتحمل معها الكثير من القرارات المشكوك فيها — إسنادات تُنشئ متغيرات عامة بصمت، وكلمة this التي يتغيّر معناها حسب طريقة استدعاء الدالة، وأسماء معاملات مكرّرة كانت تعمل بكل بساطة... وكفى. كسر أيٍّ من هذه السلوكيات يعني كسر الويب بأكمله، لذلك اختارت TC39 (اللجنة المسؤولة عن صيانة اللغة) طريقاً مختلفاً: وضعٌ اختياري يتم فيه تشذيب هذه الحواف الحادة.

هذا الوضع الاختياري يُعرف بـ الوضع الصارم (strict mode). يمكنك تفعيله بسطر واحد في بداية الملف أو الدالة:

index.js
Output
Click Run to see the output here.

جرّب تشغيل الكود وستظهر لك رسالة ReferenceError: x is not defined. أما بدون هذا التوجيه، فنفس الكود سيُنشئ متغيّرًا عامًّا اسمه x دون أي مشكلة ويطبع 10. نفس اللغة، لكن بمجموعتين مختلفتين من القواعد.

توجيه 'use strict'

التوجيه ليس سوى سلسلة نصية حرفية — 'use strict'; أو "use strict";. ويجب أن يكون أول تعبير في السكربت أو الدالة. فإذا سبقه أي شيء، ولو مجرد تعبير عابر، فسيتعامل معه المحرّك كسلسلة نصية عادية ويتجاهله.

index.js
Output
Click Run to see the output here.

يمكنك تفعيل الوضع الصارم داخل دالة واحدة فقط بوضع التوجيه في بدايتها، لكن عملياً لم يعد أحد يفعل ذلك — فإما أن تكتب وحدات (modules) تعمل بالوضع الصارم افتراضياً، أو تُفعّله على مستوى الملف بأكمله.

ماذا يُغيّر الوضع الصارم فعلياً؟

الوضع الصارم في جافا سكريبت ليس قاعدة واحدة، بل حزمة من القواعد. وأبرزها:

  • إسناد قيمة لمتغيّر غير مُعرَّف يُطلق خطأً بدلاً من إنشاء متغيّر عام.
  • قيمة this داخل استدعاء دالة عادية تكون undefined، لا الكائن العام.
  • تكرار أسماء المعاملات (function f(a, a) {}) يُعدّ خطأً نحوياً.
  • الإسناد إلى خصائص للقراءة فقط يُطلق خطأً بدلاً من الفشل الصامت.
  • حذف متغيّر عادي أو دالة يُطلق خطأً.
  • بعض الكلمات المحجوزة للمستقبل (implements, interface, package, private, protected, public, static, yield) لا يمكن استخدامها كأسماء متغيّرات.

جولة سريعة على مثال:

index.js
Output
Click Run to see the output here.

كل حالة من هذه الحالات تعني شيئاً واحداً: "المحرّك اكتشف خطأً محتملاً في وقت مبكّر". هذه هي القيمة الحقيقية للوضع الصارم، باختصار.

مشكلة المتغيّر العام الصامت

هذا هو السبب الأهم لوجود الوضع الصارم من الأساس. فبدونه، أي خطأ إملائي بسيط يتحوّل تلقائياً إلى متغيّر عام (global variable):

// الوضع غير الصارم (لا تفعل هذا)
function setup() {
    usernmae = 'Ada';   // خطأ إملائي — ينشئ window.usernmae
}

setup();
console.log(username);  // undefined — لم يتم تعيين المتغيّر الحقيقي أبدًا

البرنامج يشتغل عادي. ما في أي خطأ. البق يظهر لاحقًا، لما شيء كان المفروض يقرأ username يلاقي undefined بدل ذلك. أما في الوضع الصارم، نفس هذا الخطأ المطبعي يرمي استثناءً فور التشغيل، وتصلحه في ثوانٍ بدل ساعات.

جافا سكريبت الحديثة تعمل بالوضع الصارم تلقائيًا

هنا النقطة اللي تربك كثير من الناس: معظم كود جافا سكريبت اللي تكتبه اليوم يعمل فعلًا في الوضع الصارم، دون ما تكتب 'use strict' في أي مكان.

هناك مصدران رئيسيان للصرامة التلقائية:

  • وحدات ES (ES modules). أي ملف .mjs، وأي <script type="module">، وأي شيء يتم استيراده عبر import/export يعمل في الوضع الصارم. ولا حاجة لأي توجيه.
  • أجسام الأصناف (class bodies). كل تعليمة داخل class { ... } تُنفَّذ بصرامة، حتى لو كان الملف المحيط بها غير صارم.
index.js
Output
Click Run to see the output here.

إذًا متى تحتاج فعلًا أن تكتب 'use strict'; بنفسك؟ فقط في السكربتات الكلاسيكية — أي ملفات JS القديمة التي تُحمَّل عبر وسم <script> عادي، أو ملفات Node.js القديمة التي تعتمد على require دون استخدام أدوات تجميع الوحدات. أما أي كود جديد، فالوحدات (modules) تكفّيك هذه المهمة تلقائيًا.

كيف يغيّر الوضع الصارم قيمة this داخل الدوال العادية

هذا سلوك يستحق التنبيه لأنه يوقع المبتدئين في فخ. في الوضع غير الصارم، عندما تستدعي دالة عادية دون أن يسبقها كائن، فإن this يرتبط بالكائن العام (window في المتصفح، وglobal في Node). أما في الوضع الصارم فيصبح this مساويًا لـ undefined:

index.js
Output
Click Run to see the output here.

هذا في الغالب هو السلوك الذي تريده. فعندما تكون قيمة this هي undefined، يظهر الخطأ فوراً إذا نسيت ربط الدالة (binding). أما إذا كانت تشير بصمت إلى الكائن العام (global object)، فسيختبئ الخطأ إلى أن ينكسر شيء آخر لاحقاً في سلسلة التنفيذ.

ما الذي لا يفعله الوضع الصارم

الوضع الصارم في جافا سكريبت هو تشديد على مستوى زمن التصريف (compile-time) وزمن التشغيل (runtime)، لكنه لا يمنحك نظام أنواع، ولا يلتقط أخطاء الوصول إلى null، ولا ينبّهك على المتغيرات غير المستخدمة. هذه مهام تتكفل بها أدوات مثل TypeScript وESLint ومحرر الكود لديك. فكّر في strict mode على أنه يعالج مجموعة محددة من الفخاخ اللغوية في جافا سكريبت، لا أنه شبكة أمان شاملة.

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

خلاصة ما يجب أن تأخذه معك

  • كتابة 'use strict'; في أعلى الملف أو داخل دالة يُفعّل نسخة أكثر صرامة من جافا سكريبت.
  • الأخطاء الإملائية لن تُنشئ متغيرات عامة بعد الآن، وthis لن يتحول ضمنياً إلى الكائن العام، وعدد من الفخاخ الأخرى ستتحول إلى أخطاء صريحة.
  • وحدات ES (ES modules) وأجسام class تعمل في الوضع الصارم تلقائياً — لذا نادراً ما تحتاج إلى كتابة التوجيه يدوياً.
  • الهدف هو اكتشاف الأخطاء مبكراً، لا إضافة ميزات جديدة إلى اللغة.

التالي: التعليقات

تعرّفت حتى الآن على التوجيهات (directives) والفواصل المنقوطة والقواعد التي يهتم بها محرك جافا سكريبت. في الدرس القادم سنتحدث عن الملاحظات التي تتركها أنت لمن يقرأ الكود لاحقاً: كيف تعمل التعليقات في جافا سكريبت، ومتى يستحق الأمر فعلاً أن تكتبها.

الأسئلة الشائعة

ما هو الوضع الصارم (strict mode) في JavaScript؟

الوضع الصارم هو نسخة اختيارية من JavaScript تحوّل مجموعة من الأخطاء الصامتة إلى أخطاء حقيقية تظهر لك بوضوح. تقوم بتفعيله بكتابة النص 'use strict'; في أول الملف أو أول الدالة. هذا الوضع يشدّد قواعد اللغة: إسناد قيمة إلى متغير غير معرّف يرمي خطأً، وتكرار أسماء المعاملات (parameters) غير مسموح، وقيمة this داخل استدعاء دالة عادية تصبح undefined بدلاً من الكائن العمومي.

كيف أفعّل الوضع الصارم في JavaScript؟

ضع 'use strict'; كأول جملة فعلية في السكربت أو في الدالة. لا يجوز أن يسبقه أي شيء — ولا حتى سطر فارغ غير مسبوق بتعليق — وإلا اعتبره المحرّك مجرد نص عادي. في المشاريع الحديثة نادراً ما تحتاج لكتابته يدوياً، لأن وحدات ES (ملفات .mjs أو <script type="module">) وجسم أي class يعمل في الوضع الصارم تلقائياً.

لماذا نستخدم الوضع الصارم في JavaScript؟

لأنه يمسك الأخطاء مبكراً. خطأ طباعي بسيط مثل usernmae = 'Ada' يُنشئ متغيراً عمومياً بصمت في الوضع العادي، بينما يرمي ReferenceError في الوضع الصارم. كما أنه يحجز الكلمات المفتاحية المستقبلية، ويمنع تكرار أسماء الخصائص في المحركات القديمة، ويجعل سلوك this متوقعاً — وكل هذا يسهّل قراءة الكود وفهمه.

هل أحتاج لكتابة 'use strict' في JavaScript الحديثة؟

غالباً لا. وحدات ES وأجسام الـ class تعمل في الوضع الصارم افتراضياً، ومعظم المشاريع الحديثة تعتمد على أحدهما. لن تحتاج لكتابة 'use strict'; صراحةً إلا في السكربتات الكلاسيكية القديمة — أي تلك التي تُحمَّل عبر وسم <script> عادي بدون type="module".

تعلّم البرمجة مع Coddy

ابدأ الآن