Monorepositories: sila, mesti

Monorepositories: sila, mesti

Terjemahan artikel yang disediakan untuk pelajar kursus "Amalan dan alatan DevOps" dalam projek pendidikan OTUS.

Anda harus memilih monorepositori kerana tingkah laku yang dipromosikan dalam pasukan anda adalah ketelusan dan tanggungjawab bersama, terutamanya apabila pasukan berkembang. Sama ada cara, anda perlu melabur dalam perkakasan, tetapi sentiasa lebih baik jika tingkah laku lalai ialah tingkah laku yang anda inginkan dalam arahan anda.

Mengapa kita bercakap tentang ini?

Matt Klein menulis artikel itu "Monorepos: Tolong jangan!"  (nota penterjemah: terjemahan pada Habré “Monorepositori: tolong jangan”). Saya suka Matt, saya rasa dia sangat bijak dan anda harus membaca pandangannya. Dia pada asalnya menyiarkan tinjauan pendapat di Twitter:

Monorepositories: sila, mesti

Terjemahan:
Hari Tahun Baru ini, saya akan berhujah tentang betapa tidak masuk akalnya monorepositori. 2019 bermula dengan tenang. Atas semangat ini, saya menawarkan tinjauan kepada anda. Siapa fanatik besar? Penyokong:
- Monorepo
- Rust
- Tinjauan yang salah / kedua-duanya

Jawapan saya ialah, "Saya benar-benar kedua-dua orang itu." Daripada bercakap tentang bagaimana Rust adalah dadah, mari kita lihat mengapa saya fikir dia salah tentang monorepositori. Sedikit tentang diri anda. Saya ialah CTO Perisian Chef. Kami mempunyai kira-kira 100 jurutera, asas kod sejak kira-kira 11-12 tahun, dan 4 produk utama. Sebahagian daripada kod ini berada dalam polyrepository (kedudukan permulaan saya), sesetengahnya berada dalam monorepository (kedudukan semasa saya).

Sebelum saya mula: setiap hujah yang saya buat di sini akan digunakan untuk kedua-dua jenis repositori. Pada pendapat saya, tidak ada sebab teknikal mengapa anda harus memilih satu jenis repositori berbanding yang lain. Anda boleh membuat apa-apa pendekatan berfungsi. Saya gembira untuk bercakap mengenainya, tetapi saya tidak berminat dengan sebab teknikal tiruan mengapa satu lebih unggul daripada yang lain.

Saya bersetuju dengan bahagian pertama perkara Matt:

Kerana pada skala, monorepositori akan menyelesaikan semua masalah yang sama yang diselesaikan oleh polyrepository, tetapi pada masa yang sama memaksa anda untuk menggabungkan kod anda dengan ketat dan memerlukan usaha yang luar biasa untuk meningkatkan kebolehskalaan sistem kawalan versi anda.

Anda perlu menyelesaikan masalah yang sama tanpa mengira sama ada anda memilih monorepositori atau polyrepository. Bagaimana anda mengeluarkan keluaran? Apakah pendekatan anda terhadap kemas kini? Keserasian ke belakang? Kebergantungan projek silang? Apakah gaya seni bina yang boleh diterima? Bagaimanakah anda mengurus infrastruktur binaan dan ujian anda? Senarai itu tidak berkesudahan. Dan anda akan menyelesaikan semuanya semasa anda berkembang. Tiada keju percuma.

Saya rasa hujah Matt adalah serupa dengan pandangan yang dikongsi oleh ramai jurutera (dan pengurus) yang saya hormati. Ini berlaku dari perspektif jurutera yang bekerja pada komponen atau pasukan yang bekerja pada komponen. Anda mendengar perkara seperti:

  • Pangkalan kod adalah besar - saya tidak memerlukan semua sampah ini.
  • Lebih sukar untuk menguji kerana saya perlu menguji semua sampah ini yang saya tidak perlukan.
  • Lebih sukar untuk bekerja dengan kebergantungan luar.
  • Saya memerlukan sistem kawalan versi maya saya sendiri.

Sudah tentu, semua perkara ini adalah wajar. Ini berlaku dalam kedua-dua kes - dalam polyrepository saya mempunyai sampah saya sendiri, sebagai tambahan kepada yang diperlukan untuk binaan... Saya juga mungkin memerlukan sampah lain. Jadi saya "hanya" mencipta alat yang menyemak keseluruhan projek. Atau saya mencipta monorepositori palsu dengan submodul. Kami boleh berjalan di sekitar ini sepanjang hari. Tetapi saya fikir hujah Matt merindui sebab utama, yang saya balikkan dengan sangat banyak memihak kepada monorepositori:

