اکنون می توانید تصاویر Docker را با استفاده از یک Dockerfile معمولی در werf بسازید

دیر رسیدن بهتر از هرگز نرسیدن است. یا اینکه چگونه با عدم پشتیبانی از Dockerfiles معمولی برای ساخت تصاویر برنامه تقریباً یک اشتباه جدی مرتکب شدیم.

اکنون می توانید تصاویر Docker را با استفاده از یک Dockerfile معمولی در werf بسازید

در مورد خواهد بود ورف - یک ابزار GitOps که با هر سیستم CI / CD یکپارچه می شود و مدیریت کل چرخه عمر برنامه را فراهم می کند و به شما امکان می دهد:

  • جمع آوری و انتشار تصاویر،
  • استقرار برنامه ها در Kubernetes،
  • حذف تصاویر استفاده نشده با استفاده از سیاست های خاص.


فلسفه این پروژه جمع آوری ابزارهای سطح پایین در یک سیستم واحد است که به مهندسان DevOps کنترل بر برنامه ها را می دهد. در صورت امکان، باید از ابزارهای موجود (مانند Helm و Docker) استفاده شود. اگر هیچ راه حلی برای مشکل وجود نداشته باشد، می توانیم هر چیزی را که برای آن لازم است ایجاد و نگهداری کنیم.

پس زمینه: گردآورنده تصویر شما

این همان چیزی است که با سازنده تصویر در werf اتفاق افتاد: ما فاقد Dockerfile معمولی بودیم. اگر به طور خلاصه وارد تاریخچه پروژه شوید ، این مشکل قبلاً در اولین نسخه های werf ظاهر شد (سپس به عنوان dapp شناخته می شود).

در حین ایجاد ابزاری برای ساخت برنامه‌ها در تصاویر Docker، به سرعت متوجه شدیم که Dockerfile برای برخی از کارهای بسیار خاص برای ما مناسب نیست:

  1. نیاز به مونتاژ برنامه های کاربردی وب کوچک معمولی طبق طرح استاندارد زیر:
    • وابستگی های سیستمی برنامه را نصب کنید،
    • بسته ای از کتابخانه های وابستگی برنامه را نصب کنید،
    • جمع آوری دارایی ها،
    • و از همه مهمتر، کدهای موجود در تصویر را به سرعت و کارآمد به روز کنید.
  2. هنگامی که تغییراتی در فایل های پروژه ایجاد می شود، سازنده باید به سرعت یک لایه جدید با وصله فایل های تغییر یافته ایجاد کند.
  3. اگر فایل های خاصی تغییر کرده اند، مرحله وابسته مربوطه باید دوباره ساخته شود.

امروزه امکانات بسیار دیگری در شیر آب ما وجود دارد، اما خواسته ها و اصرارهای اولیه به شرح زیر بود.

به طور کلی، بدون دو بار فکر کردن، خود را به زبان برنامه نویسی مورد استفاده مسلح کردیم (پایین را ببینید) و به جاده - برای اجرا DSL خود! مطابق با مجموعه وظایف، در نظر گرفته شده بود که فرآیند ساخت به صورت مرحله ای شرح داده شود و وابستگی این مراحل به فایل ها مشخص شود. و آن را تکمیل کرد شیر آب خود، که DSL را به هدف نهایی تبدیل کرد - تصویر مونتاژ شده. در ابتدا DSL در Ruby بود، اما به عنوان تغییر به گولنگ - پیکربندی کلکتور ما در فایل YAML شرح داده شد.

اکنون می توانید تصاویر Docker را با استفاده از یک Dockerfile معمولی در werf بسازید
پیکربندی قدیمی برای dapp در روبی

اکنون می توانید تصاویر Docker را با استفاده از یک Dockerfile معمولی در werf بسازید
پیکربندی واقعی برای werf در YAML

مکانیسم کلکتور نیز با گذشت زمان تغییر کرد. در ابتدا، ما به سادگی مقداری Dockerfile موقت را از پیکربندی خود در پرواز ایجاد کردیم، و سپس شروع به اجرای دستورالعمل های ساخت در کانتینرهای موقت و ایجاد یک commit کردیم.

NB: در حال حاضر، سازنده ما، که با پیکربندی خود (در YAML) کار می کند و Stapel builder نامیده می شود، قبلاً به یک ابزار نسبتاً قدرتمند تبدیل شده است. شرح مفصل آن مستحق مقالات جداگانه است و جزئیات اصلی را می توان در آن یافت مستندات.

آگاهی از مشکل

