歡迎光臨
每天分享高質量文章

為什麼 Kubernetes 很酷 | Linux 中國

在我剛開始學習 Kubernetes(大約是一年半以前吧?)時,我真的不明白為什麼應該去關註它。 在我使用 Kubernetes 全職工作了三個多月後,我才逐漸明白了為什麼我應該使用它。
— Julia Evans


本文導航
編譯自 | https://jvns.ca/blog/2017/10/05/reasons-kubernetes-is-cool/ 
 作者 | Julia Evans
 譯者 | qhwdw

在我剛開始學習 Kubernetes(大約是一年半以前吧?)時,我真的不明白為什麼應該去關註它。

在我使用 Kubernetes 全職工作了三個多月後,我才逐漸明白了為什麼我應該使用它。(我距離成為一個 Kubernetes 專家還很遠!)希望這篇文章對你理解 Kubernetes 能做什麼會有幫助!

我將嘗試去解釋我對 Kubernetes 感興趣的一些原因,而不去使用 “原生雲cloud native”、“編排系統orchestration”、“容器container”,或者任何 Kubernetes 專用的術語 :)。我去解釋的這些觀點主要來自一位 Kubernetes 操作者/基礎設施工程師,因為,我現在的工作就是去配置 Kubernetes 和讓它工作的更好。

我不會去嘗試解決一些如 “你應該在你的生產系統中使用 Kubernetes 嗎?”這樣的問題。那是非常複雜的問題。(不僅是因為“生產系統”根據你的用途而總是有不同的要求)

Kubernetes 可以讓你無需設置一臺新的服務器即可在生產系統中運行代碼

我首次被說教使用 Kubernetes 是與我的伙伴 Kamal 的下麵的談話:

大致是這樣的:

◈ Kamal: 使用 Kubernetes 你可以通過一條命令就能設置一臺新的服務器。
◈ Julia: 我覺得不太可能吧。
◈ Kamal: 像這樣,你寫一個配置檔案,然後應用它,這時候,你就在生產系統中運行了一個 HTTP 服務。
◈ Julia: 但是,現在我需要去創建一個新的 AWS 實體,明確地寫一個 Puppet 清單,設置服務發現,配置負載均衡,配置我們的部署軟體,並且確保 DNS 正常工作,如果沒有什麼問題的話,至少在 4 小時後才能投入使用。
◈ Kamal: 是的,使用 Kubernetes 你不需要做那麼多事情,你可以在 5 分鐘內設置一臺新的 HTTP 服務,並且它將自動運行。只要你的集群中有空閑的資源它就能正常工作!
◈ Julia: 這兒一定是一個“坑”。

這裡有一種陷阱,設置一個生產用 Kubernetes 集群(在我的經險中)確實並不容易。(查看 Kubernetes 艱難之旅[1] 中去開始使用時有哪些複雜的東西)但是,我們現在並不深入討論它。

因此,Kubernetes 第一個很酷的事情是,它可能使那些想在生產系統中部署新開發的軟體的方式變得更容易。那是很酷的事,而且它真的是這樣,因此,一旦你使用一個運作中的 Kubernetes 集群,你真的可以僅使用一個配置檔案就在生產系統中設置一臺 HTTP 服務(在 5 分鐘內運行這個應用程式,設置一個負載均衡,給它一個 DNS 名字,等等)。看起來真的很有趣。

對於運行在生產系統中的代碼,Kubernetes 可以提供更好的可見性和可管理性

在我看來,在理解 etcd 之前,你可能不會理解 Kubernetes 的。因此,讓我們先討論 etcd!

想像一下,如果現在我這樣問你,“告訴我你運行在生產系統中的每個應用程式,它運行在哪台主機上?它是否狀態很好?是否為它分配了一個 DNS 名字?”我並不知道這些,但是,我可能需要到很多不同的地方去查詢來回答這些問題,並且,我需要花很長的時間才能搞定。我現在可以很確定地說不需要查詢,僅一個 API 就可以搞定它們。