Ia mencetuskan komunikasi dan menunjukkan masalah

Apabila kami memisahkan repositori, kami mewujudkan masalah penyelarasan dan ketelusan de facto. Ini sepadan dengan cara kita berfikir tentang pasukan (terutamanya cara ahli individu berfikir tentang mereka): kita bertanggungjawab untuk komponen tertentu. Kami bekerja secara relatif terpencil. Sempadan ditetapkan pada pasukan saya dan komponen yang sedang kami usahakan.

Memandangkan seni bina menjadi lebih kompleks, satu pasukan tidak lagi boleh menguruskannya sendirian. Sangat sedikit jurutera yang mempunyai keseluruhan sistem dalam kepala mereka. Katakan anda mengurus komponen kongsi A yang digunakan oleh Pasukan B, C dan D. Pasukan A sedang memfaktorkan semula, menambah baik API dan juga mengubah pelaksanaan dalaman. Akibatnya, perubahan tidak serasi ke belakang. Apa nasihat yang anda ada?

  • Cari semua tempat di mana API lama digunakan.
  • Adakah terdapat tempat di mana API baharu tidak boleh digunakan?
  • Bolehkah anda membaiki dan menguji komponen lain untuk memastikan ia tidak pecah?
  • Bolehkah pasukan ini menguji perubahan anda sekarang?

Sila ambil perhatian bahawa soalan ini adalah bebas daripada jenis repositori. Anda perlu mencari pasukan B, C dan D. Anda perlu bercakap dengan mereka, mengetahui masa, memahami keutamaan mereka. Sekurang-kurangnya kami berharap anda akan melakukannya.

Tiada siapa yang benar-benar mahu melakukan ini. Ini adalah lebih kurang menyeronokkan daripada hanya membetulkan API sialan. Semuanya manusia dan tidak kemas. Dalam polyrepository, anda hanya boleh membuat perubahan, berikan kepada orang yang bekerja pada komponen itu (mungkin bukan B, C atau D) untuk semakan, dan teruskan. Pasukan B, C dan D hanya boleh kekal dengan versi semasa mereka buat masa ini. Mereka akan diperbaharui apabila mereka menyedari genius anda!

Dalam monorepositori, tanggungjawab dialihkan secara lalai. Pasukan A menukar komponen mereka dan, jika tidak berhati-hati, segera memecahkan B, C dan D. Ini membawa kepada B, C dan D muncul di pintu A, tertanya-tanya mengapa Pasukan A memecahkan perhimpunan. Ini mengajar A bahawa mereka tidak boleh melangkau senarai saya di atas. Mereka mesti bercakap tentang apa yang mereka akan lakukan. Bolehkah B, C dan D bergerak? Bagaimana jika B dan C boleh, tetapi D berkait rapat dengan kesan sampingan kelakuan algoritma lama?

Kemudian kita perlu bercakap tentang bagaimana kita akan keluar dari situasi ini:

  1. Sokongan untuk berbilang API dalaman dan akan menandakan algoritma lama sebagai ditamatkan sehingga D boleh berhenti menggunakannya.
  2. Sokongan untuk berbilang versi keluaran, satu dengan antara muka lama, satu dengan yang baharu.
  3. Tangguhkan pelepasan perubahan A sehingga B, C dan D boleh menerimanya secara serentak.

Katakan kami telah memilih 1, beberapa API. Dalam kes ini kita mempunyai dua keping kod. Lama dan baru. Agak selesa dalam beberapa situasi. Kami menyemak semula kod lama, menandainya sebagai tidak digunakan dan bersetuju dengan jadual pengalihan keluar dengan pasukan D. Pada asasnya sama untuk repositori poli dan mono.

Untuk mengeluarkan berbilang versi, kami memerlukan cawangan. Sekarang kita mempunyai dua komponen - A1 dan A2. Pasukan B dan C menggunakan A2 dan D menggunakan A1. Kami memerlukan setiap komponen bersedia untuk dikeluarkan kerana kemas kini keselamatan dan pembetulan pepijat lain mungkin diperlukan sebelum D boleh bergerak ke hadapan. Dalam polyrepository, kita boleh menyembunyikan ini dalam cawangan berumur panjang yang terasa baik. Dalam monorepositori, kami memaksa kod dibuat dalam modul baharu. Pasukan D masih perlu membuat perubahan pada komponen "lama". Semua orang boleh melihat kos yang kami bayar di sini - kami kini mempunyai kod dua kali ganda lebih banyak, dan sebarang pembetulan pepijat yang digunakan untuk A1 dan A2 mesti dikenakan kepada kedua-duanya. Dengan pendekatan cawangan dalam polyrepository, ini tersembunyi di sebalik ceri-pick. Kami menganggap kos lebih rendah kerana tiada pertindihan. Dari sudut pandangan praktikal, kosnya adalah sama: anda akan membina, mengeluarkan dan mengekalkan dua pangkalan kod yang hampir sama sehingga anda boleh memadamkan salah satu daripadanya. Perbezaannya ialah dengan monorepository kesakitan ini secara langsung dan kelihatan. Ini lebih teruk, dan itu bagus.

