標籤:

k8s學習筆記之持久化存儲

知識大綱

  • 理解持久化卷(pv),並知道如何創建它們
  • 理解卷(volumes)的access mode
  • 理解持久化卷聲明(pvc)的原語
  • 理解k8s的存儲對象(kubernetes storage objects)
  • 知道如何為應用配置持久化存儲

三個概念: pv ,storageclass, pvc

  • pv - 持久化卷, 支持本地存儲和網路存儲, 例如hostpath,ceph rbd, nfs等,只支持兩個屬性, capacity和accessModes。其中capacity只支持size的定義,不支持iops等參數的設定,accessModes有三種,ReadWriteOnce(被單個node讀寫), ReadOnlyMany(被多個nodes讀), ReadWriteMany(被多個nodes讀寫)
  • storageclass-另外一種提供存儲資源的方式, 提供更多的層級選型, 如iops等參數。 但是具體的參數與提供方是綁定的。 如aws和gce它們提供的storageclass的參數可選項是有不同的。
  • pvc - 對pv或者storageclass資源的請求, pvc 對 pv 類比於pod 對不同的cpu, mem的請求。

六個生命周期: Provisioning, Binding, Using, Releasing, Reclaiming, Recycling

k8s對pv和pvc之間的交互的生命周期進行管理。

  • provisioning- 配置階段, 分為static, dynamic兩種方式。靜態的方式是創建一系列的pv,然後pvc從pv中請求。 動態的方式是基於storageclass的。
  • Binding - 綁定階段, pvc根據請求的條件篩選並綁定對應的pv。 一定pvc綁定pv後, 就會排斥其它綁定,即其它pvc無法再綁定同一個pv,即使這個pv設定的access mode允許多個node讀寫。 此外 ,pvc 如何匹配不到相應條件的pv, 那麼就會顯示unbound狀態, 直到匹配為止。 需要注意的是,pvc請求100Gi大小的存儲,即使用戶創建了很多50Gi大小的存儲, 也是無法被匹配的。
  • Using- 使用階段, pods 掛載存儲, 即在pod的template文件中定義volumn使用某個pvc。
  • Releasing - 釋放階段, 當pvc對象被刪除後, 就處於釋放階段。 在這個階段, 使用的pv還不能被其它的pvc請求。 之前數據可能還會留存下來, 取決於用戶在pv中設定的policy, 見persistentVolumeReclaimPolicy。
  • Reclaiming - 重聲明階段。 到這個階段, 會告訴cluster如何處理釋放的pv。 數據可能被保留(需要手工清除), 回收和刪除。動態分配的存儲總是會被刪除掉的。
  • Recycling - 回收階段。回收階段會執行基本的遞歸刪除(取決於volumn plugins的支持),把pv上的數據刪除掉, 以使pv可以被新的pvc請求。 用戶也可以自定義一個 recycler pod , 對數據進行刪除。

三種PV的訪問模式

  • ReadWriteOnce:是最基本的方式,可讀可寫,但只支持被單個Pod掛載。
  • ReadOnlyMany:可以以只讀的方式被多個Pod掛載。
  • ReadWriteMany:這種存儲可以以讀寫的方式被多個Pod共享。

不是每一種存儲都支持這三種方式,像共享方式,目前支持的還比較少,比較常用的是NFS。在PVC綁定PV時通常根據兩個條件來綁定,一個是存儲的大小,另一個就是訪問模式。

九個PV Plugins

pv是以plugin的形式來提供支持的, 考慮到私有雲的使用場景, 排除掉azure, aws,gce等公有雲廠商綁定的plugin, 有9個插件值得關注。這些plugin所支持的accessmode是不同的。 分別是:

