أنماط التصميم في TypeScript: المستوى المتقدم مع أمثلة
\n\nتطوير التطبيقات المعقدة باستخدام TypeScript لا يتطلب فقط معرفة بناء الجملة، بل أيضًا القدرة على بناء بنية مرنة وقابلة للتوسع. تظل أنماط التصميم GoF (Gang of Four) المعيار الذهبي، لكن على المستوى المتقدم يصبح تطبيقها أكثر دقة. في هذه المقالة، سنحلل أربعة أنماط قوية — Bridge، Visitor، State و Strategy — مع أمثلة حقيقية بلغة TypeScript. ستتعلم كيفية استخدام التصنيف الصارم (strict typing)، الأدوية (generics) والواجهات (interfaces) لتنفيذ هذه الأنماط.
\n\n1. Bridge: فصل التجريد عن التنفيذ
\n\nنمط Bridge (الجسر) يفصل التجريد (abstraction) عن تنفيذه (implementation)، مما يسمح بتغييرهما بشكل مستقل. هذا مفيد بشكل خاص عندما يكون لديك عدة متغيرات من الوظائف يمكن دمجها.
\n\nمثال: نظام عرض الأشكال في واجهات برمجة تطبيقات رسومية مختلفة (Canvas و SVG).
\n\n// التنفيذ (Implementation)\ninterface Renderer {\n renderCircle(radius: number): void;\n renderSquare(side: number): void;\n}\n\nclass CanvasRenderer implements Renderer {\n renderCircle(radius: number): void {\n console.log(`Canvas: نرسم دائرة نصف قطرها ${radius}`);\n }\n renderSquare(side: number): void {\n console.log(`Canvas: نرسم مربعًا طول ضلعه ${side}`);\n }\n}\n\nclass SVGRenderer implements Renderer {\n renderCircle(radius: number): void {\n console.log(`SVG: <circle r="${radius}" />`);\n }\n renderSquare(side: number): void {\n console.log(`SVG: <rect width="${side}" height="${side}" />`);\n }\n}\n\n// التجريد (Abstraction)\nabstract class Shape {\n protected renderer: Renderer;\n\n constructor(renderer: Renderer) {\n this.renderer = renderer;\n }\n\n abstract draw(): void;\n}\n\nclass Circle extends Shape {\n private radius: number;\n\n constructor(renderer: Renderer, radius: number) {\n super(renderer);\n this.radius = radius;\n }\n\n draw(): void {\n this.renderer.renderCircle(this.radius);\n }\n}\n\nclass Square extends Shape {\n private side: number;\n\n constructor(renderer: Renderer, side: number) {\n super(renderer);\n this.side = side;\n }\n\n draw(): void {\n this.renderer.renderSquare(this.side);\n }\n}\n\n// الاستخدام\nconst canvasCircle = new Circle(new CanvasRenderer(), 10);\ncanvasCircle.draw(); // Canvas: نرسم دائرة نصف قطرها 10\n\nconst svgSquare = new Square(new SVGRenderer(), 5);\nsvgSquare.draw(); // SVG: <rect width="5" height="5" />\n\nالميزة الرئيسية: يضمن TypeScript أن جميع عمليات التنفيذ تتبع العقد Renderer. إضافة نوع جديد من الأشكال أو عارض جديد لا يكسر الكود الموجود.
2. Visitor: اجتياز الهياكل المعقدة دون تغيير الفئات
\n\nنمط Visitor (الزائر) يسمح بإضافة عمليات جديدة إلى الكائنات دون تغيير فئاتها. هذا حل مثالي للعمل مع الأشجار، AST (الأشجار النحوية المجردة) أو التسلسلات الهرمية للمكونات.
\n\nمثال: نظام تصدير عُقد المستند إلى تنسيقات مختلفة (JSON، XML).
\n\n// العناصر (Elements)\ninterface DocumentNode {\n accept(visitor: Visitor): void;\n}\n\nclass TextNode implements DocumentNode {\n constructor(public content: string) {}\n\n accept(visitor: Visitor): void {\n visitor.visitTextNode(this);\n }\n}\n\nclass ImageNode implements DocumentNode {\n constructor(public src: string, public alt: string) {}\n\n accept(visitor: Visitor): void {\n visitor.visitImageNode(this);\n }\n}\n\n// الزائر (Visitor)\ninterface Visitor {\n visitTextNode(node: TextNode): void;\n visitImageNode(node: ImageNode): void;\n}\n\nclass JSONExporter implements Visitor {\n private p