Imej Docker kecil yang percaya pada diri mereka sendiri*

[rujukan kepada kisah dongeng kanak-kanak Amerika "The Little Engine That Could" - lebih kurang. lorong]*

Imej Docker kecil yang percaya pada diri mereka sendiri*

Cara membuat imej Docker kecil secara automatik untuk keperluan anda

Ketaksuban Luar Biasa

Sejak beberapa bulan kebelakangan ini, saya terobsesi dengan betapa kecilnya imej Docker dan masih mempunyai aplikasi yang sedang berjalan?

Saya faham, idea itu pelik.

Sebelum saya masuk ke butiran dan teknikal, saya ingin menjelaskan mengapa masalah ini sangat mengganggu saya, dan bagaimana ia melibatkan anda.

Mengapa saiz penting

Dengan mengurangkan kandungan imej Docker, kami dengan itu mengurangkan senarai kelemahan. Selain itu, kami menjadikan imej lebih bersih, kerana ia hanya mengandungi apa yang diperlukan untuk menjalankan aplikasi.

Terdapat satu lagi kelebihan kecil - imej dimuat turun sedikit lebih cepat, tetapi, pada pendapat saya, ini tidak begitu penting.

Sila ambil perhatian: Jika anda bimbang tentang saiz, Alpine kelihatan sendiri kecil dan mungkin sesuai dengan anda.

Imej tanpa distro

Projek Distroless menawarkan pilihan imej "tanpa distro" asas, ia tidak mengandungi pengurus pakej, cangkerang dan utiliti lain yang biasa anda lihat pada baris arahan. Akibatnya, gunakan pengurus pakej seperti pip и apt tidak akan berfungsi:

FROM gcr.io/distroless/python3
RUN  pip3 install numpy

Fail Docker menggunakan imej tanpa distro Python 3

Sending build context to Docker daemon  2.048kB
Step 1/2 : FROM gcr.io/distroless/python3
 ---> 556d570d5c53
Step 2/2 : RUN  pip3 install numpy
 ---> Running in dbfe5623f125
/bin/sh: 1: pip3: not found

Pip tiada dalam imej

Biasanya masalah ini diselesaikan dengan binaan berbilang peringkat:

FROM python:3 as builder
RUN  pip3 install numpy

FROM gcr.io/distroless/python3
COPY --from=builder /usr/local/lib/python3.7/site-packages /usr/local/lib/python3.5/

Perhimpunan pelbagai peringkat

Hasilnya ialah imej bersaiz 130MB. Boleh tahan! Sebagai perbandingan: imej Python lalai mempunyai berat 929MB, dan yang "lebih nipis" (3,7-slim) - 179MB, imej alpine (3,7-alpine) ialah 98,6MB, manakala imej tanpa distro asas yang digunakan dalam contoh ialah 50,9MB.

Adalah wajar untuk menunjukkan bahawa dalam contoh sebelumnya kita menyalin keseluruhan direktori /usr/local/lib/python3.7/site-packages, yang mungkin mengandungi kebergantungan yang kami tidak perlukan. Walaupun jelas bahawa perbezaan saiz semua imej asas Python yang sedia ada berbeza-beza.

Pada masa penulisan, Google distroless tidak menyokong banyak imej: Java dan Python masih di peringkat percubaan, dan Python hanya wujud untuk 2,7 dan 3,5.

Imej kecil

Kembali kepada obsesi saya untuk mencipta imej kecil.

Secara umum, saya ingin melihat bagaimana imej tanpa gangguan dibina. Projek tanpa distro menggunakan alat binaan Google bazel. Walau bagaimanapun, memasang Bazel dan menulis imej anda sendiri mengambil banyak usaha (dan sejujurnya, mencipta semula roda itu menyeronokkan dan mendidik). Saya ingin memudahkan penciptaan imej yang lebih kecil: tindakan mencipta imej haruslah sangat mudah, cetek. Supaya tiada fail konfigurasi untuk anda, hanya satu baris dalam konsol: просто собрать образ для <приложение>.

Jadi, jika anda ingin mencipta imej anda sendiri, ketahuilah: terdapat imej docker yang unik, scratch. Gores ialah imej "kosong", tiada fail di dalamnya, walaupun beratnya secara lalai - wow! - 77 bait.

FROM scratch

Gambar calar

Idea imej calar ialah anda boleh menyalin sebarang kebergantungan dari mesin hos ke dalamnya dan sama ada menggunakannya di dalam Dockerfile (ini seperti menyalinnya ke apt dan pasang dari awal), atau kemudian apabila imej Docker diwujudkan. Ini membolehkan anda mengawal sepenuhnya kandungan bekas Docker, dan dengan itu mengawal sepenuhnya saiz imej.

Sekarang kita perlu mengumpul kebergantungan ini. Alat sedia ada seperti apt membolehkan anda memuat turun pakej, tetapi ia terikat pada mesin semasa dan, selepas semua, tidak menyokong Windows atau MacOS.

Jadi saya mula membina alat saya sendiri yang secara automatik akan membina imej asas dengan saiz terkecil yang mungkin dan juga menjalankan sebarang aplikasi. Saya menggunakan pakej Ubuntu/Debian, membuat pilihan (mendapatkan pakej terus dari repositori) dan mencari kebergantungan mereka secara rekursif. Program ini sepatutnya memuat turun versi stabil terkini pakej secara automatik, meminimumkan risiko keselamatan sebanyak mungkin.

Saya menamakan alat itu fetchy, kerana dia... mencari dan membawa... apa yang diperlukan [dari bahasa Inggeris “ambil”, “bawa” - lebih kurang. lorong]. Alat ini berfungsi melalui antara muka baris arahan, tetapi pada masa yang sama menawarkan API.

Untuk memasang imej menggunakan fetchy (mari ambil imej Python kali ini), anda hanya perlu menggunakan CLI seperti ini: fetchy dockerize python. Anda mungkin diminta untuk sistem pengendalian sasaran dan nama kod kerana fetchy pada masa ini hanya menggunakan pakej berdasarkan Debian dan Ubuntu.

Kini anda boleh memilih kebergantungan yang tidak diperlukan sama sekali (dalam konteks kami) dan mengecualikannya. Sebagai contoh, Python bergantung pada perl, walaupun ia berfungsi dengan baik tanpa Perl dipasang.

Penemuan

Imej Python dibuat menggunakan arahan fetchy dockerize python3.5 beratnya hanya 35MB (saya lebih pasti bahawa pada masa akan datang ia boleh dibuat lebih ringan). Ternyata kami berjaya menghilangkan 15 WW lagi daripada imej tanpa distro.

Anda boleh melihat semua imej yang dikumpul setakat ini di sini.

Projek - di sini.

Jika anda tiada ciri, buat sahaja permintaan - Saya berbesar hati untuk membantu :) Lebih-lebih lagi, saya sedang berusaha untuk menyepadukan pengurus pakej lain ke dalam fetchy, supaya tidak ada keperluan untuk binaan berbilang peringkat.

Sumber: www.habr.com

Tambah komen