三個重聲明策略(reclaim policy)

  • Retain – 手動重新使用
  • Recycle – 基本的數據擦除 (「rm -rf /thevolume/*」)
  • Delete – 相關聯的後端存儲卷刪除, 後端存儲比如AWS EBS, GCE PD, Azure Disk, or OpenStack Cinder

需要特別注意的是只有本地盤和nfs支持數據盤Recycle 擦除回收, AWS EBS, GCE PD, Azure Disk, and Cinder 存儲卷支持Delete策略

四個階段(volumn phase)

一個存儲卷會處於下面幾個階段中的一個階段:

  • Available –資源可用, 還沒有被聲明綁定
  • Bound – 被聲明綁定
  • Released – 綁定的聲明被刪除了,但是還沒有被集群重聲明
  • Failed – 自動回收失敗

四個PV選擇器

在PVC中綁定一個PV,可以根據下面幾種條件組合選擇

  • Access Modes, 按照訪問模式選擇pv
  • Resources, 按照資源屬性選擇, 比如說請求存儲大小為8個G的pv
  • Selector, 按照pv的label選擇
  • Class, 根據StorageClass的class名稱選擇, 通過annotation指定了Storage Class的名字, 來綁定特定類型的後端存儲

關於根據class過濾出pv的說明:

所有的 PVC 都可以在不使用 StorageClass 註解的情況下,直接使用某個動態存儲。把一個StorageClass 對象標記為 「default」 就可以了。StorageClass 用註解storageclass.beta.kubernetes.io 就可以成為預設存儲。有了預設的 StorageClass,用戶創建 PVC 就不用 storage-class 的註解了,1.4 中新加入的DefaultStorageClass 准入控制器會自動把這個標註指向預設存儲類。PVC 指定特定storageClassName,如fast時, 綁定名稱為fast的storageClassPVC中指定storageClassName為「」時, 綁定no class的pv(pv中無class annotation, 或者其值為「」)PVC不指定storageClassName時, DefaultStorageClass admission plugin 開啟與否(在apiserver啟動時可以指定), 對default class的解析行為是不同的。當DefaultStorageClass admission plugin啟用時, 針對沒有storageClass annotation的pvc,DefaultStorageClass會分配一個默認的class, 這個默認的class需要用戶指定,比如在創建storageclass對象時加入annotation,如 storageclass.beta.kubernetes.io 「true」 。如果有多個默認的class, 則pvc會被拒絕創建, 如果用戶沒有指定默認的class, 則這個DefaultStorageClass admission plugin不會起任何作用。 pvc會找那些no class的pv做綁定。當DefaultStorageClass admission plugin沒有啟用時, 針對沒有storageClass annotation的pvc, 會綁定no class的pv(pv中無class annotation, 或者其值為「」)

五個可移植性建議

  1. 把你的 pvc,和 其它一系列配置放一起, 比如說deployment,configmap
  2. 不要把你的pv放在其它配置里, 因為用戶可能沒有許可權創建pv
  3. 初始化pvc 模版的時候, 提供一個storageclass
  4. 在你的工具軟體中,watch那些沒有bound的pvc,並呈現給用戶
  5. 集群啟動的時候啟用DefaultStorageClass, 但是不要指定某一類特定的class, 因為不同provisioner的class,參數很難一致

如何創建和使用PV, PVC

pv示例:

apiVersion: v1nkind: PersistentVolumenmetadata:n name: pv0003nspec:n capacity:n storage: 5Gin accessModes:n - ReadWriteOncen persistentVolumeReclaimPolicy: Recyclen storageClassName: slown nfs:n path: /tmpn server: 172.17.0.2n

pvc示例:

kind: PersistentVolumeClaimnapiVersion: v1nmetadata:n name: myclaimnspec:n accessModes:n - ReadWriteOncen resources:n requests:n storage: 8Gin storageClassName: slown selector:n matchLabels:n release: "stable"n matchExpressions:n - {key: environment, operator: In, values: [dev]}n

在pod中使用pvc,示例

kind: PodnapiVersion: v1nmetadata:n name: mypodnspec:> n containers:n - name: myfrontendn image: dockerfile/nginxn volumeMounts:n - mountPath: "/var/www/html"n name: mypdn volumes:n - name: mypdn persistentVolumeClaim:n claimName: myclaimn

參考文獻

  • 官方文檔之持久化存儲

推薦閱讀:

容器編排之Kubernetes安裝與配置
梁勝關於容器的年終總結,沒再提Docker
Docker、Kubernetes 和 Apache Mesos 對比中的一些誤區

TAG:Kubernetes |