Docker-in-Docker - bu konteyner tasvirlarini yaratish uchun konteyner ichida ishlaydigan virtuallashtirilgan Docker demon muhiti. Docker-in-Docker-ni yaratishning asosiy maqsadi Docker-ning o'zini rivojlantirishga yordam berish edi. Ko'p odamlar Jenkins CI-ni ishga tushirish uchun foydalanadilar. Avvaliga bu normaldek tuyuladi, ammo keyin Docker-ni Jenkins CI konteyneriga o'rnatish orqali oldini olish mumkin bo'lgan muammolar paydo bo'ladi. Ushbu maqolada buni qanday qilish kerakligi aytiladi. Agar siz batafsil ma'lumotsiz yakuniy yechimga qiziqsangiz, maqolaning oxirgi qismini "Muammoni hal qilish" ni o'qing.
Docker-in-Docker: "Yaxshi"
Ikki yildan ko'proq vaqt oldin men Docker-ga kiritdim
- hackity hack;
- qurmoq;
- ishlaydigan Docker demonini to'xtatish;
- yangi Docker demonini ishga tushirish;
- sinov;
- tsiklni takrorlang.
Agar siz chiroyli, takrorlanadigan yig'ilishni (ya'ni idishda) qilishni istasangiz, u yanada murakkablashdi:
- hackity hack;
- Dockerning ishlaydigan versiyasi ishlayotganligiga ishonch hosil qiling;
- eski Docker bilan yangi Docker yaratish;
- Docker demonini to'xtatish;
- yangi Docker demonini ishga tushiring;
- sinov;
- yangi Docker demonini to'xtatish;
- takrorlang.
Docker-in-Docker-ning paydo bo'lishi bilan jarayon soddalashdi:
- hackity hack;
- yig'ish + bir bosqichda ishga tushirish;
- tsiklni takrorlang.
Shu tarzda yaxshiroq emasmi?
Docker-in-Docker: "Yomon"
Biroq, mashhur e'tiqoddan farqli o'laroq, Docker-in-Docker 100% yulduzlar, ponilar va yagona shoxlar emas. Men shuni nazarda tutyapmanki, ishlab chiquvchi bilishi kerak bo'lgan bir nechta muammolar mavjud.
Ulardan biri AppArmor va SELinux kabi LSM (Linux xavfsizlik modullari) bilan bog'liq: konteynerni ishga tushirganda, "ichki Docker" "tashqi Docker" ga zid keladigan yoki chalkashtirib yuboradigan xavfsizlik profillarini qo'llashga urinishi mumkin. Imtiyozli bayroqning asl tatbiqini birlashtirishga urinayotganda, bu eng qiyin muammodir. Mening o'zgarishlarim ishladi va barcha testlar mening Debian mashinam va Ubuntu sinov VM-larida o'tadi, lekin ular Maykl Krosbining mashinasida ishdan chiqadi va yonib ketadi (esimda, u Fedora edi). Muammoning aniq sababini eslay olmayman, lekin Mayk SELINUX=enforce (men AppArmor’dan foydalanganman) bilan ishlaydigan dono yigit bo‘lgani va mening o‘zgarishlarim SELinux profillarini hisobga olmagani bo‘lishi mumkin.
Docker-in-Docker: "Yovuzlik"
Ikkinchi muammo Docker xotira drayverlari bilan bog'liq. Docker-in-Docker-ni ishga tushirganingizda, tashqi Docker oddiy fayl tizimi (EXT4, BTRFS yoki sizda mavjud bo'lgan narsa) ustida ishlaydi va ichki Docker yozma nusxa ko'chirish tizimi (AUFS, BTRFS, Device Mapper) ustida ishlaydi. va boshqalar). , tashqi Docker-dan foydalanish uchun nima sozlanganiga qarab). Bu ishlamaydigan ko'plab kombinatsiyalarni yaratadi. Masalan, siz AUFS-ni AUFS-ning tepasida ishlata olmaysiz.
Agar siz BTRFS-ni BTRFS-ning tepasida ishlatsangiz, u dastlab ishlashi kerak, lekin ichki ichki jildlar mavjud bo'lganda, asosiy pastki jildni o'chirish muvaffaqiyatsiz bo'ladi. Device Mapper moduli nom maydoniga ega emas, shuning uchun agar bir nechta Docker nusxalari uni bitta mashinada ishlayotgan bo'lsa, ularning barchasi bir-biridagi va konteyner zaxira qurilmalaridagi tasvirlarni ko'ra oladi (va ta'sir qiladi). Bu yomon.
Ushbu muammolarning ko'pini hal qilish uchun vaqtinchalik echimlar mavjud. Misol uchun, agar siz ichki Docker-da AUFS-dan foydalanmoqchi bo'lsangiz, shunchaki /var/lib/docker jildini jildga aylantiring va siz yaxshi bo'lasiz. Docker bir nechta Docker qo'ng'iroqlari bir xil mashinada ishlayotgan bo'lsa, ular bir-biriga qadam qo'ymasliklari uchun Device Mapper maqsad nomlariga ba'zi asosiy nom maydonlarini qo'shdi.
Biroq, bulardan ko'rinib turganidek, bunday sozlash umuman oddiy emas
Docker-in-Docker: Bu yomonlashadi
Qurilish keshi haqida nima deyish mumkin? Bu ham juda qiyin bo'lishi mumkin. Odamlar mendan tez-tez so'rashadi: "Agar men Docker-in-Docker-da ishlayotgan bo'lsam, hamma narsani ichki Docker-ga qaytarish o'rniga xostda joylashtirilgan tasvirlardan qanday foydalanishim mumkin?"
Ba'zi tashabbuskor odamlar /var/lib/docker-ni xostdan Docker-in-Docker konteyneriga ulashga harakat qilishdi. Ba'zan ular /var/lib/docker-ni bir nechta konteynerlar bilan bo'lishadi.
Ma'lumotlaringizni buzmoqchimisiz? Chunki aynan shu narsa ma'lumotlaringizga zarar yetkazadi!
Docker demoni /var/lib/docker-ga eksklyuziv kirish huquqiga ega bo'lishi uchun aniq ishlab chiqilgan. Ushbu jildda joylashgan Docker fayllariga boshqa hech narsa “tegishi, tepishi yoki ishlab chiqarishi” kerak emas.
Nega bunday? Chunki bu dotCloudni ishlab chiqishda olingan eng qiyin saboqlardan biri natijasidir. DotCloud konteyner dvigateli bir vaqtning o'zida /var/lib/dotcloud-ga bir nechta jarayonlarga kirish orqali ishladi. Atom faylini almashtirish (joyida tahrir qilish o'rniga), maslahat va majburiy qulflar bilan qalampirlash kodlari va SQLite va BDB kabi xavfsiz tizimlar bilan boshqa tajribalar kabi hiyla-nayranglar har doim ham ish bermadi. Oxir-oqibat Dockerga aylangan konteyner dvigatelimizni qayta loyihalashtirganimizda, eng katta dizayn qarorlaridan biri barcha konteyner operatsiyalarini bitta demon ostida birlashtirish edi.
Meni noto'g'ri tushunmang: bir nechta jarayonlarni va zamonaviy parallel boshqaruvni o'z ichiga olgan yaxshi, ishonchli va tezkor narsalarni qilish mutlaqo mumkin. Lekin bizning fikrimizcha, yagona o'yinchi sifatida Docker-dan foydalanib kod yozish va unga xizmat ko'rsatish osonroq va osonroq.
Bu shuni anglatadiki, agar siz /var/lib/docker katalogini bir nechta Docker misollari orasida baham ko'rsangiz, sizda muammolar paydo bo'ladi. Albatta, bu, ayniqsa sinovning dastlabki bosqichlarida ishlashi mumkin. "Eshiting, onam, men ubuntuni doker sifatida boshqara olaman!" Ammo murakkabroq narsani sinab ko'ring, masalan, bir xil tasvirni ikki xil misoldan tortib oling, shunda dunyo yonayotganini ko'rasiz.
Bu shuni anglatadiki, agar sizning CI tizimingiz qurish va qayta qurishni amalga oshirsa, har safar Docker-in-Docker konteyneringizni qayta ishga tushirganingizda, uning keshiga yadro qo'yish xavfi bor. Bu umuman zo'r emas!
Muammolarni bartaraf etish
Keling, bir qadam orqaga qaytaylik. Sizga haqiqatan ham Docker-in-Docker kerakmi yoki siz shunchaki Docker-ni ishga tushirishni va CI tizimining o'zi konteynerda bo'lganda CI tizimingizdan konteynerlar va tasvirlarni qurish va ishga tushirishni xohlaysizmi?
Ishonchim komilki, ko'pchilik oxirgi variantni xohlaydi, ya'ni ular Jenkins kabi CI tizimi konteynerlarni ishga tushirishni xohlashadi. Va buni amalga oshirishning eng oson yo'li oddiygina Docker soketini CI konteyneringizga kiritish va uni -v bayrog'i bilan bog'lashdir.
Oddiy qilib aytganda, CI konteyneringizni (Jenkins yoki boshqa) ishga tushirganingizda, Docker-in-Docker bilan biror narsani buzish o'rniga, uni quyidagi qatordan boshlang:
docker run -v /var/run/docker.sock:/var/run/docker.sock ...
Ushbu konteyner endi Docker soketiga kirish huquqiga ega bo'ladi va shuning uchun konteynerlarni ishga tushirishi mumkin. Bundan tashqari, "bolalar" konteynerlarini ishga tushirish o'rniga, "birodarlar" konteynerlarini ishga tushiradi.
Buni rasmiy docker tasviridan foydalanib ko'ring (u Docker binarini o'z ichiga oladi):
docker run -v /var/run/docker.sock:/var/run/docker.sock
-ti docker
U Docker-in-Docker-ga o'xshaydi va ishlaydi, lekin u Docker-in-Docker emas: bu konteyner qo'shimcha konteynerlarni yaratganda, ular yuqori darajadagi Docker-da yaratiladi. Siz joylashtirishning nojo'ya ta'sirini sezmaysiz va yig'ish keshi bir nechta qo'ng'iroqlar bo'ylab baham ko'riladi.
Eslatma: Ushbu maqolaning oldingi versiyalarida Docker ikkilik faylini xostdan konteynerga ulash tavsiya etilgan. Bu endi ishonchsiz bo'lib qoldi, chunki Docker dvigateli endi statik yoki yaqin statik kutubxonalarni qamrab olmaydi.
Shunday qilib, agar siz Jenkins CI-dan Docker-dan foydalanmoqchi bo'lsangiz, sizda ikkita variant mavjud:
Docker CLI-ni asosiy tasvirlarni qadoqlash tizimidan foydalangan holda o'rnatish (ya'ni, agar sizning rasmingiz Debian-ga asoslangan bo'lsa, .deb paketlaridan foydalaning), Docker API yordamida.
Ba'zi reklamalar 🙂
Biz bilan qolganingiz uchun tashakkur. Bizning maqolalarimiz sizga yoqdimi? Ko'proq qiziqarli tarkibni ko'rishni xohlaysizmi? Buyurtma berish yoki do'stlaringizga tavsiya qilish orqali bizni qo'llab-quvvatlang,
Amsterdamdagi Equinix Tier IV ma'lumotlar markazida Dell R730xd 2 baravar arzonmi? Faqat shu yerda
Manba: www.habr.com