الحُرّاس: التفويض
الحُرّاس: التفويض
يجيب الحارس (guard) عن سؤال واحد: هل يُسمح لهذا الطلب بالمتابعة؟ يُعيد true للسماح بمرور الطلب إلى المعالج، أو false (أو يرمي خطأ) لحجبه. والحُرّاس هم المكان القياسي لمنطق المصادقة والتفويض.
واجهة CanActivate
الحارس صنف قابل للحقن يُنفّذ CanActivate بدالّة canActivate() واحدة. تستقبل ExecutionContext وتُعيد قيمة منطقية (أو وعدًا/Observable بها):
إن أعادت canActivate() القيمة false، يستجيب NestJS تلقائيًا بـ 403 Forbidden ولا يعمل المعالج أبدًا.
سياق التنفيذ ExecutionContext
يصف ExecutionContext الطلب الحالي بطريقة مستقلّة عن النقل. تمنحك switchToHttp() طلب/استجابة HTTP، لكنّ الحارس نفسه قد يعمل لـ WebSockets أو الخدمات المصغّرة عبر switchToWs() / switchToRpc(). كما يكشف الصنف الهدف والمعالج — وهو أساسي لقراءة البيانات الوصفية.
تطبيق الحُرّاس
اربط حارسًا بـ @UseGuards() على مستوى الدالّة أو المتحكّم، أو عامًّا في main.ts:
التفويض القائم على الأدوار بالبيانات الوصفية
يصبح الحُرّاس أقوياء حين يُدمَجون مع بيانات وصفية مخصّصة. تُرفِق الأدوار المطلوبة بمعالج عبر @SetMetadata() (أو مُزخرِف مخصّص)، ثم تقرأها داخل الحارس باستخدام Reflector:
الحُرّاس مقابل الوسيطات
ExecutionContext الكامل — يعرفون أي معالج مستهدَف بالضبط ويقرؤون بياناته الوصفية (كالأدوار المطلوبة). أمّا الوسيط فيعمل مبكرًا جدًا قبل معرفة أيٍّ من ذلك.
الخلاصة
يُنفّذ الحُرّاس CanActivate ويُعيدون true/false للسماح أو الحجب، فيستجيبون 403 عند المنع. يستقبلون ExecutionContext (مستقلًّا عن النقل)، ويُطبَّقون بـ @UseGuards()، ويصيرون واعين للأدوار بقراءة بيانات المسار عبر Reflector. يعمل الحُرّاس بعد الوسيطات وهم المكان الصحيح للتفويض. تاليًا: المعترِضات، التي تُغلّف المعالج نفسه.