Mikir kanthi teliti sadurunge nggunakake Docker-in-Docker kanggo CI utawa lingkungan test

Mikir kanthi teliti sadurunge nggunakake Docker-in-Docker kanggo CI utawa lingkungan test

Docker-in-Docker minangka lingkungan daemon Docker virtualisasi sing mlaku ing wadhah kasebut kanggo nggawe gambar wadhah. Tujuan utama nggawe Docker-in-Docker yaiku mbantu ngembangake Docker dhewe. Akeh wong nggunakake kanggo mbukak Jenkins CI. Iki katon normal ing wiwitan, nanging banjur ana masalah sing bisa dihindari kanthi nginstal Docker ing wadhah Jenkins CI. Artikel iki ngandhani carane nindakake iki. Yen sampeyan kasengsem ing solusi final tanpa rincian, mung maca bagean pungkasan saka artikel, "Ngatasi masalah."

Mikir kanthi teliti sadurunge nggunakake Docker-in-Docker kanggo CI utawa lingkungan test

Docker-in-Docker: "Apik"

Luwih saka rong taun kepungkur aku sijine menyang Docker gendera - hak istimewa lan nulis versi pisanan saka dind. Tujuane yaiku mbantu tim inti ngembangake Docker luwih cepet. Sadurunge Docker-in-Docker, siklus pangembangan khas katon kaya iki:

  • hackity hack;
  • mbangun;
  • mungkasi daemon Docker sing mlaku;
  • ngluncurake daemon Docker anyar;
  • testing;
  • mbaleni siklus.

Yen sampeyan pengin nggawe perakitan sing apik lan bisa direproduksi (yaiku, ing wadhah), banjur dadi luwih rumit:

  • hackity hack;
  • priksa manawa versi Docker sing bisa digunakake;
  • mbangun Docker anyar karo Docker lawas;
  • mungkasi daemon Docker;
  • miwiti daemon Docker anyar;
  • tes;
  • mungkasi daemon Docker anyar;
  • mbaleni.

Kanthi tekane Docker-in-Docker, proses kasebut dadi luwih gampang:

  • hackity hack;
  • perakitan + diluncurake ing siji tahap;
  • mbaleni siklus.

Apa ora luwih apik kanthi cara iki?

Mikir kanthi teliti sadurunge nggunakake Docker-in-Docker kanggo CI utawa lingkungan test

Docker-in-Docker: "Apik"

Nanging, bertentangan karo kapercayan populer, Docker-in-Docker dudu 100% lintang, ponies lan unicorn. Maksudku yaiku ana sawetara masalah sing kudu dingerteni pangembang.

Salah sijine yaiku LSM (modul keamanan Linux) kayata AppArmor lan SELinux: nalika mbukak wadhah, "Docker internal" bisa uga nyoba ngetrapake profil keamanan sing bakal konflik utawa mbingungake "Docker eksternal". Iki minangka masalah sing paling angel kanggo diatasi nalika nyoba nggabungake implementasi asli saka gendera -privileged. Owah-owahan saya bisa lan kabeh tes bakal ngliwati mesin Debian lan VM test Ubuntu, nanging bakal nabrak lan diobong ing mesin Michael Crosby (dheweke duwe Fedora kaya sing dakelingake). Aku ora bisa ngelingi sabab pas masalah, nanging bisa uga amarga Mike iku wong wicaksana sing dianggo karo SELINUX = nglakokakΓ© (Aku digunakake AppArmor) lan owah-owahan ora njupuk profil SELinux menyang akun.

Docker-in-Docker: "Evil"

Masalah kapindho yaiku karo driver panyimpenan Docker. Nalika sampeyan mbukak Docker-in-Docker, Docker eksternal mbukak ing ndhuwur sistem file biasa (EXT4, BTRFS, utawa apa wae sing sampeyan duwe) lan Docker internal mlaku ing ndhuwur sistem copy-on-write (AUFS, BTRFS, Device Mapper. , etc.). , gumantung apa sing dikonfigurasi kanggo nggunakake Docker eksternal). Iki nggawe akeh kombinasi sing ora bakal bisa. Contone, sampeyan ora bakal bisa mbukak AUFS ing ndhuwur AUFS.

Yen sampeyan mbukak BTRFS ing ndhuwur BTRFS, iku kudu bisa ing kawitan, nanging yen ana subvolume nested, mbusak subvolume induk bakal gagal. Modul Device Mapper ora duwe ruang jeneng, dadi yen sawetara kasus Docker mlaku ing mesin sing padha, kabeh bakal bisa ndeleng (lan pengaruhe) gambar ing saben liyane lan ing piranti serep wadhah. Iki ala.

Ana solusi kanggo ngatasi akeh masalah kasebut. Contone, yen sampeyan pengin nggunakake AUFS ing Docker internal, mung nguripake folder / var / lib / docker menyang volume lan sampeyan bakal nggoleki. Docker wis nambah sawetara ruang jeneng dhasar menyang jeneng target Device Mapper supaya yen sawetara panggilan Docker mlaku ing mesin sing padha, ora bakal saling ngindhari.

Nanging, persiyapan kasebut ora gampang, kaya sing bisa dideleng saka iki artikel ing repositori dind ing GitHub.

Docker-in-Docker: Dadi luwih elek

Apa babagan cache mbangun? Iki bisa uga cukup angel. Wong asring takon kula "yen aku mlaku Docker-in-Docker, carane aku bisa nggunakake gambar sing di-host ing host tinimbang narik kabeh bali menyang Docker internal"?

Sawetara wong sing giat nyoba ngiket /var/lib/docker saka host menyang wadhah Docker-in-Docker. Kadhangkala padha nuduhake /var/lib/docker karo macem-macem kontaner.

