Imej sedia pengeluaran untuk k8s

Cerita ini adalah tentang cara kami menggunakan bekas dalam persekitaran pengeluaran, khususnya Kubernetes. Artikel ini dikhaskan untuk mengumpul metrik dan log daripada bekas, serta membina imej.

Imej sedia pengeluaran untuk k8s

Kami daripada syarikat fintech Exness, yang membangunkan perkhidmatan untuk dagangan dalam talian dan produk fintech untuk B2B dan B2C. R&D kami mempunyai banyak pasukan yang berbeza, jabatan pembangunan mempunyai 100+ pekerja.

Kami mewakili pasukan yang bertanggungjawab ke atas platform untuk pembangun kami mengumpul dan menjalankan kod. Khususnya, kami bertanggungjawab untuk mengumpul, menyimpan dan melaporkan metrik, log dan peristiwa daripada aplikasi. Pada masa ini kami mengendalikan kira-kira tiga ribu bekas Docker dalam persekitaran pengeluaran, mengekalkan storan data besar 50 TB kami dan menyediakan penyelesaian seni bina yang dibina di sekitar infrastruktur kami: Kubernetes, Rancher dan pelbagai penyedia awan awam. 

motivasi kita

Apa yang terbakar? Tiada siapa yang boleh menjawab. Di manakah perapian? Sukar untuk difahami. Bilakah ia terbakar? Anda boleh mengetahui, tetapi tidak serta-merta. 

Imej sedia pengeluaran untuk k8s

Mengapakah beberapa bekas berdiri manakala yang lain telah jatuh? Bekas mana yang patut dipersalahkan? Lagipun, bahagian luar bekas adalah sama, tetapi di dalam setiap bekas mempunyai Neo sendiri.

Imej sedia pengeluaran untuk k8s

Pembangun kami adalah lelaki yang cekap. Mereka membuat perkhidmatan yang baik yang membawa keuntungan kepada syarikat. Tetapi terdapat kegagalan apabila bekas dengan aplikasi tersesat. Satu bekas menggunakan terlalu banyak CPU, satu lagi menggunakan rangkaian, satu lagi menggunakan operasi I/O, dan yang keempat tidak jelas apa yang dilakukannya dengan soket. Semuanya jatuh dan kapal itu karam. 

Ejen

Untuk memahami apa yang berlaku di dalam, kami memutuskan untuk meletakkan ejen secara langsung dalam bekas.

Imej sedia pengeluaran untuk k8s

Ejen-ejen ini menghalang program yang menyimpan bekas dalam keadaan sedemikian sehingga mereka tidak pecah antara satu sama lain. Ejen diseragamkan, dan ini membolehkan pendekatan standard untuk menservis bekas. 

Dalam kes kami, ejen mesti menyediakan log dalam format standard, ditanda dan didikit. Mereka juga harus memberikan kami metrik piawai yang boleh dikembangkan dari perspektif aplikasi perniagaan.

Ejen juga bermaksud utiliti untuk operasi dan penyelenggaraan yang boleh berfungsi dalam sistem orkestrasi berbeza yang menyokong imej berbeza (Debian, Alpine, Centos, dll.).

Akhir sekali, ejen mesti menyokong CI/CD mudah yang merangkumi fail Docker. Jika tidak, kapal akan runtuh, kerana kontena akan mula dihantar di sepanjang rel "bengkok".

Proses bina dan peranti imej sasaran

Untuk memastikan segala-galanya piawai dan terurus, beberapa jenis proses binaan standard perlu diikuti. Oleh itu, kami memutuskan untuk mengumpul bekas mengikut bekas - ini adalah rekursi.

Imej sedia pengeluaran untuk k8s

Di sini bekas diwakili oleh garis besar pepejal. Pada masa yang sama, mereka memutuskan untuk meletakkan kit pengedaran di dalamnya supaya "kehidupan tidak kelihatan seperti raspberi." Mengapa ini dilakukan, kami akan menerangkan di bawah.
 
Hasilnya ialah alat binaanβ€”bekas khusus versi yang merujuk versi pengedaran tertentu dan versi skrip tertentu.

Bagaimana kita menggunakannya? Kami mempunyai Hab Docker yang mengandungi bekas. Kami mencerminkannya di dalam sistem kami untuk menyingkirkan kebergantungan luaran. Hasilnya ialah bekas bertanda kuning. Kami mencipta templat untuk memasang semua pengedaran dan skrip yang kami perlukan ke dalam bekas. Selepas itu, kami memasang imej sedia untuk digunakan: pembangun meletakkan kod dan beberapa kebergantungan khas mereka sendiri ke dalamnya. 

