器開發仍然要考慮 Linux 發行版嗎?

容器構建有兩大趨勢:使用基本鏡像和從頭開始構建。每個都有工程上的權衡。

有人說 Linux 發行版不再與容器有關。像 distroless 和 scratch 容器等可替代的方法,似乎是風靡一時。看來,我們在考慮和做出技術決策時,更多的是基於時尚感和即時的情感滿足,而不是考慮我們選擇的次要影響。我們應該問這樣的問題:這些選擇將如何影響未來六個月的維護?工程權衡是什麼?這種範式轉換如何影響我們的大規模構建系統?

這真讓人沮喪。如果我們忘記了工程是一個零和遊戲,有可衡量的利弊權衡,有不同方法的成本和收益 —— 這樣對我們自己不利,對僱主不利,對最終維護我們的代碼的同事不利。最後,我們對所有的維護人員(向維護人員致敬! )都是一種傷害,因爲我們不欣賞他們所做的工作。

理解問題所在

爲了理解這個問題,我們必須首先研究爲什麼我們使用 Linux 發行版。我將把原因分爲兩大類:內核和其他包。編譯內核實際上相當容易。Slackware 和 Gentoo( 我的小心臟還是有點害怕)教會了我們這一點。

另一方面,對於一個可用的 Linux 系統需要打包大量的開發軟件和應用軟件,這可能會讓人望而生畏。此外,確保數百萬個程序包可以一起安裝和工作的唯一方法是使用舊的範例:即編譯它並將它作爲一個工件(即 Linux 發行版)一起發佈。那麼,爲什麼 Linux 發行版要將內核和所有包一起編譯呢?很簡單:確保事情協調一致。

首先,我們來談談內核。內核很特別。在沒有編譯好的內核的情況下引導 Linux 系統有點困難。它是 Linux 操作系統的核心,也是我們在系統啓動時首先依賴的。內核在編譯時有很多不同的配置選項,這些選項會對硬件和軟件如何在一個內核上運行產生巨大影響。這方面中的第二個問題是,系統軟件(如編譯器 、C 庫和解釋器)必須針對內核中內置的選項進行調優。Gentoo 的維基以一種發自內心的方式教我們這一點,它把每個人都變成了一個微型的開發版維護者。

令人尷尬的是(因爲我在過去五年裏一直在使用容器),我必須承認我最近才編譯過內核。我必須讓嵌套的 KVM 在 RHEL7 上工作,這樣我才能在筆記本電腦上的 KVM 虛擬機中運行 OpenShift on OpenStack 虛擬機,以及我的 Container Development Kit(CDK)。我只想說,當時我在一個全新的 4.X 內核上啓動了 RHEL7。和任何優秀的系統管理員一樣,我有點擔心自己錯過了一些重要的配置選項和補丁。當然,我也的確錯過了一些東西。比如睡眠模式無法正常工作,我的擴展底座無法正常工作,還有許多其他小的隨機錯誤。但它在我的筆記本電腦上的一個 KVM 虛擬機上,對於 OpenStack 上的 OpenShift 的實時演示來說已經足夠好了。來吧,這很有趣,對吧?但我離題了……

現在,我們來談談其他的軟件包。雖然內核和相關的系統軟件可能很難編譯,但從工作負載的角度來看,更大的問題是編譯成千上萬的包,以提供一個可用的 Linux 系統。每個軟件包都需要專業知識。有些軟件只需要運行三個命令:./configuremake 和 make install。另一些則需要大量的專業知識,從在 etc 中添加用戶和配置特定的默認值到運行安裝後腳本和添加 systemd 單元文件。對於任何一個人來說,調試好你可能用得到的成千上萬種不同軟件所需要的一套技能都是令人望而生畏的。但是,如果你想要一個可以隨時嘗試新軟件的可用系統,你必須學會如何編譯和安裝新軟件,然後才能開始學習使用它。這就是沒有 Linux 發行版的 Linux。當你放棄使用 Linux 發行版時,那麼你就得自己編譯軟件。

關鍵是,你必須將所有內容構建在一起,以確保它能夠以任何合理的可靠性級別協同工作,而且構建一個可用的包羣需要大量的知識。這是任何一個開發人員或系統管理員都無法合理地學習和保留的知識。我描述的每個問題都適用於你的 容器主機(內核和系統軟件)和 容器鏡像(系統軟件和所有其他包)——請注意:在容器鏡像中還包含有編譯器 、C 庫、解釋器和 JVM。

解決方案