Mikir kanthi teliti sadurunge nggunakake Docker-in-Docker kanggo CI utawa lingkungan test
Apa sampeyan pengin ngrusak data sampeyan? Amarga iki persis sing bakal ngrusak data sampeyan!

Daemon Docker dirancang kanthi jelas kanggo duwe akses eksklusif menyang /var/lib/docker. Ora ana liyane sing kudu "ndemek, nyodok, utawa nyolong" file Docker sing ana ing folder iki.

Kok ngono? Amarga iki minangka asil saka salah sawijining pelajaran sing paling angel dipelajari nalika ngembangake dotCloud. Mesin kontainer dotCloud mlaku kanthi akeh proses ngakses /var/lib/dotcloud bebarengan. Trik licik kayata panggantos file atom (tinimbang suntingan ing panggonan), kode peppering kanthi kunci penasehat lan wajib, lan eksperimen liyane kanthi sistem aman kayata SQLite lan BDB ora tansah bisa. Nalika kita ngrancang maneh mesin kontaner, sing pungkasane dadi Docker, salah sawijining keputusan desain gedhe yaiku nggabungake kabeh operasi kontainer ing daemon siji kanggo ngilangi kabeh omong kosong.

Aja salah: sampeyan bisa nggawe sing apik, dipercaya lan cepet sing kalebu macem-macem proses lan kontrol paralel modern. Nanging kita mikir iku luwih prasaja lan luwih gampang kanggo nulis lan njaga kode nggunakake Docker minangka siji-sijine pemain.

Iki tegese yen sampeyan nuduhake direktori / var / lib / docker ing antarane sawetara instance Docker, sampeyan bakal duwe masalah. Mesthi wae, iki bisa ditindakake, utamane ing tahap awal tes. "Ngrungokake, Ma, aku bisa mbukak ubuntu minangka buruh pelabuhan!" Nanging coba sing luwih rumit, kayata narik gambar sing padha saka rong kedadeyan sing beda, lan sampeyan bakal weruh jagad iki kobong.

Iki tegese yen sistem CI sampeyan nindakake mbangun lan mbangun maneh, saben sampeyan miwiti maneh wadhah Docker-in-Docker, sampeyan duwe risiko nyelehake nuke menyang cache. Iki ora kelangan kabeh!

Ngatasi masalah

Ayo mundur selangkah. Apa sampeyan pancene mbutuhake Docker-in-Docker utawa sampeyan mung pengin bisa mbukak Docker lan mbangun lan mbukak wadhah lan gambar saka sistem CI nalika sistem CI dhewe ana ing wadhah?

Aku nang paling wong pengin pilihan terakhir, tegese padha pengin sistem CI kaya Jenkins bisa mbukak kontaner. Lan cara paling gampang kanggo nindakake iki yaiku nglebokake soket Docker menyang wadhah CI lan digandhengake karo bendera -v.

Cukup, nalika sampeyan mbukak wadhah CI (Jenkins utawa liyane), tinimbang hacking soko bebarengan karo Docker-in-Docker, miwiti karo baris:

docker run -v /var/run/docker.sock:/var/run/docker.sock ...

Wadhah iki saiki bakal duwe akses menyang soket Docker lan mulane bisa mbukak wadhah. Kajaba iku, tinimbang mbukak wadhah "anak", bakal mbukak wadhah "sedulur".

Coba iki nggunakake gambar docker resmi (sing ngemot binar Docker):

docker run -v /var/run/docker.sock:/var/run/docker.sock 
           -ti docker

Katon lan kerjane kaya Docker-in-Docker, nanging dudu Docker-in-Docker: nalika wadhah iki nggawe wadhah tambahan, bakal digawe ing Docker tingkat paling dhuwur. Sampeyan ora bakal nemu efek sisih nesting lan cache perakitan bakal dienggo bareng ing sawetara telpon.

Cathetan: Versi sadurunge artikel iki menehi saran kanggo ngubungake binar Docker saka host menyang wadhah. Iki saiki wis ora bisa dipercaya amarga mesin Docker ora nutupi perpustakaan statis utawa cedhak statis.

Dadi, yen sampeyan pengin nggunakake Docker saka Jenkins CI, sampeyan duwe 2 pilihan:
nginstal Docker CLI nggunakake sistem packaging gambar dhasar (i.e. yen gambar adhedhasar Debian, nggunakake paket .deb), nggunakake Docker API.

Sawetara iklan πŸ™‚

Matur nuwun kanggo tetep karo kita. Apa sampeyan seneng karo artikel kita? Pengin ndeleng konten sing luwih menarik? Ndhukung kita kanthi nggawe pesenan utawa menehi rekomendasi menyang kanca, cloud VPS kanggo pangembang saka $4.99, analog unik saka server level entri, sing diciptakake kanggo sampeyan: Bebener kabeh babagan VPS (KVM) E5-2697 v3 (6 Cores) 10GB DDR4 480GB SSD 1Gbps saka $ 19 utawa carane nuduhake server? (kasedhiya karo RAID1 lan RAID10, munggah 24 intine lan nganti 40GB DDR4).

Dell R730xd 2 kaping luwih murah ing pusat data Equinix Tier IV ing Amsterdam? Mung kene 2 x Intel TetraDeca-Core Xeon 2x E5-2697v3 2.6GHz 14C 64GB DDR4 4x960GB SSD 1Gbps 100 TV saka $199 ing Walanda! Dell R420 - 2x E5-2430 2.2Ghz 6C 128GB DDR3 2x960GB SSD 1Gbps 100TB - saka $99! Maca babagan Carane mbangun infrastruktur corp. kelas karo nggunakake Dell R730xd E5-2650 v4 server worth 9000 euro kanggo Penny?

Source: www.habr.com

Add a comment