在 Kubernetes 中,你的集群的所有狀態 – 運行中的應用程式 (“pod”)、節點、DNS 名字、 cron 任務、 等等 —— 都儲存在一個單一的資料庫中(etcd)。每個 Kubernetes 組件是無狀態的,並且基本是通過下列方式工作的:

◈ 從 etcd 中讀取狀態(比如,“分配給節點 1 的 pod 串列”)
◈ 產生變化(比如,“在節點 1 上運行 pod A”)
◈ 更新 etcd 中的狀態(比如,“設置 pod A 的狀態為 ‘running’”)

這意味著,如果你想去回答諸如 “在那個可用區中有多少台運行著 nginx 的 pod?” 這樣的問題時,你可以通過查詢一個統一的 API(Kubernetes API)去回答它。並且,你可以在每個其它 Kubernetes 組件上運行那個 API 去進行同樣的訪問。

這也意味著,你可以很容易地去管理每個運行在 Kubernetes 中的任何東西。比如說,如果你想要:

◈ 部署實現一個複雜的定製的部署策略(部署一個東西,等待 2 分鐘,部署 5 個以上,等待 3.7 分鐘,等等)
◈ 每當推送到 github 上一個分支,自動化 啟動一個新的 web 服務器[2]
◈ 監視所有你的運行的應用程式,確保它們有一個合理的記憶體使用限制。

這些你只需要寫一個程式與 Kubernetes API(“controller”)通訊就可以了。

另一個關於 Kubernetes API 的令人激動的事情是,你不會局限於 Kubernetes 所提供的現有功能!如果對於你要部署/創建/監視的軟體有你自己的方案,那麼,你可以使用 Kubernetes API 去寫一些代碼去達到你的目的!它可以讓你做到你想做的任何事情。

即便每個 Kubernetes 組件都“掛了”,你的代碼將仍然保持運行

關於 Kubernetes 我(在各種博客文章中 :))承諾的一件事情是,“如果 Kubernetes API 服務和其它組件‘掛了’也沒事,你的代碼將一直保持運行狀態”。我認為理論上這聽起來很酷,但是我不確定它是否真是這樣的。

到目前為止,這似乎是真的!

我已經斷開了一些正在運行的 etcd,發生了這些情況:

☉ 所有的代碼繼續保持運行狀態
☉ 不能做 新的 事情(你不能部署新的代碼或者生成變更,cron 作業將停止工作)
☉ 當它恢復時,集群將趕上這期間它錯過的內容

這樣做意味著如果 etcd 宕掉,並且你的應用程式的其中之一崩潰或者發生其它事情,在 etcd 恢復之前,它不能夠恢復。

Kubernetes 的設計對 bug 很有彈性

與任何軟體一樣,Kubernetes 也會有 bug。例如,到目前為止,我們的集群控制管理器有記憶體泄漏,並且,調度器經常崩潰。bug 當然不好,但是,我發現 Kubernetes 的設計可以幫助減輕它的許多核心組件中的錯誤的影響。

如果你重啟動任何組件,將會發生:

◈ 從 etcd 中讀取所有的與它相關的狀態
◈ 基於那些狀態(調度 pod、回收完成的 pod、調度 cron 作業、按需部署等等),它會去做那些它認為必須要做的事情

因為,所有的組件並不會在記憶體中保持狀態,你在任何時候都可以重啟它們,這可以幫助你減輕各種 bug 的影響。

例如,如果在你的控制管理器中有記憶體泄露。因為,控制管理器是無狀態的,你可以每小時定期去重啟它,或者,在感覺到可能導致任何不一致的問題發生時重啟它。又或者,在調度器中遇到了一個 bug,它有時忘記了某個 pod,從來不去調度它們。你可以每隔 10 分鐘來重啟調度器來緩減這種情況。(我們並不會這麼做,而是去修複這個 bug,但是,你可以這樣做 :))

因此,我覺得即使在它的核心組件中有 bug,我仍然可以信任 Kubernetes 的設計可以讓我確保集群狀態的一致性。並且,總在來說,隨著時間的推移軟體質量會提高。唯一你必須去操作的有狀態的東西就是 etcd。

