Kubernetes爲每一個Pod都分配了惟一的IP地址,稱之爲Pod IP,一個Pod裏的多個容器共享Pod IP地址。Kubernetes要求底層網絡支持集羣內任意兩個Pod之間的TCP/IP直接通訊,這一般採用虛擬二層網絡技術來實現,例如Flannel、Open vSwitch等。所以,在Kubernetes裏,一個Pod裏的容器與另外主機上的Pod容器可以直接通訊。
Pod有兩種類型:普通的Pod和靜態Pod(Static Pod),靜態Pod不存放在etcd存儲裏,而是存放在某個具體的Node上的一個具體文件中,而且只在此Node上啓動運行。普通的Pod一旦被建立,就會被存儲到etcd中,隨後會被Kubernetes Master調度到某個具體的Node上並進行綁定(Binding),該Node上的kubelet進程會將其實例化成一組相關的Docker容器並啓動起來。當Pod裏的某個容器中止時,Kubernetes會自動檢測到這個問題而且從新啓動這個Pod(重啓Pod裏的全部容器);若是Pod所在的Node宕機,則會將這個Node上的全部Pod從新調度到其餘節點上運行。
Pod、容器與Node的關係以下圖:
Kubernetes裏的全部資源對象均可以採用yaml或者JSON格式的文件來定義或描述,下面是一個簡單的Pod資源定義文件:php
apiVersion: v1 kind: Pod metadata: name: myweb labels: name: myweb spec: containers: - name: myweb image: kubeguide/tomcat-app: v1 ports: - containerPort: 8080 env: - name: MYSQL_SERVICE_HOST value: 'mysql' - name: MYSQL_SERVICE_PORT value: '3306'
kind爲pod代表這是一個Pod的定義,metadata裏的name屬性爲Pod的名字,metadata裏還能定義資源對象的標籤(Label),這裏聲明myweb擁有一個name=myweb的標籤(Label)。Pod裏包含的容器組的定義則在spec一節中聲明,這裏定義了一個名字爲myweb,對應鏡像爲kubeguide/tomcat-app: v1的容器,該容器注入了名爲MYSQL_SERVICE_HOST='mysql'和MYSQL_SERVICE_PORT='3306'的環境變量(env關鍵字),而且在8080端口(containerPort)上啓動容器進程。Pod的IP加上這裏的容器端口,就組成了一個新的概念——Endpoint,它表明着此Pod裏的一個服務進程的對外通訊地址。一個Pod也存在着具備多個Endpoint的狀況,好比咱們把Tomcat定義爲一個Pod時,能夠對外暴露管理端口與服務端口這兩個Endpoint。
Docker裏的Volume在Kubernetes裏也有對應的概念——Pod Volume,Pod Volume有一些擴展,好比能夠用分佈式文件系統GlusterFS等實現後端存儲功能;Pod Volume是定義在Pod之上,而後被各個容器掛載到本身的文件系統中的。對於Pod Volume的定義咱們後面會講到。
這裏順便提一下Event概念,Event是一個事件的記錄,記錄了事件的最先產生時間、最後重現時間、重複次數、發起者、類型,以及致使此事件的緣由等衆多信息。Event一般會關聯到某個具體的資源對象上,是排查故障的重要參考信息,當咱們發現某個Pod遲遲沒法建立時,能夠用kubectl describe pod xxx來查看它的描述信息,用來定位問題的緣由。
每一個Pod均可以對其能使用的服務器上的計算資源設置限額,當前能夠設置限額的計算資源有CPU和Memory兩種,其中CPU的資源單位爲CPU(Core)的數量,是一個絕對值。
對於容器來講一個CPU的配額已是至關大的資源配額了,因此在Kubernetes裏,一般以千分之一的CPU配額爲最小單位,用m來表示。一般一個容器的CPU配額被定義爲100-300m,即佔用0.1-0.3個CPU。與CPU配額相似,Memory配額也是一個絕對值,它的單位是內存字節數。
對計算資源進行配額限定須要設定如下兩個參數:前端
一般咱們應該把Requests設置爲一個比較小的數值,知足容器平時的工做負載狀況下的資源需求,而把Limits設置爲峯值負載狀況下資源佔用的最大量。下面是一個資源配額的簡單定義:node
spec: containers: - name: db image: mysql resources: requests: memory: "64Mi" cpu: "250m" limits: memory: "128Mi" cpu: "500m"
最小0.25個CPU及64MB內存,最大0.5個CPU及128MB內存。mysql
Label至關於咱們熟悉的「標籤」,給某個資源對象定義一個Label,就至關於給它打了一個標籤,隨後能夠經過Label Selector(標籤選擇器)查詢和篩選擁有某些Label的資源對象,Kubernetes經過這種方式實現了相似SQL的簡單又通用的對象查詢機制。
Label Selector至關於SQL語句中的where查詢條件,例如,name=redis-slave這個Label Selector做用於Pod時,至關於select * from pod where pod’s name = ‘redis-slave’這樣的語句。Label Selector的表達式有兩種:基於等式的(Equality-based)和基於集合的(Set-based)。下面是基於等式的匹配例子。
name=redis-slave:匹配全部標籤爲name=redis-slave的資源對象。
env != production:匹配全部標籤env不等於production的資源對象。
下面是基於集合的匹配例子nginx
還能夠經過多個Label Selector表達式的組合實現複雜的條件選擇,多個表達式之間用「,」進行分隔便可,幾個條件之間是「AND」的關係,即同時知足多個條件,例如:git
name=redis-slave, env!=production name not in (php-frontend), env!=production
以Pod爲例,Label定義在metadata中:web
apiVersion: v1 kind: Pod metadata: name: myweb labels: app: myweb
RC和Service在spec中定義Selector與Pod進行關聯:redis
apiVersion: v1 kind: ReplicationController metadata: name: myweb spec: replicas: 1 selector: app: myweb template: …………
Deployment、ReplicaSet、DaemonSet和Job則能夠在Selector中使用基於集合的篩選條件:sql
selector: matchLabels: app: myweb matchExpressions: - {key: tier, operator: In, values: [frontend]} - {key: environment, operator: NotIn, values: [dev]}
matchLabels用於定義一組Label,與直接寫在Selector中做用相同;matchExpressions用於定義一組基於集合的篩選條件,可用的條件運算符包括:In、NotIn、Exists和DoesNotExist。
若是同時設置了matchLabels和matchExpressions,則兩組條件爲「AND」關係,即全部條件須要同時知足才能完成Selector的篩選。
Label Selector在Kubernetes中的重要使用場景以下:docker
下面舉個複雜點的例子,假設咱們爲Pod定義了3個Label:release、env和role,不一樣的Pod定義了不一樣的Label。以下圖所示,若是咱們設置了「role=frontend」的Label Selector,則會選取到Node 1和Node 2上的Pod。
若是咱們設置「release=beta」的Label Selector,則會選取到Node 2和Node 3上的Pod,以下圖所示。
總結:使用Label能夠給對象建立多組標籤,Label和Label Selector共同構成了Kubernetes系統中最核心的應用模型,使得被管理對象可以被精細地分組管理,同時實現了整個集羣的高可用性。
RC的做用是聲明Pod的副本數量在任意時刻都符合某個預期值,因此RC的定義包括以下幾個部分。
下面是一個完整的RC定義的例子,即確保擁有tier=frontend標籤的這個Pod(運行Tomcat容器)在整個Kubernetes集羣中始終有三個副本:
apiVersion: v1 kind: ReplicationController metadata: name: frontend spec: replicas: 3 selector: tier: frontend template: metadata: labels: app: app-demo tier: frontend spec: containers: - name: tomcat-demo image: tomcat imagePullPolicy: IfNotPresent env: - name: GET_HOSTS_FROM value: dns ports: - containerPort: 80
當咱們定義了一個RC並提交到Kubernetes集羣中後,Master節點上的Controller Manager組件就獲得通知,按期巡檢系統中當前存活的目標Pod,並確保目標Pod實例的數量恰好等於此RC的指望值。若是有過多的Pod副本在運行,系統就會停掉多餘的Pod;若是運行的Pod副本少於指望值,即若是某個Pod掛掉,系統就會自動建立新的Pod以保證數量等於指望值。
經過RC,Kubernetes實現了用戶應用集羣的高可用性,而且大大減小了運維人員在傳統IT環境中須要完成的許多手工運維工做(如主機監控腳本、應用監控腳本、故障恢復腳本等)。
下面咱們來看下Kubernetes如何經過RC來實現Pod副本數量自動控制的機制,假如咱們有3個Node節點,在RC裏定義了redis-slave這個Pod須要保持兩個副本,系統將會在其中的兩個Node上建立副本,以下圖所示。
假如Node2上的Pod2意外終止,根據RC定義的replicas數量2,Kubernetes將會自動建立並啓動一個新的Pod,以保證整個集羣中始終有兩個redis-slave Pod在運行。
系統可能選擇Node1或者Node3來建立一個新的Pod,以下圖。
經過修改RC的副本數量,能夠實現Pod的動態縮放(Scaling)功能。kubectl scale rc redis-slave --replicas=3
此時Kubernetes會在3個Node中選取一個Node建立並運行一個新的Pod3,使redis-slave Pod副本數量始終保持3個。
因爲Replication Controller與Kubernetes代碼中的模塊Replication Controller同名,同時這個詞也沒法準確表達它的意思,因此從Kubernetes v1.2開始,它就升級成了另一個新的對象——Replica Set,官方解釋爲「下一代的RC」。它與RC當前存在的惟一區別是:Replica Set支持基於集合的Label selector(Set-based selector),而RC只支持基於等式的Label selector(equality-based selector),因此Replica Set的功能更強大。下面是Replica Set的定義例子(省去了Pod模板部分的內容):
apiVersion: extensions/v1beta1 kind: ReplicaSet metadata: name: frontend spec: selector: matchLabels: tier: frontend matchExpressions: - {key: tier, operator: In, values: [frontend]} template: …………
Replica Set不多單獨使用,它主要被Deployment這個更高層的資源對象所使用,從而造成一整套Pod建立、刪除、更新的編排機制。
RC和RS的特性與做用以下:
Deployment相對於RC的最大區別是咱們能夠隨時知道當前Pod「部署」的進度。一個Pod的建立、調度、綁定節點及在目標Node上啓動對應的容器這一完整過程須要必定的時間,因此咱們期待系統啓動N個Pod副本的目標狀態,其實是一個連續變化的「部署過程」致使的最終狀態。
Deployment的典型使用場景有如下幾個:
Deployment的定義與Replica Set的定義相似,只是API聲明與Kind類型不一樣。
apiVersion: extensions/v1beta1 kind: Deployment metadata: name: nginx-deployment
apiVersion: v1 kind: ReplicaSet metadata: name: nginx-repset
下面是Deployment定義的一個完整例子:
apiVersion: extensions/v1beta1 kind: Deployment metadata: name: frontend spec: replicas: 1 selector: matchLabels: tier: frontend matchExpressions: - {key: tier, operator: In, values: [frontend]} template: metadata: labels: app: app-demo tier: frontend spec: containers: - name: tomcat-demo image: tomcat imagePullPolicy: IfNotPresent ports: - containerPort: 8080
能夠經過命令kubectl get deployment來查看Deployment的信息,其中的幾個參數解釋以下:
Pod的管理對象,除了RC、ReplicaSet、Deployment,還有DaemonSet、StatefulSet、Job等,分別用於不一樣的應用場景。
HPA與RC、Deployment同樣,也屬於Kubernetes資源對象。經過追蹤分析RC或RS控制的全部目標Pod的負載變化狀況,來肯定是否須要針對性地調整目標Pod的副本數。
HPA有如下兩種方式做爲Pod負載的度量指標:
CPUUtilizationPercentage是一個算術平均值,即目標Pod全部副本自帶的CPU利用率的平均值。一個Pod自身的CPU利用率是該Pod當前CPU的使用量除以它的Pod Request的值,好比咱們定義一個Pod的Pod Request爲0.4,而當前Pod的CPU使用量爲0.2,則它的CPU使用率爲50%,這樣咱們就能夠算出來一個RC或RS控制的全部Pod副本的CPU利用率的算術平均值了。若是某一時刻CPUUtilizationPercentage的值超過80%,則意味着當前的Pod副本數極可能不足以支撐接下來更多的請求,須要進行動態擴容,而當請求高峯時段過去後,Pod的CPU利用率又會降下來,此時對應的Pod副本數應該自動減小到一個合理的水平。
下面是HPA定義的一個具體的例子:
apiVersion: autoscaling/v1 kind: HorizontalPodAutoscaler metadata: name: php-apache namespace: default spec: maxReplicas: 10 minReplicas: 2 scaleTargetRef: kind: Deployment name: php-apache targetCPUUtilizationPercentage: 90
經過HPA控制php-apache的Pod副本,當Pod副本的CPUUtilizationPercentage的值超過90%時,會進行自動擴容增長Pod副本的數量,擴容或縮容時Pod的副本數量要介於2-10之間。
除了經過yaml文件來定義HPA對象以外,還能夠經過命令的方式建立:kubectl autoscale deployment php-apache --cpu-percent=90 --min=1 --max=10
Pod的管理對象RC、Deployment、DaemonSet和Job都是面向無狀態的服務,但實際中有不少服務是有狀態的,好比Mysql集羣、MongoDB集羣、ZooKeeper集羣等,可使用StatefulSet來管理有狀態的服務。
StatefulSet有以下一些特性:
StatefulSet除了要與PV卷捆綁使用以存儲Pod的狀態數據,還要與Headless Service配合使用,即在每一個StatefulSet的定義中要聲明它屬於哪一個Headless Service。Headless Service與普通Service的區別在於,它沒有Cluster IP,若是解析Headless Service的DNS域名,則返回的是該Service對應的所有Pod的Endpoint列表。StatefulSet在Headless Service的基礎上又爲StatefulSet控制的每一個Pod實例建立了一個DNS域名,這個域名的格式爲:
$(podname).$(headless service name)
好比一個3節點的kafka的StatefulSet集羣,對應的Headless Service的名字爲kafka,StatefulSet的名字爲kafka,則StatefulSet裏面的3個Pod的DNS名稱分別爲kafka-0.kafka、kafka-1.kafka、kafka-3.kafka,這些DNS名稱能夠直接在集羣的配置文件中固定下來。
1.概述
Service其實就是咱們常常提起的微服務架構中的一個「微服務」,Pod、RC等資源對象其實都是爲它做「嫁衣」的。Pod、RC或RS與Service的邏輯關係以下圖所示。
經過上圖咱們看到,Kubernetes的Service定義了一個服務的訪問入口地址,前端的應用(Pod)經過這個入口地址訪問其背後的一組由Pod副本組成的集羣實例,Service與其後端Pod副本集羣之間則是經過Label Selector來實現「無縫對接」的。而RC的做用其實是保證Service的服務能力和服務質量始終處於預期的標準。
經過分析、識別並建模系統中的全部服務爲微服務——Kubernetes Service,最終咱們的系統由多個提供不一樣業務能力而又彼此獨立的微服務單元所組成,服務之間經過TCP/IP進行通訊,從而造成了強大而又靈活的彈性集羣,擁有了強大的分佈式能力、彈性擴展能力、容錯能力。所以,咱們的系統架構也變得簡單和直觀許多。
既然每一個Pod都會被分配一個單獨的IP地址,並且每一個Pod都提供了一個獨立的Endpoint(Pod IP+ContainerPort)以被客戶端訪問,多個Pod副本組成了一個集羣來提供服務,那麼客戶端如何來訪問它們呢?通常的作法是部署一個負載均衡器(軟件或硬件),但這樣無疑增長了運維的工做量。在Kubernetes集羣裏使用了Service(服務),它提供了一個虛擬的IP地址(Cluster IP)和端口號,Kubernetes集羣裏的任何服務均可以經過Cluster IP+端口的方式來訪問此服務,至於訪問請求最後會被轉發到哪一個Pod,則由運行在每一個Node上的kube-proxy負責。kube-proxy進程其實就是一個智能的軟件負載均衡器,它負責把對Service的請求轉發到後端的某個Pod實例上,並在內部實現服務的負載均衡與會話保持機制。
下面是一個Service的簡單定義:
apiVersion: v1 kind: Service metadata: name: tomcat-service spec: ports: - port: 8080 selector: tier: frontend
上述內容定義了一個名爲「tomcat-service」的Service,它的服務端口爲8080,擁有「tier=frontend」這個Label的全部Pod實例。
不少服務都存在多個端口的問題,一般一個端口提供業務服務,另一個端口提供管理服務,好比Mycat、Codis等常見中間件。Kubernetes Service支持多個Endpoint,要求每一個Endpoint定義一個名字來區分,下面是tomcat多端口的Service定義樣例。
apiVersion: v1 kind: Service metadata: name: tomcat-service spec: ports: - port: 8080 name: service-port - port: 8005 name: shutdown-port selector: tier: frontend
多端口爲何須要給每一個端口命名呢?這就涉及Kubernetes的服務發現機制了。
2.Kubernetes的服務發現機制
每一個Kubernetes中的Service都有一個惟一的Cluster IP及惟一的名字,而名字是由咱們本身定義的,那咱們是否能夠經過Service的名字來訪問呢?
最先時Kubernetes採用了Linux環境變量的方式來實現,即每一個Service生成一些對應的Linux環境變量(ENV),並在每一個Pod的容器啓動時,自動注入這些環境變量,以實現經過Service的名字來創建鏈接的目的。
考慮到經過環境變量獲取Service的IP與端口的方式仍然不方便、不直觀,後來Kubernetes經過Add-On增值包的方式引入了DNS系統,把服務名做爲DNS域名,這樣程序就能夠直接使用服務名來創建鏈接了。
關於DNS的部署,後續博文我會單獨講解,有興趣的朋友能夠關注個人博客。
3.外部系統訪問Service的問題
Kubernetes集羣裏有三種IP地址,分別以下:
外部訪問Kubernetes集羣裏的某個節點或者服務時,必需要經過Node IP進行通訊。
Pod IP是Docker Engine根據docker0網橋的IP地址段進行分配的一個虛擬二層網絡IP地址,Pod與Pod之間的訪問就是經過這個虛擬二層網絡進行通訊的,而真實的TCP/IP流量則是經過Node IP所在的物理網卡流出的。
Service的Cluster IP具備如下特色:
咱們的應用若是想讓外部訪問,最經常使用的做法是使用NodePort方式。
apiVersion: v1 kind: Service metadata: name: tomcat-service spec: type: NodePort ports: - port: 8080 nodePort: 31002 selector: tier: frontend
NodePort的實現方式是在Kubernetes集羣裏的每一個Node上爲須要外部訪問的Service開啓一個對應的TCP監聽端口,外部系統只要用任意一個Node的IP地址+具體的NodePort端口號便可訪問此服務。
NodePort尚未徹底解決外部訪問Service的全部問題,好比負載均衡問題,經常使用的作法是在Kubernetes集羣以外部署一個負載均衡器。
Load balancer組件獨立於Kubernetes集羣以外,能夠是一個硬件負載均衡器,也能夠是軟件方式實現,例如HAProxy或者Nginx。這種方式,無疑是增長了運維的工做量及出錯的機率。
因而Kubernetes提供了自動化的解決方案,若是咱們使用谷歌的GCE公有云,那麼只須要將type: NodePort改爲type: LoadBalancer,此時Kubernetes會自動建立一個對應的Load balancer實例並返回它的IP地址供外部客戶端使用。其餘公有云提供商只要實現了支持此特性的驅動,則也能夠達到上述目的。
Volume是Pod中可以被多個容器訪問的共享目錄。Volume定義在Pod上,被一個Pod裏的多個容器掛載到具體的文件目錄下,當容器終止或者重啓時,Volume中的數據也不會丟失。Kubernetes支持多種類型的Volume,例如GlusterFS、Ceph等分佈式文件系統。
除了可讓一個Pod裏的多個容器共享文件、讓容器的數據寫到宿主機的磁盤上或者寫文件到網絡存儲中,Kubernetes還提供了容器配置文件集中化定義與管理,經過ConfigMap對象來實現。
Kubernetes支持多種Volume類型,下面咱們一一進行介紹。
1.emptyDir
emptyDir是在Pod分配到Node時建立的,它的初始內容爲空,而且無須指定宿主機上對應的目錄文件,它是Kubernetes自動分配的一個目錄,當Pod從Node上移除時,emptyDir中的數據也會被永久刪除。
emptyDir的用途以下:
emptyDir的定義以下:
template: metadata: labels: app: app-demo tier: frontend spec: volumes: - name: datavol emptyDir: {} containers: - name: tomcat-demo image: tomcat volumeMounts: - mountPath: /mydata-data name: datavol imagePullPolicy: IfNotPresent
2.hostPath
使用hostPath掛載宿主機上的文件或目錄,主要用於如下幾個方面:
使用hostPath時,須要注意如下幾點:
hostPath的定義以下:
volumes: - name: "persistent-storage" hostPath: path: "/data"
3.gcePersistentDisk
使用這種類型的Volume表示使用谷歌公有云提供的永久磁盤(Persistent Disk,PD)存放數據,使用gcePersistentDisk有如下一些限制條件:
經過gcloud命令建立一個PD:gcloud compute disks create --size=500GB --zone=us-centrall-a my-data-disk
定義gcePersistentDisk類型的Volume的示例以下:
volumes: - name: test-volume gcPersistentDisk: pdName: my-data-disk fsType: ext4
4.awsElasticBlockStore
與GCE相似,該類型的Volume使用亞馬遜公有云提供的EBS Volume存儲數據,須要先建立一個EBS Volume才能使用awsElasticBlockStore。
使用awsElasticBlockStore的一些限制條件以下:
經過aws ec2 create-volume命令建立一個EBS volume:aws ec2 create-volume --availability-zone eu-west-la --size 10 --volume-type gp2
定義awsElasticBlockStore類型的Volume的示例以下:
volumes: - name: test-volume awsElasticBlockStore: volumeID: aws://<availability-zone>/<volume-id> fsType: ext4
5.NFS
使用NFS網絡文件系統提供的共享目錄存儲數據時,咱們須要在系統中部署一個NFS Server。
定義NFS類型的Volume的示例以下:
volumes: - name: nfs-volume nfs: server: nfs-server.localhost path: "/"
6.其餘類型的Volume
上面提到的Volume是定義在Pod上的,屬於「計算資源」的一部分,而實際上,「網絡存儲」是相對獨立於「計算資源」而存在的一種實體資源。好比在使用雲主機的狀況下,咱們一般會先建立一個網絡存儲,而後從中劃出一個「網盤」並掛載到雲主機上。Persistent Volume(簡稱PV)和與之相關聯的Persistent Volume Claim(簡稱PVC)實現了相似的功能。
PV與Volume的區別以下:
下面是NFS類型PV的yaml定義內容,聲明瞭須要5G的存儲空間:
apiVersion: v1 kind: PersistentVolume metadata: name: pv003 spec: capacity: storage: 5Gi accessModes: - ReadWriteOnce nfs: path: /somepath server: 172.17.0.2
PV的accessModes屬性有如下類型:
若是Pod想申請使用PV資源,則首先須要定義一個PersistentVolumeClaim(PVC)對象:
apiVersion: v1 kind: PersistentVolumeClaim metadata: name: myclaim spec: accessModes: - ReadWriteOnce resources: requests: storage: 5Gi
而後在Pod的volume定義中引用上述PVC便可
volumes: - name: mypd persistentVolumeClaim: claimName: myclaim
PV是有狀態的對象,它有如下幾種狀態:
經過將Kubernetes集羣內部的資源對象「分配」到不一樣的Namespace中,造成邏輯上分組的不一樣項目、小組或用戶組,便於不一樣的分組在共享使用整個集羣的資源的同時還能被分別管理。
Kubernetes集羣在啓動後,會建立一個名爲「default」的Namespace,經過kubectl能夠查看到:kubectl get namespaces
若是不特別指明Namespace,則用戶建立的Pod、RC、RS、Service都獎被系統建立到這個默認的名爲default的Namespace中。
下面是Namespace的定義示例:
apiVersion: v1 kind: Namespace metadata: name: development
定義一個Pod,並指定它屬於哪一個Namespace:
apiVersion: v1 kind: Pod metadata: name: busybox namespace: development spec: containers: - image: busybox command: - sleep - "3600" name: busybox
使用kubectl get命令查看Pod狀態信息時,須要加上--namespace參數,指定查看哪一個namespace下的資源對象,不加這個參數則默認查看 default下的資源對象。kubectl get pods --namespace=development
當咱們給每一個租戶建立一個Namespace來實現多租戶的資源隔離時,還能結合Kubernetes的資源配額管理,限定不一樣租戶能佔用的資源,例如CPU使用量、內存使用量等。
Annotation與Label相似,也使用key/value鍵值對的形式進行定義。不一樣的是Label具備嚴格的命名規則,它定義的是Kubernetes對象的元數據(Metadata),而且用於Label Selector。而Annotation則是用戶任意定義的「附加」信息,以便於外部工具進行查找。一般Kubernetes的模塊會經過Annotation的方式標記資源對象的一些特殊信息。
使用Annotation來記錄的信息以下:
注:本文內容摘自《Kubernetes權威指南:從Docker到Kubernetes實踐全接觸(記念版》,並精減了部份內部,並且對部份內容作了相應的調整,能夠幫助你們加深對Kubernetes的各類資源對象的理解和定義方法,關注個人博客,跟我一塊兒開啓k8s的學習之旅吧。