البحث في الموقع
المحتوى عن 'جو'.
-
لعلّك سمعت في السنوات القليلة الماضية عن لغة برمجة جديدة نشأت من داخل شركة Google تحمل اسم Go (أو Golang كمصطلح قابل للبحث على محركات البحث)، سنحاول من خلال هذه السلسلة التعرّف على هذه اللغة، مزاياها، عيوبها وما يجعلها مختلفة عن غيرها. سيكون الدرس الأول من هذه السلسلة درسًا كلاميا فقط، يركز على نقاط اختلاف اللغة مع باقي اللغات، وهو موجه لمن له خلفية برمجية نوعا ما مع باقي اللغات، لكن ستكون باقي الدروس موجهة للمبتدئين. كعادة كل عقد من الزمن، فإنه تظهر هناك أدوات وتقنيات جديدة تحاول الاستفادة من أخطاء أسلافها من الأدوات والتقنيات، هذا يشمل لغات البرمجة أيضا، لذلك دعك من قول "لماذا لغة برمجة جديدة؟" و "ما الحاجة للغة برمجة جديدة؟" أو "لماذا لا يتفقون على لغة برمجة واحدة؟"، فما لغة البرمجة إلا أداة تقضي بها مهامك، وكل منها يكون أصلح لنوع مهام ما. فاختر لكل مهمة أنسب أداة، ولا داعي لتقديس الأداة وإنشاء الحروب الكلامية -غير التقنية- حولها أو خلق هاجس وهمي يحول عن تعلمها. أَحَسَّ فريقٌ من المبرمجين (العريقين) من داخل Google أنه حان الوقت لتحسين سير عملهم بلغة C و ++C، وأنهم يحتاجون إلى أداة جديدة تلغي عيوب هاتين الأخيرين وتحسن من إنتاجيتهم أكثر، وتكون ملائمة لنوعية احتياجات Google الحسابية. أسسوا لغة البرمجة Go داخل Google عام 2007. الفريق العريق المؤسس لهذه اللغة يشمل مؤسس نظام Unix نفسه Ken Thompson (عَلَمٌ في عِلم الحاسوب، يُعرف اختصارًا بـ Ken) الذي عمل لدى Bell Labs، كذلك Robert Pike الذي كان أيضا من ضمن فريق Unix لدى Bell Labs وأحد مؤسسي ترميز UTF-8 وأخيرًا Robert Griesemer أحد العاملين على محرك جافاسكريب V8. Ken على يسار الصورة بجانب Dennis Ritchie مؤسس لغة C بمعرفة هذه النبذة التاريخية البسيطة عن Go، أحب أن أقتل فيك كل حماس مُفرط، فلا أحب منك أن تعشق لغة برمجة بسبب مؤسيسها، أو أنها خرجت من شركة تحبها، لذلك سأبدأ بسرد أشياء قد لا تحبها حول لغة البرمجة Go، حتى إذا قرأتها ولم تعجبك، فقد يجدر بك التوقف عن القراءة حينها. سأكون سعيدا شخصيا بمتابعة عدد قليل جدا من القراء لهذه السلسلة يدركون حقا ما يفعلون، عوض زخم يتحمس لكل جديد دون وعي وإلمام بالأمور. أشياء قد لن تحبها حول لغة البرمجة Go1. ليست كائنية التوجههذا إن كنت تظن أنها كذلك، فلا يوجد مفهوم الصنف (Class) ولا الكائنات (Objects) وبالتالي لا يوجد وراثة (inheritance). مع ذلك فإن Go تحمل بضعا من مزايا البرمجة الكائنية كتوفيرها لـ Interface و دوال البنيات (Struct methods) وتركيب البنيات (Struct composition). لماذا؟ مؤسسي اللغة يرون أن اللغات كائنية التوجه تحمل العديد من العيوب والتعقيدات التي يمكن إلغاؤها بالتخلي عن بعض هذه المفاهيم كلية. حتى مبرمجي Java أنفسهم ينصحون بـ Composition مثلا في كثير من الأحيان عوض inheritance، مؤسسي اللغة ممن يرون أن البرمجة كائنية التوجه غالبا ما تكون فكرة سيئة -تقنيا-. 2. لا توجد معالجة للاستثناءات Exception Handlingقد تكون هذه نتيجة طبيعية بسبب غياب مفهوم البرمجة الكائنية لدى Go، فمعالجة الأخطاء في Go تتم بطريقة واضحة وتقليدية نوعا ما، حيث أن الأخطاء تُرجع كقيم عادية من نوع error. حيث error هو نوع بدائي في حد ذاته مثله مثل أي نوع أصلي آخر (int, string .. الخ). مع ذلك تسمح لك Go بقذف خطأ للحالات الاستثنائية عبر الكلمة المفتاحية panic (أشبه بـ raise أو throw في باقي اللغات) وكذا التعافي من هذه الأخطاء عن طريق recover. 3. لا توجد معامِلات افتراضية أو اختيارية يمكن تمريرها للدوال (default/optional arguments)ربما قد اعتدت في لغات البرمجة الأخرى على القيام بشيء مثل: function listFolders(path, subfolders=false, recursive=false){ ... } لكن في Go لن يمكنك تمرير subfolder=false ولا recursive=false كإمضاء للدالة listFolders لأنها لن تقبل مثل هذه المعاملات الافتراضية/الاختيارية، وسينتج عن ذلك خطأ عند التجميع (compile error). لماذا؟ يرى مؤسسوا اللغة أن هذه السلوكيات تساهم في بناء واجهات برمجية (API) غير ثابتة أو تساهم في جعل تصرفها غير مُتوقع. في مثالنا السابق مثلا، هم يفضلون كتابة الدالة من دون معاملات افتراضية، أي: func listFolders(path string, subfolders bool, recursive bool) { ... }يجبرك هذا على كتابة التصرف الذي تريده من الدالة بشكل صريح عوض ترك الواجهة البرمجية تملي عليك التصرف الافتراضي، هذا لتقليل الأخطاء البشرية. أيضا قد يدفعك هذا إلى كتابة ثلاث دوال، كل بتصرفها الخاص الواضح من اسمها، مثال: listFolders, listFoldersRecursivly و listFoldersWithFirstLevelSubFolders. 4. لا توجد ميزة إثقال الدوال (Method Overloading)لنفس الأسباب السابقة، فإنه لا يوجد Method overloading، أي لا يمكنك إعادة تعريف دالة تحمل نفس الاسم لكن بإمضاء مغاير. مثلا، إذا وُجدت دالة باسم: func listFolders(path string) { ... }فلا يمكنك إنشاء دالة أخرى بنفس الاسم لكن بإمضاء مغاير مثل: func listFolder(path string, level int) { ... }بل عليك تغيير اسمها إلى مثلا: dunc listFolderToLevel(path string, level int) { ... }على الرغم من ذلك فهناك طريقة غير مباشرة لجعل دالة ما تقبل قيما اعتباطية عبر جعل الإمضاء من نوع {}interface سنتطرق إليها في الدروس القادمة. 5. لا وجود للعموميات (generics)تمكّنك باقي اللغات من كتابة دوال أو أصناف عامة، حيث لا تصرّح عند كتابتها بنوع المعاملات التي تقبلها لكن تترك لها مهمة معرفة نوع المعاملات لاحقا عند استدعائها، لعل أقرب مثال هو ما توفره لغة Java مثلا في صنف <List<T حيث T يرمز إلى أي نوع يتم تحديده لاحقا، بالتالي يمكن إنشاء <List<String أو <List<Integer بكل سهولة مع الحفاظ على نفس الوظائف والعمليات التي يمكن إجراؤها على القائمة List بشكل عام. لا يوجد في Go مثل هذا، وعوضا عن ذلك فهناك {}interface كنوع شامل يرضي جميع الأنواع، لكنه ليس كبديل تام لـ Generics. لماذا؟ سبب عدم توفر العموميات (Generics) في Go هو أن مؤسسيها لم يتبيّنوا بعد الطريقة الأنسب لهم لإضافة هذه الميزة إلى اللغة دون زيادة حِمل أثناء وقت التشغيل (run-time). 6. Go لُغة مملة كما أنها ليست أفضل لغة برمجة!لشدة بساطة اللغة وعدم إتيانها بشيء جديد، فإن الكثيرين يعتبرها لغة مملة. فعدد الكلمات المفتاحية بها والأنواع الأصلية فيها ضئيل مقارنة بباقي اللغات، كما أنها تقلل كثيرا من وجود أكثر من طريقة للقيام بمهمة معينة. حتى أنها لا تحتوي على حلقة while وتقتصر فقط على حلقة for، الكثيرون يعتبرون هذا من مزايا اللغة، لكني ذكرتها لك حتى لا تتوقع شيئا جديدا يصلح للتباهي. أيضا لن تسمح لك اللغة بترك متغير دون استعمال أو استيراد شيء غير مستعمل (unused import/variable) ولن يقبل المُجمع (compiler) أبدا بذلك. 7. لغة عنيدةمؤسسوا اللغة متشبثون برأيهم وقراراتهم في تصميم اللغة، فلا تتوقع تغيرات جوهرية قد تحدث على المدى القريب أو المتوسط في اللغة أو تغيرات في طريقة القيام بالأمور وسلوك المُجمّع (compiler). ولا داعي لفتح نقاشات فارغة حول تصميم اللغة وعيوبها إلا إذا كنت في نفس مستوى خبرتهم وحكمتهم. هم نفسهم يصرحون بهذا، ويذكرون أن هناك خيارات ولغات برمجة أخرى إن لم تعجبك Go. 8. لا يوجد إجماع على مدير حزم واحدتملك بايثون pip، وجافاسكريب تملك npm، وغيرهم من اللغات تملك مدير حزم (package manager) شهير أو متفق عليه، لا تخلو Go من مدير حزم، فهي تملك الكثير من ذلك، لكنها لم تتفق بعد على مدير حزم واحد ولا عن كيفية جلب وسرد الاعتماديات بطريقة قياسية، لكن حديثا يتم العمل على ذلك عبر مفهوم Vendoring. هذه الأمور الثمانية، للذكر وليس للحصر من أشد الانتقادات التي توجّه إلى Go كلغة برمجة، فإن كنت توافقها فقد لا تناسبك اللغة، وإن كنت ترى أن من ورائها حكمة -مثلي- فأكمل قراءة المقال حول أمور قد تعجبك حول Go. أشياء قد تحبها حول لغة البرمجة Go1. خيوط المعالجة المتوازية الخفيفة (goroutines)تسمح لك Go بعمل معالجة متوازية والاستفادة من كامل قوة المعالج (CPU) لديك بكل بساطة، حيث تملك ما يسمى بـ goroutine وهو خيط معالجة متوازي أخف من thread في باقي اللغات. يسمح لك هذا بإطلاق عشرات الآلاف من خيوط المعالجة المتوازية (عوض مثلا عشرات أو مئات threads فقط) دون عناء إنشائها وجعلها تتواصل فيما بينها أو تُكمّل بعضها البعض. يكفي مثلا لعمل دالة تعمل في خيط معالجة لوحدها بسبقها بالكلمة المفتاحية go، مثلا: go func(){ // دالة نكرة تقوم بعمل أمور في خيط معالجة لوحدها .... }هذا يسمح بكتابة تطبيقات عالية الأداء بشكل أسهل بكثير. 2. لغة تجميعية سريعة (compiled)عكس Ruby, Python, Java و PHP فإن Go لغة تجميعية، حيث أن الناتج النهائي لبرنامجك سيكون عبارة عن ملف تنفيذي قائم بذاته يحوي جميع الاعتماديات اللازمة لتشغيله دون الحاجة لاعتماديات خارجية، هذا مفيد جدا في تطوير الويب مثلا للتخلص أو تقليص مشاكل الاعتمادية (dependency hell). أيضا تساهم هذه الميزة في تسهيل عملية نشر التطبيق الخاص بك (deployment) حيث سيكون عليك فقط نقل الملف التنفيذي إلى الخادوم مثلا ثم تشغيله وكفى. لا حاجة لتنصيب أي شيء آخر لتشغيل برمجيتك، لا حاجة حتى لتنصيب Go على الخادوم نفسه. قد يتبادر إلى الذهن أن عملية التجميع (compiling) قد تأخذ وقتا خاصة إذا كان حجم البرنامج كبيرا، لكن الحقيقة أن عملية تجميع Go سريعة جدا وفي كثير من الأحيان لن تلاحظها حتى. 3. لغة إنتاجيةبسبب أنها لغة مملة، فإنها تضيق عليك مجال المجادلة مع زميلك في العمل أو من يعمل معك على المشروع أو البحث عن أفضل طريقة -مذهلة- للقيام بشيء ما، فكل شيء واضح وبسيط. 4. متعددة المنصات بامتيازنفس البرنامج يمكن إعادة تجميعه ليعمل على ويندوز، لينكس، Mac OSx أو حتى الهواتف الذكية ومعمارية ARM. حتى أنه بعد الإصدارة رقم 1.5 من Go يمكن إنشاء ملف تنفيذي لجميع المنصات من خلال المنصة التي أنت فيها، مثلا يمكن من خلال نظام لينكس إنشاء ملف تنفيذي لنظام ويندوز و Mac OS دون الحاجة ﻷن تكون على ذلك النظام. 5. مكتبة قياسية قوية (Rich Standard Library)على الرغم من حداثة اللغة، فإن مكتبتها القياسية حققت تقدما في ظرف قياسي. وغالبا ما يُنصح بالاعتماد على المكتبة القياسية قدر الإمكان، حيث تحتوي على أمور كثيرة تحتاجها أغلب أنواع التطبيقات، حتى أنها تحتوي على محرك قوالب html، أدوات للتعامل مع ترميز json، تشفير كلمات المرور وغيرها من الأمور الصالحة للاستعمال في تطبيقات الويب على سبيل المثال. 6. كل شيء Unicode افتراضاموضوع ترميز السلاسل النصية وكيفية التعامل مع الحرف رقميا كبير، لكن Go جعلت كل شيء unicode بشكل افتراضي إلا إذا تم تعيين غير ذلك صراحة. تملك Go نوع rune عوض نوع char في باقي اللغات، وهو ببساطة اختصار (alias) لنوع int32 فقط يشير إلى نقطة ترميز Unicode لذلك الحرف. بالتي فإن string في Go عبارة عن سلسلة rune وليس عن سلسلة char يشير إلى byte كما في C مثلا. 7. أدوات مساعدة جيدة مضمنة يمكن توليد توثيق برمجيتك بمجرد كتابة أمر godoc أو تحسين التنسيق بكتابة gofmt أو بدء إجراءات فحص الشفرة البرمجية (Unit testing مثلا) عبر كتابة go test وكلها أدوات تأتي مع تنصيب Go. 8. لغة سهلة من حيث الكتابة والتنسيق (Syntax)تنسيق اللغة شبيه نوعا ما بلغة بايثون، حيث لا وجود للفاصلة المنقوطة بعد نهاية كل تعليمة (;)، كما يمكن عمل متغير جديد دون تحديد نوعه، على الرغم من أن اللغة شديدة النوعية strongly styped إلا أنها توحي أنها سَلِسَة وديناميكية، مثلا يمكن كتابة age := 35 وسيتم اسناد نوع int إلى المتغير age. كما أنه يمكن للدوال إرجاع أكثر من قيمة كما في بايثون مثلا. لعل أكثر شيء مغاير لباقي اللغات هو طريقة كتابة الدوال، حيث أن القيمة التي تُرجعها الدالة تُكتب على يمين الدالة (كما في Pascal) وليس على يسارها، مثلا: func HelloHsoub() string { return "Hello Hsoub Academy!" }لاحظ أنه تم كتابة string على يمين الدالة وليس يسارها، أي أن هذه الدالة تُرجع قيمة من نوع string. يمكن للدوال إرجاع دوال أخرى أيضا كقيمة كما يمكن للمتغيرات أن تشير إلى دوال (كما في جافاسكريبت وبايثون...) مثلا: sayHi := HelloHsoub حتى لا أنحاز، فهذه 8 أشياء قد تحبها سأتوقف عندها مقابل 8 قد لا تعجبك كنت قد ذكرتها. بهذا نكون وصلنا إلى ختام الدرس الأول -الكلامي- من هذه السلسلة، والتي رأيت أن أبدأها هكذا عمدا ولو أن بعضا مما قيل في هذا الدرس قد لا يكون بالضرورة موجها للمبرمج المبتدئ، لكني سأحاول جعل الدروس القادمة أبسط ما يكون وتُعنى بالمبتدئ أولا.
- 5 تعليقات
-
- golang
- concurrency
-
(و 3 أكثر)
موسوم في:
-
بعد تعرُّفنا في الدرس السابق على لغة Go ونقاط اختلافها مع باقي لغات البرمجة، سنحاول في هذا الدرس شرح كيفية تنصيبها، تهيئة وفهم بيئة العمل (Workspace) الخاصة بها. من المهم جدا فهم تقسيم المجلدات الذي تمليه عليك بيئة عمل Go، حيث سيمكّنك ذلك من ترتيب مشروعك بشكل أفضل، تسهيل مشاركته، وجعله قابلا للجلب والتضمين في مشاريع أخرى عبر أمر go get الذي سنتعرّف عليه لاحقا. تملك Go نوعين من المُجمّعات (Compilers). وكتذكير سريع، وظيفة المُجمّع هي أخذ شيفرتك البرمجية في شكلها النصّي البحت، وتحويلها إلى برنامج تنفيذي (أو مكتبة). أحد مجمّعَيْ Go هو المجمع القياسي الذي يحمل اسم gc اختصارًا لـ Go Compiler، والآخر مُجمّع يعتمد على مجمّع gcc وما يوفره كمنصة ودعم معماريات معالجات (CPU) أكثر ويحمل اسم gccgo. يجدر الإشارة إلى أن مجمع gccgo متأخر نوعا ما في زرع كامل مواصفات النسخة الأحدث من Go، فعلى سبيل المثال، ولدى كتابة هذا الدرس، يوفر gccgo نسخة 1.4.1 من Go في حين يوفر gc دائما آخر نسخة (1.5.2) من اللغة. ذكرت هذا من باب العلم بالشيء، وباختصار، إن لم يهمك دعم معماريات أكثر أو بعض تفاصيل منصة gcc فلن تحتاج إلى gccgo وستكتفي بـ gc القياسي وهو ما سنتبعه خلال هذه السلسلة. تنصيب Goكما ذكرنا في الدرس السابق، فإن Go لغة متعددة المنصّات بامتياز، وهي جاهزة للتحميل والتنصيب على نظامك المفضل لكلا معماريتي 32bit و 64bit. تنصيب Go على Windows و Mac OSيكفي التوجه إلى موقع اللغة ثم تحميل النسخة الخاصة بنظامك. عملية تنصيبها عادية وهي مشابهة لعملية تنصيب أي برنامج عادي آخر. بعد التنصيب، تأكد من أن العملية تمت بنجاح عبر كتابة go version أو فقط go في سطر الأوامر. إن كنت على Windows تأكد من غلق أي نافذة سطر أوامر مفتوحة مسبقا (إن وُجدت) ثم فتح نافذة جديدة. تنصيب Go على Linuxأنصحك بالاطلاع على مدير حزم توزيعتك قبل تحميل وتنصيب Go من أي مكان آخر. فإن وجدت أن مدير حزم توزيعتك يوفر آخر نسخة من Go فسيكون الأمر أسهل بكثير، إن وجدت أن توزيعتك توفر نسخة أقدم من Go 1.5.1 فعليك تنصيب آخر نسخة منها إن كنت تريد متابعة هذه السلسلة. إن كنت على Ubuntu والتوزيعات المبنية عليها، فأغلب الظن أن نسخة Go التي يوفرها مدير الحزم apt قديمة، كون التوزيعة يتم تحديثها كل 6 أشهر أو عامين (في حال كانت LTS). لذلك أنصحك بالتنصيب من خلال إضافة مستودع etherneum. sudo add-apt-repository -y ppa:ethereum/ethereum sudo apt-get update sudo apt-get install golangيُفترض بباقي التوزيعات أن تحتوي على آخر نسخة من Go، يكفي حينئذ التنصيب من مدير الحزم، مثلا على Arch Linux: sudo pacman -S goبعد التنصيب، تأكد من أن عملية التنصيب تمت بنجاح عبر كتابة go version أو فقط go في سطر الأوامر. من المفروض تتلقى نتيجة مشابهة لهذه: go version go1.5.2 linux/amd64فهم بيئة العملنقصد ببيئة العمل هنا أمران أساسيان: مجلد على حاسوبك، تقوم بإنشائه في أي مكان تريد، سيكون مكانا لجميع مشاريع Go.متغير بيئة (environment variable) يحمل اسم GOPATH يشير إلى هذ المجلد.لنفرض أنك سمّيت مجلد العمل باسم work، فإن هذا الأخير بدوره يجدر به أن يحوي ثلاث مجلدات فرعية أخرى: مجلد فرعي باسم src، حيث ستضع فيه جميع الشيفرات البرمجية لكامل مشاريع Go خاصتك.مجلد فرعي باسم bin، حيث سيقوم مجمع gc بنقل الملفات التنفيذية الناتجة عن شيفراتك البرمجية مباشرة إلى هذا المجلد.مجلد فرعي باسم pkg، مثل bin لكن ليس للملفات التنفيذية، إن كتبت برنامجا عبارة عن مكتبة وليس برنامجا تنفيذيا في حد ذاته، أو جلبت مكتبة خارجية عبر أمر go get، فسيتم تجميعها كمكتبة يتم وضعها في هذا المجلد حتى يسهل جلبها في باقي البرامج دون إعادة تجميعها في كل مرة (هذا يُسرّع من عملية تجميع برنامجك التنفيذي الذي يستخدم هذه المكتبات).باعتبار ما سبق، فإن بيئة Go ستكون مشابهة لهذا التقسيم الشجري: work # مجلد العمل ├── bin # مجلد الملفات التنفيذية الناتجة ├── pkg # مجلد المكتبات البرمجية الناتجة └── src # مجلد شيفراتنا البرمجية هل هذا كل شيء؟ طبعا لا. بما أن Go لغة حديثة نسبيا، فإنها تفترض أنك ستستضيف شيفرتك البرمجية في مكان (مستودع) ما، وهذه عادة أي مبرمج محترف، خشية على الشيفرة البرمجية من الضياع أو من أجل مشاركتها مع أناس آخرين. طبعا مستودع شيفرتك البرمجية سيكون مُدارا بأحد أدوات إدارة النُسخ (VCS) مثل Git أو Mercurial مثلا. قد تكون الشيفرة على خادومك الخاص (Server)، أو على أحد خدمات استضافة المشاريع البرمجية مثل Github و Bitbucket. بما أن Github أشهر المنصات لمشاركة الشيفرات البرمجية، فسأضرب به المثال. تدفعك Go (أي أنه من المستحسن) إلى وضع شيفرتك البرمجية في مسار مشابه لمسار حسابك على github مثلا -وحتى أقرّب الصورة- لنفرض أن حسابك على github اسمه HsoubAcademy وبالتالي رابط حسابك هو: https://github.com/HsoubAcademyإذا أنشأت مشروعا بـ Go يحمل اسم example على سبيل المثال ثم رفعته على Github باستخدام حسابك HsoubAcademy فسيكون رابط المشروع هو: https://github.com/HsoubAcademy/exampleبالتالي فإن Go تدفعك ﻷن يكون مجلد المشروع على حاسوبك مشابها لهذا الرابط، أي تحت هذا المسار: work/src/github.com/HsoubAcademy/exampleحيث: github.com هو مجلد فرعي تحت مجلد src.HsoubAcademy هو مجلد فرعي تحت مجلد github.com آنف الذكر، غيّره إلى حسابك على Github مثلا.example هو مجلد فرعي يحوي ملفات مشروعك تحت مجلد HsoubAcademy.ملاحظة: أسماء المجلدات حسّاسة لحالة الأحرف (case-sensitive) ماعدا على نظام Windows. لماذا ترتيب بيئة العمل بهذا الشكل؟ببساطة ﻷن التنظيم بهذا الشكل مفيد جدًا من ناحيتين: 1. بالإمكان جلب أي مكتبة خارجية بمجرد عمل import لها من مسار مستودعها، مثلا: لنفرض أننا نريد استعمال مكتبة لنزع التشكيل عن النص العربي، سنستخدم مكتبة goarabic، سيكفي لتضمينها في مشروعنا البرمجي كتابة الأمر: go get github.com/01walid/goarabic2. يقوم أمر go get بوضع ناتج تجميع هذه المكتبة في مجلد pkg بنفس مسار رابطها على github، أي سيضعها داخل مجلد فرعي باسم 01walid داخل مجلد github.com الذي هو بدوره عبارة عن مجلد فرعي داخل مجلد العمل، بالتالي يمكن تضمينها مباشرة في مشروعنا بهذا الشكل: import "github.com/01walid/goarabic" لاحظ أن مسار استيراد هذه المكتبة هو نفسه رابطها على github. هذا يُسهّل من عملية مشاركة المكتبات البرمجية وإثراء مكتبات اللغة نفسها. من المهم جدا أن يتبع مشروعك نفس هذا المنهاج، خاصة إن كان عبارة عن مكتبة. تهيئة بيئة العملإن كنت على لينكس أو Mac OS، يمكنك مثلا إنشاء مجلد باسم work داخل مجلد Home خاصتك بكتابة أمر: mkdir $HOME/workثم جعل هذا الأخير هو بيئة عمل Go عبر إنشاء متغير بيئة باسم GOPATH (حسّاس لحالة الأحرف) يُشير له: export GOPATH=$HOME/workطبعا لجعل هذا المتغير دائم حتى بعد إعادة التشغيل، سيكون عليك كتابته في bashrc. (في حال كنت تستعمل صدفة bash، أو ملف zshrc. إن كنت تستعمل صدفة zsh كمثال، وهي ملفات موجود داخل مجلد المنزل خاصتك HOME$). أما إن كنت على Windows فيكفي إضافة متغير باسم GOPATH عبر التوجه إلى: خصائص النظام (System -> Advanced system settings)ثم النقر على متغيرات البيئة (Environment Variables)ثم إضافة المتغير من قسم System variables كما هو مبين أسفله. إذا كان مجلد عملك مثلا في Windows هو C:\Projects\Go فسيكون عليك إضافته بهذا الشكل: يمكنك التحقق من أنه تم إضافة المتغير الجديد، عبر فتح نافذة سطر أوامر جديدة، وكتابة الأمر: %echo %GOPATH كما هو موضح أسفله: إن تم إظهار المسار المُختار لمجلد عملك، فقد قمت أخيرًا بتنصيب Go وتهيئتها بنجاح. إضافة (Bonus)ماذا لو أمكننا جعل البرامج التنفيذية التي نكتبها أو نجلبها عبر أمر go get متوفرة مباشرة لدينا في نافذة سطر الأوامر دون التصفح إليها في كل مرة؟ مثلا لنقل أننا نريد الاستفادة من أداة ha المكتوبة بلغة Go، لتحويل ملفات Markdown إلى HTML جاهز للّصق على محرر آخر، نقوم بجلب الأداة: go get github.com/HsoubAcademy/haبما أن أداة ha عبارة عن برنامج تنفيذي فإن أمر go get سينقله مباشرة إلى مجلد bin داخل بيئة العمل. لكن لا نريد التنقل إلى مجلد bin داخل مجلد العمل لاستعمالها، نريد فقط كتابة ha في سطر الأوامر مباشرة للاستفادة من الأداة واستعمالها حتى وإن كنا في مجلد آحر. بما أن Go تقوم بوضع ناتج الملفات التنفيذية في مجلد bin تحت مجلد العمل، بالتالي، يكفي إضافة مسار مجلد bin إلى مسارات متغير البيئة PATH ليكون كل شيء متوفر لديك! حتى برامجك التنفيذية التي تكتبها بنفسك. بالنسبة لمستخدي Linux أو Mac OS فإن ذلك ممكن عبر إضافة مسار مجلد bin داخل مجلد العمل إلى متغير البيئة PATH: export PATH=$PATH:$GOPATH/binأما لمستخدمي Windows فعليهم إضافة مسار مجلد bin داخل مجلد العمل إلى متغير البيئة PATH عبر التوجه إلى: خصائص النظام (System -> Advanced system settings)ثم النقر على متغيرات البيئة (Environment Variables)البحث عن قيمة Path في قسم System variables ثم الضغط على edit وإضافة المسار إلى آخر السطة مسبوقا بفاصلة منقوطة (;) كما هو مبين أسفله. الآن ستجد أن كل ما هو موجود في مجلد bin من برامج وأدوات متاح لك، من ذلك أداة ha التي أشرنا إليها سابقا (جرب فتح نافذة سطر أوامر جديدة وكتابة الأمر ha). بهذا نأتي إلى نهاية الدرس الثاني من هذه السلسلة، سنشرع في الدرس القادم في كيفية بدء البرمجة بـ Go والاستفادة من بيئة العمل هذه.