Apa yang bagus tentang pendekatan ini? 

  • Pertama, kawalan versi penuh alat binaan - bina versi bekas, skrip dan pengedaran. 
  • Kedua, kami telah mencapai penyeragaman: kami mencipta templat, imej pertengahan dan sedia untuk digunakan dengan cara yang sama. 
  • Ketiga, bekas memberi kita mudah alih. Hari ini kami menggunakan Gitlab, dan esok kami akan bertukar kepada TeamCity atau Jenkins dan kami akan dapat menjalankan kontena kami dengan cara yang sama. 
  • Keempat, meminimumkan kebergantungan. Bukan kebetulan kami meletakkan kit pengedaran di dalam bekas, kerana ini membolehkan kami mengelak daripada memuat turunnya dari Internet setiap kali. 
  • Kelima, kelajuan binaan telah meningkat - kehadiran salinan imej tempatan membolehkan anda mengelak daripada membuang masa untuk memuat turun, kerana terdapat imej tempatan. 

Dalam erti kata lain, kami telah mencapai proses pemasangan terkawal dan fleksibel. Kami menggunakan alatan yang sama untuk membina mana-mana bekas versi penuh. 

Bagaimana prosedur binaan kami berfungsi

Imej sedia pengeluaran untuk k8s

Perhimpunan dilancarkan dengan satu arahan, proses itu dilaksanakan dalam imej (diserlahkan dalam warna merah). Pembangun mempunyai fail Docker (diserlahkan dalam warna kuning), kami memberikannya, menggantikan pembolehubah dengan nilai. Dan sepanjang perjalanan kami menambah pengepala dan pengaki - ini adalah ejen kami. 

Pengepala menambah pengedaran daripada imej yang sepadan. Dan footer memasang perkhidmatan kami di dalam, mengkonfigurasi pelancaran beban kerja, pengelogan dan ejen lain, menggantikan titik masuk, dsb. 

Imej sedia pengeluaran untuk k8s

Kami berfikir untuk masa yang lama sama ada untuk memasang penyelia. Akhirnya, kami memutuskan bahawa kami memerlukannya. Kami memilih S6. Penyelia menyediakan pengurusan kontena: membolehkan anda menyambung kepadanya jika proses utama ranap dan menyediakan pengurusan kontena secara manual tanpa menciptanya semula. Log dan metrik ialah proses yang berjalan di dalam bekas. Mereka juga perlu dikawal entah bagaimana, dan kami melakukan ini dengan bantuan penyelia. Akhirnya, S6 menjaga pengemasan, pemprosesan isyarat dan tugas-tugas lain.

Memandangkan kami menggunakan sistem orkestrasi yang berbeza, selepas membina dan menjalankan, bekas mesti memahami persekitarannya dan bertindak mengikut situasi. Sebagai contoh:
Ini membolehkan kami membina satu imej dan menjalankannya dalam sistem orkestrasi yang berbeza, dan ia akan dilancarkan dengan mengambil kira spesifikasi sistem orkestrasi ini.

 Imej sedia pengeluaran untuk k8s

Untuk bekas yang sama kami mendapat pepohon proses yang berbeza dalam Docker dan Kubernetes:

Imej sedia pengeluaran untuk k8s

Muatan dilaksanakan di bawah pengawasan S6. Beri perhatian kepada pengumpul dan acara - ini adalah ejen kami yang bertanggungjawab untuk log dan metrik. Kubernetes tidak mempunyainya, tetapi Docker mempunyainya. kenapa? 

Jika kita melihat spesifikasi "pod" (selepas ini - pod Kubernetes), kita akan melihat bahawa bekas acara dilaksanakan dalam pod, yang mempunyai bekas pengumpul berasingan yang menjalankan fungsi mengumpul metrik dan log. Kita boleh menggunakan keupayaan Kubernetes: menjalankan bekas dalam satu pod, dalam satu proses dan/atau ruang rangkaian. Sebenarnya perkenalkan ejen anda dan laksanakan beberapa fungsi. Dan jika bekas yang sama dilancarkan di Docker, ia akan menerima semua keupayaan yang sama seperti output, iaitu, ia akan dapat menyampaikan log dan metrik, kerana ejen akan dilancarkan secara dalaman. 

Metrik dan log

Menyampaikan metrik dan log adalah tugas yang kompleks. Terdapat beberapa aspek dalam keputusannya.
Infrastruktur dicipta untuk melaksanakan muatan, dan bukan untuk penghantaran besar-besaran log. Iaitu, proses ini mesti dilakukan dengan keperluan sumber kontena yang minimum. Kami berusaha untuk membantu pembangun kami: "Dapatkan bekas Docker Hub, jalankan dan kami boleh menghantar log." 