不用過多地討論“狀態”這個東西 —— 而我認為在 Kubernetes 中很酷的一件事情是,唯一需要去做備份/恢復計劃的東西是 etcd (除非為你的 pod 使用了持久化儲存的捲)。我認為這樣可以使 Kubernetes 運維比你想的更容易一些。

在 Kubernetes 之上實現新的分佈式系統是非常容易的

假設你想去實現一個分佈式 cron 作業調度系統!從零開始做工作量非常大。但是,在 Kubernetes 裡面實現一個分佈式 cron 作業調度系統是非常容易的!(仍然沒那麼簡單,畢竟它是一個分佈式系統)

我第一次讀到 Kubernetes 的 cron 作業控制器的代碼時,我對它是如此的簡單感到由衷高興。去讀讀看,其主要的邏輯大約是 400 行的 Go 代碼。去讀它吧! => cronjob_controller.go[3] <=

cron 作業控制器基本上做的是:

◈ 每 10 秒鐘:

◈ 列出所有已存在的 cron 作業
◈ 檢查是否有需要現在去運行的任務
◈ 如果有,創建一個新的作業物件去調度,並通過其它的 Kubernetes 控制器實際運行它
◈ 清理已完成的作業
◈ 重覆以上工作

Kubernetes 模型是很受限制的(它有定義在 etcd 中的資源樣式,控制器讀取這個資源並更新 etcd),我認為這種相關的固有的/受限制的模型,可以使它更容易地在 Kubernetes 框架中開發你自己的分佈式系統。

Kamal 給我說的是 “Kubernetes 是一個寫你自己的分佈式系統的很好的平臺” ,而不是“ Kubernetes 是一個你可以使用的分佈式系統”,並且,我覺得它真的很有意思。他做了一個 為你推送到 GitHub 的每個分支運行一個 HTTP 服務的系統[2] 的原型。這花了他一個周末的時間,大約 800 行 Go 代碼,我認為它真不可思議!

Kubernetes 可以使你做一些非常神奇的事情(但並不容易)

我一開始就說 “kubernetes 可以讓你做一些很神奇的事情,你可以用一個配置檔案來做這麼多的基礎設施,它太神奇了”。這是真的!

為什麼說 “Kubernetes 並不容易”呢?是因為 Kubernetes 有很多部分,學習怎麼去成功地運營一個高可用的 Kubernetes 集群要做很多的工作。就像我發現它給我了許多抽象的東西,我需要去理解這些抽象的東西才能除錯問題和正確地配置它們。我喜歡學習新東西,因此,它並不會使我發狂或者生氣,但是我認為瞭解這一點很重要 :)

對於 “我不能僅依靠抽象概念” 的一個具體的例子是,我努力學習了許多 Linux 上網絡是如何工作的[4],才讓我對設置 Kubernetes 網絡稍有信心,這比我以前學過的關於網絡的知識要多很多。這種方式很有意思但是非常費時間。在以後的某個時間,我或許寫更多的關於設置 Kubernetes 網絡的困難/有趣的事情。

或者,為了成功設置我的 Kubernetes CA,我寫了一篇 2000 字的博客文章[5],述及了我不得不學習 Kubernetes 不同方式的 CA 的各種細節。

我覺得,像 GKE (Google 的 Kubernetes 產品) 這樣的一些監管的 Kubernetes 的系統可能更簡單,因為,他們為你做了許多的決定,但是,我沒有嘗試過它們。


via: https://jvns.ca/blog/2017/10/05/reasons-kubernetes-is-cool/

作者:Julia Evans[7] 譯者:qhwdw 校對:wxy

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

LCTT 譯者

qhwdw ? ? ? ?
共計翻譯:60 篇
貢獻時間:96 天


推薦文章

< 左右滑動查看相關文章 >

點擊圖片、輸入文章 ID 或識別二維碼直達

赞(0)

分享創造快樂