وحدات Terraform: دليلك الشامل لتنظيم البنية التحتية وإعادة استخدامها بكفاءة
في عالم تطوير البنية التحتية كتعليمات برمجية (Infrastructure as Code – IaC)، تبرز Terraform كأداة لا غنى عنها لإدارة الموارد السحابية. ومع ذلك، يميل العديد من المبتدئين إلى تجاوز مفهوم الوحدات (Modules) في Terraform، اعتقاداً منهم بأنها تضيف تعقيداً غير ضروري. لكن سرعان ما يجدون أنفسهم غارقين في مئات الأسطر من التعليمات البرمجية المتكررة وغير المنظمة، مما يعيق الإنتاجية ويزيد من فرص الأخطاء.
إذا كنت قد بدأت رحلتك مع Terraform ولديك بعض المعرفة الأساسية، فإن هذا المقال سيأخذك في جولة معمقة لفهم وحدات Terraform وكيف يمكنها تحويل طريقة إدارتك للبنية التحتية. سنركز على المبادئ الأساسية دون الخوض في تفاصيل مزود خدمة سحابية محدد (مثل AWS أو Google Cloud) لضمان الشمولية والتركيز على المفهوم الجوهري.
أنت تكتب الوحدات البرمجية بالفعل دون أن تدري!
قد تفاجأ عندما تعلم أنك، كمستخدم لـ Terraform، تقوم بالفعل بكتابة الوحدات البرمجية حتى لو لم تقم بإنشائها بشكل صريح. فكل ملف تهيئة لـ Terraform (يحمل الامتداد .tf) موجود في دليل معين، حتى لو كان ملفاً واحداً فقط، يُعتبر وحدة برمجية. هذه الوحدة الأساسية التي تعمل عليها تُعرف باسم “الوحدة الجذرية” (Root Module).
ماذا تقدم وحدات Terraform من قيمة؟
تُمكنك وحدة Terraform من بناء طبقة تجريدية منطقية فوق مجموعة من الموارد. بعبارة أخرى، تسمح لك الوحدات بتجميع الموارد ذات الصلة معًا وإعادة استخدام هذه المجموعة لاحقًا، ربما عدة مرات، مما يقلل من التكرار ويزيد من الاتساق.
لنتخيل أن لدينا خادماً افتراضياً (Virtual Server) بميزات محددة مستضافاً في السحابة. ما هي مجموعة الموارد التي قد تصف هذا الخادم؟ إليك بعض الأمثلة:
- الجهاز الافتراضي (
Virtual Machine) نفسه، والذي يتم إنشاؤه من صورة معينة. - جهاز تخزين كُتلي (
Block Device) مرفق بحجم محدد للتخزين الإضافي. - عنوان
IPعام ثابت (Static Public IP) مربوط بواجهة الشبكة الافتراضية للخادم. - مجموعة من قواعد جدار الحماية (
Firewall Rules) ليتم إرفاقها بالخادم. - عناصر أخرى مثل جهاز تخزين كُتلي إضافي، واجهة شبكة إضافية، وما إلى ذلك.