所以你也看到了,其實使用 Linux 發行版就是解決方案。別再看了,給離你最近的軟件包維護者(再次向維護人員致敬!)發張電子卡吧(等等,我是不是把我的年齡告訴別人了?)。不過說真的,這些人做了大量的工作,這真的是被低估了。Kubernetes、Istio、Prometheus,還有 Knative:我在看着你們。你們的時代要來了,到時候你們會進入維護模式,被過度使用,被低估。大約七到十年後,我將再次寫這篇文章,可能是關於 Kubernetes 的。

容器構建的首要原則

從零開始構建和從基礎鏡像構建之間存在權衡。

從基礎鏡像構建

從基礎鏡像構建的優點是,大多數構建操作只不過是安裝或更新包。它依賴於 Linux 發行版中包維護人員所做的大量工作。它還有一個優點,即六個月甚至十年後的修補事件(使用 RHEL)是運維/系統管理員事件 (yum update),而不是開發人員事件(這需要通過代碼找出某些函數參數不再工作的原因)。

你想想,應用程序代碼依賴於許多庫,從 JSON mung 庫到對象關係映射器。與 Linux 內核和 Glibc 不同,這些類型的庫很少改變 API 兼容性。這意味着三年後你的修補事件可能會變成代碼更改事件,而不是 yum 更新事件。因此讓他自己深入下去吧。開發人員,如果安全團隊找不到防火牆黑客來阻止攻擊,你將在凌晨 2 點收到短信。

從基礎鏡像構建不是完美的;還有一些缺點,比如所有被拖入的依賴項的大小。這幾乎總是會使容器鏡像比從頭開始構建的鏡像更大。另一個缺點是你並不總是能夠訪問最新的上游代碼。這可能會讓開發人員感到沮喪,尤其是當你只想使用依賴項中的一部分功能時,但是你仍然不得不將你根本用不着的東西一起打包帶走,因爲上游的維護人員一直在改變這個庫。

如果你是一個 web 開發人員,正在對我翻白眼,我有一個詞可以形容你:DevOps。那意味着你帶着尋呼機,我的朋友。

Scratch 構建

Scratch 構建的優點是鏡像非常小。當你不依賴容器中的 Linux 發行版時,你有很多控制權,這意味着你可以根據需要定製所有內容。這是一個最佳模型,在某些用例中是很有效的。另一個優勢是你可以訪問最新的軟件包。你不必等待 Linux 發行版更新任何內容。是你自己在控制,所以你可以自行選擇什麼時候去費功夫納入新的軟件。

記住,控制一切都是有代價的。通常,更新到具有新特性的新庫會拖如不必要的 API 更改,這意味着修復代碼中的不兼容(換句話說,這就像給犛牛剪毛)。在凌晨 2 點應用程序不起作用的時候給犛牛剪毛是不好玩的。幸運的是,使用容器,你可以在下一個工作日回滾並給犛牛剪毛,但它仍會佔用你爲業務提供新價值、爲應用程序提供新功能的時間。歡迎來到系統管理員的生活。

好吧,也就是說,有些時候,Scratch 構建是有意義的。我完全承認,靜態編譯的 Golang 程序和 C 程序是 scratch/distorless 構建的兩個不錯的候選程序。對於這些類型的程序,每個容器構建都是一個編譯事件。三年後你仍然需要擔心 API 的損壞,但是如果你是一個 Golang 商店,你應該有能力隨着時間的推移修復問題。

結論

基本上,Linux 發行版做了大量工作來節省你在常規 Linux 系統或容器上的時間。維護人員所擁有的知識是巨大的,而且沒有得到真正的讚賞。容器的採用使得問題更加嚴重,因爲它被進一步抽象了。

通過容器主機,Linux 發行版可以讓你訪問廣泛的硬件生態系統,從微型 ARM 系統到 128 核 CPU x86 巨型機箱,再到雲服務商的虛擬機。他們提供可工作的容器引擎和開箱即用的容器運行時環境,所以你只需啓動你的容器,讓其他人擔心事情的進展。

對於容器鏡像,Linux 發行版爲你的項目提供了對大量軟件的輕鬆訪問。即使你從頭開始構建,你也可能會看到一個包維護人員是如何構建和運送東西的 —— 一個好的藝術家是一個好的偷學者,所以不要低估這項工作的價值。

所以,感謝 Fedora、RHEL(Frantisek,你是我的英雄 )、Debian、Gentoo 和其他 Linux 發行版的所有維護人員。我很感激你所做的工作,儘管我是個“容器工人”


via: https://opensource.com/article/19/2/linux-distributions-still-matter-containers

作者:Scott McCarty 選題:lujun9972 譯者:Chao-zhi 校對:wxy

本文由 LCTT 原創編譯,Linux中國 榮譽推出



發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章