یکی از دوستان سناریویی مطرح کرد در راستای این که اگه runner روی کلاستر کوبر باشه و executorش هم روی کوبر قرار داده باشیم، چه طوری میتونیم یه Dockerfile رو اجرا کنیم که واسمون build کنه؟
ساختن image در CI یکی از کارهای رایجی هستش که رخ میده، ولی خب سوالاتی هم مثل همین مورد که اگه روی کوبر باشیم چی، این که اصلا چه طوری میشه این کار رو کرد، مگه runner و executorش رو کوبر نیست، پس قاعدتا یک pod میاد بالا تا جاب رو انجام بده، چه طوری میشه یک ایمیج داکر ساخت؟.
که ما میخوایم با buildah به این سوالات پاسخ بدیم.
قبل از شروع موضوع اصلی یه نگاهی به ساختار CIمون بندازیم:
میدونیم که راه های متفاوتی برای ساختن یک Image وجود داره، ولی این رو هم میدونیم که نمیتونیم از دستور . docker build -t testiamge استفاده کنیم، چون این مورد نیاز به docker daemon داره و از اوجایی که خود این مورد قراره توی یک pod انجام بشه کار رو پیچیده تر هم میکنه.
یک کار زشت ولی خب به طور معمول رو میشه انجام داد، اونم mount کردن docker socket به داخل یک کانیتر هستش که عملا بهش این اجازه رو میدیم که از داخل کانتینر با دستور docker بتونه docker daemon اجرا روی سرورمون (host) رو مدیریت کنه، خب قاعدتن ما این کار رو نمیکنیم.
از یک پروژه زیبا به اسم buildah استفاده میکنیم و این کار رو برامون خیلی راحت و بهتر میکنه، حتی زمانی که از داخل یک کانتینر اجرا میکنین.
ما از image خودش استفاده میکنیم که alpine-based هستش و شامل موارد زیر هم میشه:
ما میخوایم از طریق پایپ لاین Gitlab-CI این کار رو انجام بدیم، من runner رو با Helm ساختم و از values فایل زیر استفاده کردم:
Gitlab Runner Helm Values File
ما نیاز داریم یک آدرسی رو برای buildah که عملا کانتینرها رو اونجا ذخیره میکنه توی config.toml رانرمون mount کنیم، دیتای بیشتر بابت علت این mount کردن.
شاید براتون سوال باشه که چرا Mount کردن دایرکتوری بهتر از اینه که یک socket رو mount کنیم؟
تفاوت خیلی زیادی دارن، ما میتونیم هر دایرکتوری از hostمون رو به داخل buildah به صورت راحت mount کنیم و پروژه های جداگانهای رو باهاشون داشته باشیم. و از همه مهمتر این که آدرس `/var/lib/containers/` فقط یک دایرکتوریه (واسه storage و ذخیره سازی)، نه مدیریت socket.
حالا ما هم builder imageمون رو داریم و هم Gitlab runnerمون رو که آماده هستن واسه ساختن image و تنها چیزی که نیاز داریم اینه تا پایپ لاین CIمون رو بنویسیم.
فقط نیازه دو سه تا دستور رو جایگزین کنیم به جای روال عادی مون در استفاده از docker:
و حالا پایپ لاین رو اجرا میکنیم و میریم چایی میخوریم تا کارش تموم بشه:
حالا ما میتونیم imageهایی که میخوایم رو با Gitlab CI با توجه به این که executor رانرمون هم کوبرنتیز هستش رو هم بسازیم. این هم در نظر داشته باشین که تماما به شما بستگی داره که از چه ابزاری برای این مورد استفاده میکنین، ولی استفاده های جالب تری هم میشه از podman و buildah هم داشت مثل image signing. اگه از این مطلب خوشتون اومد حتما به من بگین.
منابع:
Use Buildah in a rootless container with GitLab Runner Operator