الآن، لنفترض أنك بحاجة إلى إنشاء هذا الخادم بمجموعته الكاملة من الموارد عدة مرات. هنا تكمن القوة الحقيقية للوحدات: أنت بالتأكيد لا تريد تكرار نفس التعليمات البرمجية للتهيئة مراراً وتكراراً. الوحدات تحل هذه المشكلة بفعالية.
عندما “تستدعي وحدة” (Call a module)، فهذا يعني أنك تستخدمها ضمن ملف التهيئة الخاص بك. يوضح المثال التالي كيف يمكن استدعاء وحدة “الخادم” (server) الخاصة بنا لإنشاء خمسة نُسخ من الخادم باستخدام مجموعة واحدة من التهيئة المعرفة داخل الوحدة:
module "server" {
count = 5
source = "./module_server"
some_variable = some_value
}
هيكلة الوحدات: الوحدات الفرعية (Child) والجذرية (Root)
من الطبيعي أن ترغب في إنشاء أكثر من وحدة برمجية واحدة لتمثيل مكونات مختلفة من بنيتك التحتية. إليك بعض الأمثلة الشائعة للمكونات التي يمكن تجريدها إلى وحدات:
- الشبكات: مثل شبكة سحابية خاصة افتراضية (
Virtual Private Cloud - VPC). - استضافة المحتوى الثابت: مثل حاويات التخزين (
Buckets) في خدمات التخزين السحابي. - موازنات التحميل (
Load Balancers): والموارد المرتبطة بها. - تهيئة التسجيل (
Logging Configuration): أو أي مكون منطقي آخر تعتبره جزءاً مميزاً من البنية التحتية.
لنفترض أن لدينا وحدتين مختلفتين: وحدة “الخادم” (server) ووحدة “الشبكة” (network). في وحدة “الشبكة”، نقوم بتعريف وتهيئة شبكتنا الافتراضية، ثم نضع الخوادم بداخلها. يمكن أن يبدو استدعاء هذه الوحدات في الوحدة الجذرية (Root Module) كما يلي:
module "server" {
source = "./module_server"
some_variable = some_value
}
module "network" {
source = "./module_network"
some_other_variable = some_other_value
}
بمجرد أن نقوم بإنشاء وحداتنا المخصصة، يمكننا الإشارة إليها على أنها “وحدات فرعية” (Child Modules). وملف التهيئة الذي نستدعي فيه هذه الوحدات الفرعية يُعرف بالوحدة الجذرية (Root Module) أو الوحدة الأم.

يمكن استيراد الوحدة الفرعية من عدة مصادر:
- المسارات المحلية: مسار نسبي أو مطلق داخل نظام الملفات.
- سجل
Terraformالرسمي (Terraform Registry): إذا كنت على دراية بسجلات أخرى مثل سجلDocker Registry، فستفهم الفكرة. - مستودع
Git: سواء كان مستودعاً مخصصاً أو على منصات مثلGitHubأوBitBucket. - عنوان
URLلملف.zip: يحتوي على الوحدة عبر بروتوكولHTTP.
ولكن السؤال الأهم هو: كيف يمكننا تمرير تفاصيل الموارد بين الوحدات؟ في مثالنا، يجب إنشاء الخوادم داخل شبكة معينة. فكيف يمكننا إخبار وحدة “الخادم” بإنشاء الأجهزة الافتراضية في الشبكة التي تم إنشاؤها بواسطة وحدة “الشبكة”؟ هنا يأتي دور التغليف (Encapsulation).
تغليف الوحدات (Module Encapsulation): حجر الزاوية في التصميم المعياري
يُعد التغليف في Terraform مبدأً أساسياً لضمان تنظيم التعليمات البرمجية وقابليتها للصيانة. يتكون التغليف من مفهومين رئيسيين:
- نطاق الوحدة (
Module Scope). - التعرض الصريح للموارد (
Explicit Resource Exposure).
نطاق الوحدة (Module Scope)
تكون جميع نُسخ الموارد وأسمائها، وبالتالي رؤية الموارد، معزولة ضمن نطاق الوحدة الخاصة بها. على سبيل المثال، لا تستطيع الوحدة “A” رؤية الموارد الموجودة في الوحدة “B” أو معرفة تفاصيلها بشكل افتراضي. تضمن هذه الرؤية المحدودة للموارد، والتي تُعرف أحياناً بعزل الموارد (Resource Isolation)، أن تكون للموارد أسماء فريدة ضمن مساحة اسم الوحدة.
على سبيل المثال، عند إنشاء 5 نُسخ من وحدة “الخادم” (server) الخاصة بنا، ستكون عناوين الموارد داخل كل نسخة فريدة:
module.server[0].resource_type.resource_name
module.server[1].resource_type.resource_name
module.server[2].resource_type.resource_name
...
من ناحية أخرى، يمكننا إنشاء نُسختين من نفس الوحدة بأسماء مختلفة، مما يوفر مرونة أكبر في التسمية والتهيئة:
module "server-alpha" {
source = "./module_server"
some_variable = some_value
}
module "server-beta" {
source = "./module_server"
some_variable = some_value
}
في هذه الحالة، سيكون عنوان الموارد أو تسميتها على النحو التالي:
module.server-alpha.resource_type.resource_name
module.server-beta.resource_type.resource_name
التعرض الصريح للموارد (Explicit Resource Exposure)
إذا كنت ترغب في الوصول إلى تفاصيل معينة لموارد موجودة في وحدة أخرى، فستحتاج إلى تهيئة ذلك بشكل صريح. فبشكل افتراضي، لا تعرف وحدة “الخادم” (server) الخاصة بنا شيئاً عن الشبكة التي تم إنشاؤها في وحدة “الشبكة” (network).