اما ما متوجه شدیم، و نه بلافاصله، که یک اشتباه مرتکب شده بودیم: توانایی را اضافه نکردیم ساخت تصاویر از طریق یک Dockerfile استاندارد و آنها را در همان زیرساخت مدیریت برنامه های کاربردی ادغام کنید (یعنی جمع آوری تصاویر، استقرار و پاکسازی آنها). چگونه می توانید یک ابزار استقرار در Kubernetes ایجاد کنید و پشتیبانی Dockerfile را پیاده سازی نکنید. یک روش استاندارد برای توصیف تصاویر برای اکثر پروژه ها؟...

به جای پاسخ به چنین سوالی، راه حل آن را ارائه می دهیم. اگر از قبل یک Dockerfile (یا مجموعه ای از Dockerfiles) داشته باشید و بخواهید از werf استفاده کنید چه؟

NB: به هر حال، چرا حتی می خواهید از werf استفاده کنید؟ ویژگی های اصلی به موارد زیر خلاصه می شود:

  • چرخه مدیریت کامل برنامه شامل تمیز کردن تصاویر.
  • توانایی مدیریت مونتاژ چندین تصویر به طور همزمان از یک پیکربندی واحد؛
  • روند استقرار بهبود یافته برای نمودارهای سازگار Helm.

لیست کامل تر را می توانید در اینجا پیدا کنید صفحه پروژه.

بنابراین، اگر قبلاً پیشنهاد می‌کردیم Dockerfile را در پیکربندی خود بازنویسی کنیم، اکنون با خوشحالی می‌گوییم: «اجازه دهید ورف Dockerfiles شما را بسازد!»

چگونه استفاده کنیم؟

اجرای کامل این ویژگی در نسخه منتشر شد werf نسخه 1.0.3-بتا.1. اصل کلی ساده است: کاربر مسیر یک Dockerfile موجود را در پیکربندی werf مشخص می‌کند و سپس دستور را اجرا می‌کند. werf build... و بس - werf تصویر را می سازد. بیایید یک مثال انتزاعی را در نظر بگیریم.

بعدی را اعلام کنیم Dockerfile در ریشه پروژه:

FROM ubuntu:18.04
RUN echo Building ...

و اعلام خواهیم کرد werf.yamlکه از این استفاده می کند Dockerfile:

configVersion: 1
project: dockerfile-example
---
image: ~
dockerfile: ./Dockerfile

همه! ترک کرد اجرا کن werf build:

اکنون می توانید تصاویر Docker را با استفاده از یک Dockerfile معمولی در werf بسازید

علاوه بر این می توانید موارد زیر را اعلام کنید werf.yaml برای ساخت چندین تصویر به طور همزمان از Dockerfiles مختلف:

configVersion: 1
project: dockerfile-example
---
image: backend
dockerfile: ./dockerfiles/Dockerfile-backend
---
image: frontend
dockerfile: ./dockerfiles/Dockerfile-frontend

در نهایت، ارسال پارامترهای ساخت اضافی نیز پشتیبانی می شود - مانند --build-arg и --add-host - از طریق پیکربندی werf. شرح کاملی از پیکربندی تصویر Dockerfile در این آدرس موجود است صفحات اسناد.

چگونه کار می کند؟

در طی فرآیند ساخت، کش استاندارد لایه های محلی در توابع داکر عمل می کند. با این حال، مهم است، ورف نیز پیکربندی Dockerfile را در زیرساخت خود ادغام می کند. این یعنی چی؟

  1. هر تصویر ساخته شده از یک Dockerfile از یک مرحله تشکیل شده است که به آن می گویند dockerfile (در مورد اینکه چه مراحلی در werf هستند، می توانید بخوانید اینجا).
  2. برای صحنه dockerfile werf یک امضا را محاسبه می کند که به محتوای پیکربندی Dockerfile بستگی دارد. با تغییر پیکربندی Dockerfile، امضای مرحله تغییر می کند dockerfile و werf بازسازی آن مرحله را با پیکربندی جدید Dockerfile آغاز خواهد کرد. اگر امضا تغییر نکند، werf تصویر را از حافظه پنهان می گیرد (بیشتر در مورد استفاده از امضا در werf در توضیح داده شد این گزارش).
  3. علاوه بر این، تصاویر جمع آوری شده را می توان با دستور منتشر کرد werf publish (یا werf build-and-publish) و از آن برای استقرار در Kubernetes استفاده کنید. تصاویر منتشر شده در Docker Registry با ابزارهای استاندارد پاکسازی werf پاک می شوند. پاکسازی خودکار تصاویر قدیمی (قدیمی‌تر از N روز)، تصاویر مرتبط با شاخه‌های Git وجود ندارد و سایر خط‌مشی‌ها وجود خواهد داشت.

