--- title: Kubernetes tags: Kubernetes --- Kubernetes === ## Kubernetes 是什麼? Kubernetes(K8S)是一個可以幫助我們管理微服務(microservices)的系統,他可以自動化地部署及管理多台機器上的多個容器(Container)。 提供一個平台以較高層次的抽象化去自動化操作與管理容器們。 1. 同時部署多個容器到多台機器上(Deployment) 2. 服務的乘載量有變化時,可以對容器做自動擴展(Scaling) 3. 管理多個容器的狀態,自動偵測並重啟故障的容器(Management) ## 為什麼要使用Kubernetes? 1. service 和 系統部署更方便 由於容器可在任何容器平台運行,因此無論是同時將多個Container部屬到一台機器,或是多個Container部屬至多台機器都不是問題。 2. 自動化管理,重啟、擴張皆可行 且K8s可自動偵測、管理各Container的狀態,若有需要,可對Container執行自動擴展。而若偵測到有Container發生故障,也可自動重啟以確保服務正確且持續地運行。 3. 彈性化運用 K8s中每個服務、系統皆可獨立部屬,因此不會因為其中一個系統出現錯誤而影響整個運作,甚至各Container也可依各自需求來修改,運用上擁有高度彈性化。 4. Kubernetes是一個開源的開發平台,不侷限任何語言與接口. 由此可知,使用K8s不僅可讓你擁有更穩定的Container環境,且透過自動化的管理,也能讓維運更加簡單、有效率。 ## Kubernetes 四元件 ### **Pod** **Kubernetes 運作的最小單位**,一個 Pod 對應到一個應用服務(Application) ,舉例來說一個 Pod 可能會對應到一個 API Server。 * 每個 Pod 都有一個身分證,也就是屬於這個 Pod 的 yaml 檔 * 一個 Pod 裡面可以有一個或是多個 Container,但一般情況一個 Pod 最好只有一個 Container * 同一個 Pod 中的 Containers 共享相同資源及網路,彼此透過 local port number 溝通 ### **Worker Node** **Kubernetes 運作的最小硬體單位**,一個 Worker Node(簡稱 Node)對應到一台機器,可以是實體機如你的筆電、或是虛擬機如 AWS 上的一台 EC2 或 GCP 上的一台 Computer Engine。 每個 Node 中都有三個組件:kubelet、kube-proxy、Container Runtime。 * #### kubelet 該 Node 的管理員,負責管理該 Node 上的所有 Pods 的狀態並負責與 Master 溝通 * #### kube-proxy 該 Node 的傳訊員,負責更新 Node 的 iptables,讓 Kubernetes 中不在該 Node 的其他物件可以得知該 Node 上所有 Pods 的最新狀態 * #### Container Runtime 該 Node 真正負責容器執行的程式,以 Docker 容器為例其對應的 Container Runtime 就是 Docker Engine ### **Master Node** Kubernetes 運作的指揮中心,可以簡化看成一個特化的 Node 負責管理所有其他 Node。一個 Master Node(簡稱 Master)中有四個組件:kube-apiserver、etcd、kube-scheduler、kube-controller-manager。 * #### kube-apiserver * 管理整個 Kubernetes 所需 API 的接口(Endpoint),例如從 Command Line 下 kubectl 指令就會把指令送到這裏 * 負責 Node 之間的溝通橋樑,每個 Node 彼此不能直接溝通,必須要透過 apiserver 轉介 * 負責 Kubernetes 中的請求的身份認證與授權 * #### etcd * 用來存放 Kubernetes Cluster 的資料作為備份,當 Master 因為某些原因而故障時,我們可以透過 etcd 幫我們還原 Kubernetes 的狀態 * #### kube-controller-manager * 負責管理並運行 Kubernetes controller 的組件,簡單來說 controller 就是 Kubernetes 裡一個個負責監視 Cluster 狀態的 Process,例如:Node Controller、Replication Controller * 這些 Process 會在 Cluster 與預期狀態(desire state)不符時嘗試更新現有狀態(current state)。例如:現在要多開一台機器以應付突然增加的流量,那我的預期狀態就會更新成 N+1,現有狀態為 N,這時相對應的 controller 就會想辦法多開一台機器 * controller-manager 的監視與嘗試更新也都需要透過訪問 kube-apiserver 達成 * #### kube-scheduler * 整個 Kubernetes 的 Pods 調度員,scheduler 會監視新建立但還沒有被指定要跑在哪個 Node 上的 Pod,並根據每個 Node 上面資源規定、硬體限制等條件去協調出一個最適合放置的 Node 讓該 Pod 跑 ### **Cluster** Kubernetes 中多個 Node 與 Master 的集合。基本上可以想成在同一個環境裡所有 Node 集合在一起的單位。 **一個cluster 最少需要3個nodes,包含一個master node和兩個worker nodes。** 解釋: Kubernetes keeps all critical data in etcd, which uses a majority to repair when there is a fault. An instance of etcd runs on each master node. Three is the minimum number of etcds one wants backing a prod-level cluster. Hence, three is the minimum number of masters per cluster. ## 基本運作與安裝  ### Kubernetes 是如何建立一個 Pod? 上圖為一個簡易的 Kubernetes Cluster,通常一個 Cluster 中其實會有多個 Master 作為備援,但為了簡化我們只顯示一個。 當使用者要部署一個新的 Pod 到 Kubernetes Cluster 時,使用者要先透過 User Command(kubectl)輸入建立 Pod 的對應指令(下面會在解說如何實際動手操作來建立一個 Pod)。此時指令會經過一層確認使用者身份的認證後,傳遞到 Master Node 中的 API Server,API Server 會把指令備份到 etcd 。 接下來 controller-manager 會從 API Server 收到需要創建一個新的 Pod 的訊息,並檢查如果資源許可,就會建立一個新的 Pod。最後 Scheduler 在定期訪問 API Server 時,會詢問 controller-manager 是否有建置新的 Pod,如果發現新建立的 Pod 時,Scheduler 就會負責把 Pod 配送到最適合的一個 Node 上面。 雖然上面的基本運作看似複雜,但實際上我們在操作時,只要輸入一行指令後 Kubernetes 就會自動幫我們完成後續的動作。 ## kubernetes resources Anything we create in a Kubernetes cluster is considered a resource: deployments, pods, services and more。 我們在Kubernetes cluster中創建的任何東西都被認為是一種資源:deployments、pods、services等等。 * CPU * memory * ephemeral storage 暫存 * extended resources 擴展資源 ### Workloads Workloads是用來管理或是運行 Container,確保正確數量的正確類型的 pod 正在運行。 ## kubernetes storage 提供cluster中的pod長期和臨時儲存的方法. container中的On-disk files是暫存的,這會發生兩種問題: * 當container掛掉文件丟失,kubelet重新啟動容器,但state都被清空 * 在同個pod中的container同時共享文件時 ### storage類型 1. Volumes * volume是共享目錄,可以被 Pod 內的多個container訪問。 * Ephemeral volume具有pod的生命週期,當pod不存在時,Ephemeral volume會被銷毀。 * volumes的壽命比 Pod 中運行的任何 Container 都長,並且數據在 Container 重新啟動時得以保留。 2. Persistent Volumes(PV) * PersistentVolume (PV) 是cluster中由管理員配置的一塊存儲空間。 * persistent volumes存在於pod生命週期之外,不會因為pod被消滅就消失,且數據會在pod重啟的時候還原。 * 它是 Kubernetes 資源的獨立定義。 3. PersistentVolumeClaim (PVC) ## Container Runtime Interface (CRI) CRI 是定義 gRPC 介面,透過一個標準介面與各個 contaienr runtime 解決方案銜接,這個銜接的接口標準就是所謂的 Container Runtime,CRI定義了container和image service接口,因為container運行時與image的生命週期是彼此隔離的,因此需要定義兩個service. ### CRI架構 CRI gRPC Server,包括RuntimeService和ImageService.該gRPC Service需要監聽本地的Unix socket,而kubelet則作為gRPC Client運行。  ## Container Network Interface(CNI) CNI就是一個與CRI相當的標準架構,其針對的則是 kubernetes 內的網路功能,CNI 的標準要求 CNI 解決方案需要提供一個執行檔,要能夠接收不同的參數來處理不同的網路生命週期,譬如創建網路,回收網路。 1. 提供 Pod 上網能力,通常都會希望能夠有連接外網的能力。 2. 分配 IP 地址,幫每個 Pod 找一個獨立不重複的 IP,至於是 ipv4 或是 ipv6 都可以。 3. 幫忙實現 Network Policy, kubernetes 內部有 Network Policy 去限制 Pod 與 Pod 之間的網路傳輸,然而 kubernetes 本身只有定義介面,仰賴各個 CNI 去完成。 ## Container Storage Interface(CSI) 將儲存系統與kubernetes這類容器編排系統接觸的標準介面。使用CSI的第三方套件可以撰寫與部署自訂的儲存系統,而無需接觸Kubernetes原始碼。 主要實現三個部分: * Identity Service:用於kubernetes與CSI協調版本訊息 * Controller Service:用於創建、刪除、管理Volume * Node Service:用於將Volume掛載到指定目錄中,以便Kubelet創建container時使用 ## Kubernetes 進階三元件 ### Service Service 就是 Kubernetes 中用來定義「一群 Pod 要如何被連線及存取」的元件。 Service 可以為一組提供特定功能(Web 服務、圖像處理等)的 Pod 分配一個名稱和唯一的 IP 地址(clusterIP)。 果我們有多個 Pods 想要同時被連線時,我們就可以用到 Service 這個進階元件。 ### Service 的Types * ClusterIP. 用於在Cluster內部的 IP 地址上開放服務。 僅允許從Cluster內部存取。 * NodePort. 僅提供外部存取。若只需要一個service接口,可以選擇NodePort。 * LoadBalancer. Exposes the service via the cloud provider’s load balancer。 供外部存取 (但只限於支援此 type 的 public cloud),若在相同service下有多個instances就必須使用LoadBalancer。若有多個services就會非常昂貴,就會建議使用Ingress。 * ExternalName. Maps a service to a predefined externalName field by returning a value for the CNAME record. ### Deployment  Deployment定義資源得長相,負責向這些 pod 公開接口,這使得可以從集群內部或外部進程與服務之間進行網絡訪問。Ingress 實際上並不是一種服務。相反,它是位於集群中多個服務前面的入口點。它可以定義為一組路由規則,這些規則控制外部用戶如何訪問在 Kubernetes 集群中運行的服務。 Deployment 為 pod & replicaset 提供了一個宣告式的設定 & 更新方式,透過定義 desired status,Deployment controller 會在所謂的 controlled rate 下達到使用者所期望的狀態,這些機制是由 k8s 自動化完成,因此官方建議應該透過 Deployment 來佈署 pod & replicaset。 ### Ingress Ingress 可以透過 HTTP/HTTPS,在我們眾多的 Service 前搭建一個 reverse-proxy。這樣 Ingress 可以幫助我們統一一個對外的 port number,並且根據 hostname 或是 pathname 決定封包要轉發到哪個 Service 上,如同下圖的比較:  在 Kubernetes 中,Ingress 這項服務其實是由 Ingress Resources、Ingress Server、Ingress Controller 構成。 ## kubectl 指令 #### get all pods in specify namespace ``` kubectl get pod -n {namespace} kubectl get pod -n cloudep ``` #### describe all resources in a pod in namespace ``` kubectl describe pod {podname} -n {namespace} kubectl describe pod cloudep-agent-activity-compensation-job-consumer-5786dcb4cprwpd -n cloudep ``` ### switch Context in different server ``` kubectl Switch Context ```
×
Sign in
Email
Password
Forgot password
or
By clicking below, you agree to our
terms of service
.
Sign in via Facebook
Sign in via Twitter
Sign in via GitHub
Sign in via Dropbox
Sign in with Wallet
Wallet (
)
Connect another wallet
New to HackMD?
Sign up