لحل هذه المشكلة، يجب علينا الإعلان عن قيمة إخراج (output value) في وحدة “الشبكة” لتصدير موردها، أو سمة من سمات المورد، إلى الوحدات الأخرى. وفي المقابل، يجب على وحدة “الخادم” الإعلان عن متغير (variable) ليتم استخدامه لاحقاً كمدخل.

على الرغم من أن أسماء output و variable يمكن أن تختلف، إلا أنه يُنصح باستخدام نفس الأسماء لزيادة الوضوح وقابلية القراءة. هذا الإعلان الصريح للإخراج هو الطريقة التي يتم بها كشف مورد معين (أو معلومات عنه) خارج نطاق الوحدة، أي إلى نطاق الوحدة الجذرية (Root Module)، وبالتالي جعله متاحاً للوحدات الأخرى.
بعد ذلك، عند استدعاء الوحدة الفرعية “الخادم” (server) في الوحدة الجذرية، يجب علينا تعيين قيمة الإخراج من وحدة “الشبكة” (network) إلى المتغير الخاص بوحدة “الخادم”. يمكن تحقيق ذلك بالشكل التالي:
network_id = module.network.network_id
إليك كيف سيبدو الكود النهائي لاستدعاء وحداتنا الفرعية بعد تطبيق هذا المفهوم:
module "server" {
count = 5
source = "./module_server"
some_variable = some_value
network_id = module.network.network_id
}
module "network" {
source = "./module_network"
some_other_variable = some_other_value
}
ستقوم تهيئة المثال هذه بإنشاء 5 نُسخ من نفس الخادم، مع جميع الموارد الضرورية، ضمن الشبكة التي أنشأناها كوحدة منفصلة. هذا يوضح قوة الوحدات في بناء بنية تحتية معقدة بطريقة منظمة وقابلة للتوسع.
خاتمة: رحلتك مع وحدات Terraform تبدأ هنا
الآن، وبعد أن استعرضنا أساسيات وحدات Terraform وكيفية عملها، يجب أن تكون لديك رؤية واضحة حول أهميتها وقدرتها على تبسيط إدارة البنية التحتية. إن تبني هيكل التعليمات البرمجية المعياري (Modular Code Structure) يجعل تهيئتك أكثر مرونة، وأسهل في الفهم والصيانة، خاصة عند العمل ضمن فريق.
إذا كنت في بداية رحلتك مع Terraform، إليك بعض الخطوات التالية المقترحة لتعميق فهمك:
- دليل
HashiCorpالتعليمي: ننصحك بالاطلاع على هذا الدليل التعليمي الموجز منHashiCorp، الشركة المطورة لـTerraform، حول تنظيم التهيئة باستخدام الوحدات: “Organize Configuration”. - دليل دراسة شهادة
Terraform Associate: للحصول على فهم شامل يغطي المفاهيم من المبتدئ إلى المتقدم، يمكنك الاستفادة من دليل الدراسة المميز لشهادةTerraform Associate Certification.
إن استخدام الوحدات ليس مجرد ممارسة جيدة، بل هو ضرورة لتحقيق الكفاءة والاستدامة في مشاريع DevOps الحديثة. استثمر وقتك في إتقانها، وسترى فرقاً كبيراً في جودة وسهولة إدارة بنيتك التحتية.
الخلاصة التقنية
تُعد وحدات Terraform حجر الزاوية في بناء بنية تحتية سحابية قابلة للتوسع، الصيانة، وإعادة الاستخدام. من خلال توفير طبقة تجريدية للموارد، تمكن الوحدات الفرق من تجنب تكرار التعليمات البرمجية، وتوحيد أفضل الممارسات، وتبسيط عمليات النشر المعقدة. إن فهم آليات التغليف، بما في ذلك نطاق الوحدة والتعرض الصريح للموارد عبر المتغيرات والمخرجات، ضروري لتصميم حلول IaC قوية وفعالة. إن دمج الوحدات في استراتيجية Terraform الخاصة بك ليس مجرد تحسين، بل هو تحول جوهري نحو إدارة بنية تحتية أكثر نضجاً وكفاءة.