جزئیات بیشتر در مورد نکاتی که در اینجا توضیح داده شده است را می توان در اسناد یافت:

یادداشت ها و اقدامات احتیاطی

1. URL خارجی در ADD پشتیبانی نمی شود

استفاده از URL خارجی در دستورالعمل در حال حاضر پشتیبانی نمی شود. ADD. هنگامی که منبعی در URL مشخص شده تغییر می کند، Werf بازسازی را راه اندازی نمی کند. این ویژگی قرار است به زودی اضافه شود.

2. نمی توانید git را به یک تصویر اضافه کنید

به طور کلی، اضافه کردن یک دایرکتوری .git درون یک تصویر یک عمل بد شرورانه است، و در اینجا دلیل آن است:

  1. اگر .git در تصویر نهایی باقی می ماند، این اصول را نقض می کند اپلیکیشن 12 عاملی: از آنجایی که تصویر حاصل باید با یک commit مرتبط باشد، انجام آن نباید امکان پذیر باشد git checkout ارتکاب خودسرانه
  2. .git اندازه تصویر را افزایش می دهد (ممکن است مخزن بزرگ باشد به این دلیل که یک بار فایل های بزرگ به آن اضافه شده و سپس حذف شده اند). اندازه درخت کاری که فقط با یک commit خاص مرتبط است به سابقه عملیات در Git بستگی ندارد. در این مورد، اضافه و حذف بعدی .git از تصویر نهایی کار نخواهد کرد: تصویر همچنان یک لایه اضافی خواهد داشت - داکر اینگونه کار می کند.
  3. داکر ممکن است باعث ایجاد یک بازسازی غیر ضروری شود، حتی اگر همان commit از درختان کاری متفاوت ساخته شود. به عنوان مثال، GitLab دایرکتوری های کلون شده مجزا را در آن ایجاد می کند /home/gitlab-runner/builds/HASH/[0-N]/yourproject با فعال بودن مونتاژ موازی بازسازی اضافی به دلیل این واقعیت است که دایرکتوری .git در نسخه های مختلف شبیه سازی شده از یک مخزن متفاوت است، حتی اگر همان commit ساخته شده باشد.

نکته آخر نیز در استفاده از werf عواقبی دارد. Werf نیاز دارد که حافظه پنهان ساخته شده هنگام اجرای برخی از دستورات وجود داشته باشد (به عنوان مثال، werf deploy). در طول اجرای چنین دستوراتی، werf امضاهای مرحله را برای تصاویر مشخص شده در آن محاسبه می کند werf.yaml، و آنها باید در کش ساخت باشند، در غیر این صورت دستور نمی تواند ادامه یابد. در صورتی که امضای مراحل به محتوا بستگی دارد .git، سپس یک حافظه پنهان دریافت می کنیم که در برابر تغییرات در فایل های نامربوط ناپایدار است و werf نمی تواند چنین نادیده گرفته شده را ببخشد (برای جزئیات بیشتر، رجوع کنید به مستندات).

به طور کلی، فقط برخی از فایل های مورد نیاز را اضافه می کند از طریق دستورالعمل ADD در هر صورت کارایی و پایایی نوشته را افزایش می دهد Dockerfile، و همچنین پایداری حافظه پنهان جمع آوری شده توسط این را بهبود می بخشد Dockerfile، به تغییرات نامربوط در Git.

مجموع

مسیر اولیه ما با نوشتن سازنده خودمان برای نیازهای خاص سخت، صادقانه و سرراست بود: به جای استفاده از عصا در بالای Dockerfile استاندارد، راه حل خود را با نحو سفارشی نوشتیم. و این مزیت های خود را به همراه داشت: کلکسیونر Stapel کار خود را به خوبی انجام می دهد.

با این حال، در فرآیند نوشتن سازنده خود، ما از پشتیبانی از Dockerfiles موجود غافل شدیم. اکنون این نقص برطرف شده است و در آینده قصد داریم پشتیبانی Dockerfile را به همراه سازنده Stapel سفارشی خود برای ساخت‌های توزیع‌شده و برای ساخت با استفاده از Kubernetes توسعه دهیم (یعنی ساختن روی رانرها در Kubernetes، همانطور که در kaniko انجام شد).

بنابراین، اگر به طور ناگهانی چند داکرفایل در اطراف شما وجود دارد ... آن را امتحان کنید ورف!

PS فهرست اسناد در مورد موضوع

در وبلاگ ما نیز بخوانید:werf - ابزار ما برای CI / CD در Kubernetes (نمایش کلی و گزارش تصویری)'.

منبع: www.habr.com

اضافه کردن نظر