Aspek kedua ialah mengehadkan jumlah log. Jika lonjakan dalam jumlah log berlaku dalam beberapa bekas (aplikasi mengeluarkan surih tindanan dalam gelung), beban pada CPU, saluran komunikasi dan sistem pemprosesan log meningkat, dan ini menjejaskan operasi hos sebagai keseluruhan dan bekas lain pada hos, maka kadangkala ini membawa kepada "kejatuhan" hos. 

Aspek ketiga ialah adalah perlu untuk menyokong sebanyak mungkin kaedah pengumpulan metrik di luar kotak. Daripada membaca fail dan mengundi Prometheus-endpoint kepada menggunakan protokol khusus aplikasi.

Dan aspek terakhir adalah untuk meminimumkan penggunaan sumber.

Kami memilih penyelesaian Go sumber terbuka yang dipanggil Telegraf. Ini ialah penyambung universal yang menyokong lebih daripada 140 jenis saluran input (pemalam input) dan 30 jenis saluran output (pemalam output). Kami telah memuktamadkannya dan kini kami akan memberitahu anda cara kami menggunakannya menggunakan Kubernetes sebagai contoh. 

Imej sedia pengeluaran untuk k8s

Katakan pembangun menggunakan beban kerja dan Kubernetes menerima permintaan untuk membuat pod. Pada ketika ini, bekas yang dipanggil Collector dicipta secara automatik untuk setiap pod (kami menggunakan webhook mutasi). Pengumpul adalah ejen kami. Pada permulaannya, bekas ini mengkonfigurasi dirinya untuk berfungsi dengan Prometheus dan sistem pengumpulan log.

  • Untuk melakukan ini, ia menggunakan anotasi pod, dan bergantung pada kandungannya, mencipta, katakan, titik akhir Prometheus; 
  • Berdasarkan spesifikasi pod dan tetapan bekas tertentu, ia memutuskan cara untuk menghantar log.

Kami mengumpul log melalui API Docker: pembangun hanya perlu meletakkannya dalam stdout atau stderr, dan Pemungut akan menyusunnya. Log dikumpul dalam ketulan dengan sedikit kelewatan untuk mengelakkan kemungkinan lebihan hos. 

Metrik dikumpulkan merentas kejadian (proses) beban kerja dalam bekas. Semuanya ditag: ruang nama, di bawah, dan seterusnya, dan kemudian ditukar kepada format Prometheus - dan tersedia untuk koleksi (kecuali untuk log). Kami juga menghantar log, metrik dan acara kepada Kafka dan seterusnya:

  • Log tersedia dalam Graylog (untuk analisis visual);
  • Log, metrik, acara dihantar ke Clickhouse untuk simpanan jangka panjang.

Semuanya berfungsi sama dalam AWS, cuma kami menggantikan Graylog dengan Kafka dengan Cloudwatch. Kami menghantar log ke sana, dan semuanya ternyata sangat mudah: ia serta-merta jelas yang mana kluster dan bekas mereka. Perkara yang sama berlaku untuk Google Stackdriver. Iaitu, skim kami berfungsi di premis dengan Kafka dan di awan. 

Jika kami tidak mempunyai Kubernetes dengan pod, skema ini sedikit lebih rumit, tetapi ia berfungsi pada prinsip yang sama.

Imej sedia pengeluaran untuk k8s

Proses yang sama dilaksanakan di dalam bekas, ia diatur menggunakan S6. Semua proses yang sama berjalan di dalam bekas yang sama.

Hasilnya,

Kami telah mencipta penyelesaian lengkap untuk membina dan melancarkan imej, dengan pilihan untuk mengumpul dan menghantar log dan metrik:

  • Kami membangunkan pendekatan piawai untuk memasang imej, dan berdasarkannya kami membangunkan templat CI;
  • Ejen pengumpulan data ialah sambungan Telegraf kami. Kami menguji mereka dengan baik dalam pengeluaran;
  • Kami menggunakan webhook mutasi untuk melaksanakan bekas dengan ejen dalam pod; 
  • Disepadukan ke dalam ekosistem Kubernetes/Rancher;
  • Kami boleh melaksanakan bekas yang sama dalam sistem orkestrasi yang berbeza dan mendapatkan hasil yang kami harapkan;
  • Mencipta konfigurasi pengurusan kontena yang dinamik sepenuhnya. 

Pengarang bersama: Ilya Prudnikov

Sumber: www.habr.com

Tambah komen