الفرق بين المراجعتين ل"Design Patterns/proxy"

من موسوعة حسوب
اذهب إلى التنقل اذهب إلى البحث
(2.0 محتوى)
(2.1 محتوى)
سطر 12: سطر 12:
 
الصورة. يتخفى الوكيل في هيئة قاعدة بيانات، ويمكنه التعامل مع البدء الكسول وحفظ النتائج دون ملاحظة العميل أو قاعدة البيانات الحقيقية.
 
الصورة. يتخفى الوكيل في هيئة قاعدة بيانات، ويمكنه التعامل مع البدء الكسول وحفظ النتائج دون ملاحظة العميل أو قاعدة البيانات الحقيقية.
  
لكن ما الفائدة؟ إن كنت تحتاج إلى تنفيذ إجراء قبل أو بعد المنطق الأساسي للفئة ()
+
لكن ما الفائدة؟ إن كنت تحتاج إلى تنفيذ إجراء قبل أو بعد المنطق الأساسي للفئة (Primary Logic) فإن الوكيل يسمح لك بهذا دون تغيير تلك الفئة، وبما أنه -أي الوكيل- يستخدم نفس الواجهة كالفئة الأصلية، فيمكن تمريره إلى أي عميل يتوقع كائن خدمة حقيقي.
 +
 
 +
== مثال واقعي ==
 +
الصورة. يمكن استخدام بطاقات الائتمان للدفع مثل النقود الورقية تمامًا.
 +
 
 +
تمثل بطاقات الائتمان وكيلًا للحساب البنكي الذي يكون وكيلًا لكمية مالية، وكلاهما يستخدم نفس الواجهة، أنهما يُستخدمان للدفع مقابل المشتريات. وذلك يسعد العميل لا شك لأنه ليس عليه حمل أمواله كلما حل وارتحل، كما يسعد البائع أيضًا لأنه يقيه مخاطر السرقة أثناء نقل المال إلى البنك، أو مخاطر فقد المال داخل المتجر.
 +
 
 +
== البنية ==
 +
# تصرح فئة Service Interface عن واجهة للخدمة، ويجب أن يتبع الوكيل هذه الواجهة ليتمكن من التخفي في صورة كائن خدمة.
 +
# فئة الخدمة هي فئة تعطي بعض المنطق التجاري المفيد.
 +
# فئة Proxy لها حقل مرجعي يشير إلى كائن الخدمة، وبعد أن ينهي الوكيل عمليات معالجته (البدء الكسول والتسجيل والتحكم في الوصول والحفظ، إلخ) فإنه يمرر الطلب إلى كائن الخدمة، وعادة يدير الوكلاء دورة الحياة كاملة لكائنات الخدمة الخاصة بها.
 +
# يجب أن تعمل فئة Client مع كل من الخدمات والوكلاء من خلال نفس الواجهة، وهكذا يمكنك تمرير وكيل إلى أي شيفرة تتوقع كائن خدمة.
 +
 
 +
== مثال توضيحي ==

مراجعة 23:27، 18 أبريل 2019

نمط الوكيل (Proxy) هو نمط تصميم إنشائي يسمح لك بتوفير بديل لكائن موجود لديك، ويتحكم في الوصول إلى الكائن الأصلي، مما يمكنك من تنفيذ إجراءات قبل أو بعد وصول الطلب إلى الكائن الأصلي.

المشكلة

إليك مثالًا يوضح الحالة التي قد ترغب فيها بتقييد الوصول إلى إلى كائن ما، لنفرض أن لديك كائنًا كبيرًا جدًا يستهلك موارد النظام بشراهة، وأنت لا تريده أصلًا بشكل مستمر، بل من وقت لآخر.

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

الحل

يقترح نمط الوكيل أن تنشئ فئة وكيل جديدة بنفس الواجهة التي يستخدمها كائن الخدمة (Service Object)، ثم تحدِّث تطبيقك ليمرِّر كائن الوكيل إلى كل عملاء الكائن الأصلي، وعند استلام طلب من عميل ينشئ الوكيلُ كائنَ خدمةٍ حقيقي ويفوض كل المهام إليه.

الصورة. يتخفى الوكيل في هيئة قاعدة بيانات، ويمكنه التعامل مع البدء الكسول وحفظ النتائج دون ملاحظة العميل أو قاعدة البيانات الحقيقية.

لكن ما الفائدة؟ إن كنت تحتاج إلى تنفيذ إجراء قبل أو بعد المنطق الأساسي للفئة (Primary Logic) فإن الوكيل يسمح لك بهذا دون تغيير تلك الفئة، وبما أنه -أي الوكيل- يستخدم نفس الواجهة كالفئة الأصلية، فيمكن تمريره إلى أي عميل يتوقع كائن خدمة حقيقي.

مثال واقعي

الصورة. يمكن استخدام بطاقات الائتمان للدفع مثل النقود الورقية تمامًا.

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

البنية

  1. تصرح فئة Service Interface عن واجهة للخدمة، ويجب أن يتبع الوكيل هذه الواجهة ليتمكن من التخفي في صورة كائن خدمة.
  2. فئة الخدمة هي فئة تعطي بعض المنطق التجاري المفيد.
  3. فئة Proxy لها حقل مرجعي يشير إلى كائن الخدمة، وبعد أن ينهي الوكيل عمليات معالجته (البدء الكسول والتسجيل والتحكم في الوصول والحفظ، إلخ) فإنه يمرر الطلب إلى كائن الخدمة، وعادة يدير الوكلاء دورة الحياة كاملة لكائنات الخدمة الخاصة بها.
  4. يجب أن تعمل فئة Client مع كل من الخدمات والوكلاء من خلال نفس الواجهة، وهكذا يمكنك تمرير وكيل إلى أي شيفرة تتوقع كائن خدمة.

مثال توضيحي