Akhirnya, kami sampai ke titik ketiga. Pelepasan kelewatan. Ada kemungkinan perubahan yang dibuat oleh A akan meningkatkan kehidupan Pasukan A. Penting, tetapi tidak mendesak. Bolehkah kita menunda? Dalam polyrepository, kami menolak ini untuk menyematkan artifak. Sudah tentu kami memberitahu ini kepada Pasukan D. Hanya kekal pada versi lama sehingga anda mengejar ketinggalan! Ini membuatkan anda bersedia untuk bermain pengecut. Pasukan A terus mengusahakan komponen mereka, mengabaikan fakta bahawa Pasukan D menggunakan versi yang semakin ketinggalan zaman (itulah masalah Pasukan D, mereka bodoh). Sementara itu, Pasukan D bercakap buruk tentang sikap cuai Pasukan A terhadap kestabilan kod, jika mereka bercakap mengenainya sama sekali. Bulan berlalu. Akhirnya, Pasukan D memutuskan untuk melihat kemungkinan mengemas kini, tetapi A hanya mempunyai lebih banyak perubahan. Pasukan A hampir tidak ingat bila atau bagaimana mereka memecahkan D. Peningkatan lebih menyakitkan dan akan mengambil masa yang lebih lama. Yang menghantarnya lebih jauh ke bawah timbunan keutamaan. Sehingga hari kami mempunyai isu keselamatan di A yang memaksa kami membuat cawangan. Pasukan A mesti kembali ke masa lalu, mencari titik apabila D stabil, menyelesaikan masalah di sana dan menyediakannya untuk dilepaskan. Ini adalah pilihan de facto yang dibuat orang, dan ia adalah yang paling teruk. Nampaknya bagus untuk kedua-dua Pasukan A dan Pasukan D selagi kita boleh mengabaikan satu sama lain.

Dalam monorepositori, yang ketiga sebenarnya bukan pilihan. Anda terpaksa menangani situasi itu dalam satu daripada dua cara. Anda perlu melihat kos untuk mempunyai dua cawangan keluaran. Belajar untuk melindungi diri anda daripada kemas kini yang memecahkan keserasian ke belakang. Tetapi yang paling penting: anda tidak boleh mengelak daripada mengadakan perbualan yang sukar.

Dalam pengalaman saya, apabila pasukan menjadi besar, tidak mungkin lagi untuk mengingati keseluruhan sistem, dan itulah bahagian yang paling penting. Anda mesti meningkatkan keterlihatan perselisihan dalam sistem. Anda mesti berusaha secara aktif untuk mendapatkan pasukan supaya menjauhkan diri daripada komponen mereka dan melihat kerja pasukan dan pengguna lain.

Ya, anda boleh mencipta alat yang cuba menyelesaikan masalah polyrepository. Tetapi pengalaman saya mengajar penyampaian dan automasi berterusan dalam perusahaan besar memberitahu saya perkara ini: gelagat lalai tanpa menggunakan alat tambahan ialah gelagat yang anda harapkan untuk dilihat. Tingkah laku lalai polyrepository ialah pengasingan, itulah intinya. Tingkah laku lalai monorepositori ialah tanggungjawab dan ketelusan bersama, itulah intinya. Dalam kedua-dua kes, saya akan mencipta alat yang akan melicinkan tepi kasar. Sebagai seorang pemimpin, saya akan memilih monorepositori setiap kali kerana alatan itu perlu mengukuhkan budaya yang saya inginkan, dan budaya datang daripada keputusan kecil dan kerja harian pasukan.

Hanya pengguna berdaftar boleh mengambil bahagian dalam tinjauan. Log masuk, Sama-sama.

Siapa fanatik terbesar? Penyokong:

  • Monorepo

  • Rust

  • Tinjauan yang salah / kedua-duanya

33 pengguna telah mengundi. 13 pengguna berpantang.

Sumber: www.habr.com

Tambah komen