Information in this document may be out of date
This document has an older update date than the original, so the information it contains may be out of date. If you're able to read English, see the English version for the most up-to-date information: Migrate Kubernetes Objects Using Storage Version Migration
使用存储版本迁移功能来迁移 Kubernetes 对象
Kubernetes v1.30 [alpha]
Kubernetes 依赖主动重写的 API 数据来支持与静态存储相关的一些维护活动。 两个著名的例子是已存储资源的版本化模式(即针对给定资源的首选存储模式从 v1 更改为 v2) 和静态加密(即基于数据加密方式的变化来重写过时的数据)。
准备开始
安装 kubectl
。
你必须拥有一个 Kubernetes 的集群,且必须配置 kubectl 命令行工具让其与你的集群通信。 建议运行本教程的集群至少有两个节点,且这两个节点不能作为控制平面主机。 如果你还没有集群,你可以通过 Minikube 构建一个你自己的集群,或者你可以使用下面的 Kubernetes 练习环境之一:
你的 Kubernetes 服务器版本必须是 v1.30. 要获知版本信息,请输入kubectl version
.
使用存储版本迁移来重新加密 Kubernetes Secret
-
首先配置 KMS 驱动, 以便使用如下加密配置来加密 etcd 中的静态数据。
kind: EncryptionConfiguration apiVersion: apiserver.config.k8s.io/v1 resources: - resources: - secrets providers: - aescbc: keys: - name: key1 secret: c2VjcmV0IGlzIHNlY3VyZQ==
确保通过将
--encryption-provider-config-automatic-reload
设置为 true,允许自动重新加载加密配置文件。
-
使用 kubectl 创建 Secret。
kubectl create secret generic my-secret --from-literal=key1=supersecret
-
验证该 Secret 对象的序列化数据带有前缀
k8s:enc:aescbc:v1:key1
。 -
按照以下方式更新加密配置文件,以轮换加密密钥。
kind: EncryptionConfiguration apiVersion: apiserver.config.k8s.io/v1 resources: - resources: - secrets providers: - aescbc: keys: - name: key2 secret: c2VjcmV0IGlzIHNlY3VyZSwgaXMgaXQ/ - aescbc: keys: - name: key1 secret: c2VjcmV0IGlzIHNlY3VyZQ==
-
要确保之前创建的 Secret
my-secert
使用新密钥key2
进行重新加密,你将使用存储版本迁移。 -
创建以下名为
migrate-secret.yaml
的 StorageVersionMigration 清单:kind: StorageVersionMigration apiVersion: storagemigration.k8s.io/v1alpha1 metadata: name: secrets-migration spec: resource: group: "" version: v1 resource: secrets
使用以下 kubectl 命令创建对象:
kubectl apply -f migrate-secret.yaml
-
通过检查 StorageVersionMigration 的
.status
来监控 Secret 的迁移。 成功的迁移应将其Succeeded
状况设置为 true。 获取 StorageVersionMigration 对象的方式如下:kubectl get storageversionmigration.storagemigration.k8s.io/secrets-migration -o yaml
输出类似于:
kind: StorageVersionMigration apiVersion: storagemigration.k8s.io/v1alpha1 metadata: name: secrets-migration uid: 628f6922-a9cb-4514-b076-12d3c178967c resourceVersion: "90" creationTimestamp: "2024-03-12T20:29:45Z" spec: resource: group: "" version: v1 resource: secrets status: conditions: - type: Running status: "False" lastUpdateTime: "2024-03-12T20:29:46Z" reason: StorageVersionMigrationInProgress - type: Succeeded status: "True" lastUpdateTime: "2024-03-12T20:29:46Z" reason: StorageVersionMigrationSucceeded resourceVersion: "84"
- 验证存储的
Secret 现在带有前缀
k8s:enc:aescbc:v1:key2
。
更新 CRD 的首选存储模式
考虑这样一种情况: 用户创建了 CustomResourceDefinition (CRD) 来提供自定义资源 (CR),并将其设置为首选的存储模式。 当需要引入 CRD 的 v2 版本时,只需提供转换 Webhook 就可以为 v2 版本提供服务。 基于转换 Webhook 的方式能够实现更平滑的过渡,用户可以使用 v1 或 v2 模式创建 CR,并通过合适的 Webhook 执行必要的模式转换。 在将 v2 设置为首选的存储模式版本之前,重要的是要确保将当前已存储为 v1 的所有 CR 已被迁移到 v2。 这种迁移可以通过使用存储版本迁移将所有 CR 从 v1 迁移到 v2 来达成。
-
如下针对名为
test-crd.yaml
的 CRD 创建一个清单:apiVersion: apiextensions.k8s.io/v1 kind: CustomResourceDefinition metadata: name: selfierequests.stable.example.com spec: group: stable.example.com names: plural: SelfieRequests singular: SelfieRequest kind: SelfieRequest listKind: SelfieRequestList scope: Namespaced versions: - name: v1 served: true storage: true schema: openAPIV3Schema: type: object properties: hostPort: type: string conversion: strategy: Webhook webhook: clientConfig: url: https://127.0.0.1:9443/crdconvert caBundle: <CABundle info> conversionReviewVersions: - v1 - v2
使用 kubectl 创建 CRD:
kubectl apply -f test-crd.yaml
-
为 testcrd 示例创建一个清单。命名为
cr1.yaml
并使用以下内容:apiVersion: stable.example.com/v1 kind: SelfieRequest metadata: name: cr1 namespace: default
使用 kubectl 创建 CR:
kubectl apply -f cr1.yaml
-
通过从 etcd 获取对象来验证 CR 是否以 v1 格式被写入和存储。
ETCDCTL_API=3 etcdctl get /kubernetes.io/stable.example.com/testcrds/default/cr1 [...] | hexdump -C
其中
[...]
包含连接到 etcd 服务器的额外参数。
-
如下更新 CRD
test-crd.yaml
,将 v2 版本设置为 served 和 storage,并将 v1 设置为仅 served:apiVersion: apiextensions.k8s.io/v1 kind: CustomResourceDefinition metadata: name: selfierequests.stable.example.com spec: group: stable.example.com names: plural: SelfieRequests singular: SelfieRequest kind: SelfieRequest listKind: SelfieRequestList scope: Namespaced versions: - name: v2 served: true storage: true schema: openAPIV3Schema: type: object properties: host: type: string port: type: string - name: v1 served: true storage: false schema: openAPIV3Schema: type: object properties: hostPort: type: string conversion: strategy: Webhook webhook: clientConfig: url: "https://127.0.0.1:9443/crdconvert" caBundle: <CABundle info> conversionReviewVersions: - v1 - v2
使用 kubectl 更新 CRD:
kubectl apply -f test-crd.yaml
-
如下创建名为
cr2.yaml
的 CR 资源文件:apiVersion: stable.example.com/v2 kind: SelfieRequest metadata: name: cr2 namespace: default
-
使用 kubectl 创建 CR:
kubectl apply -f cr2.yaml
-
通过从 etcd 获取对象来验证 CR 是否以 v2 格式被写入和存储。
ETCDCTL_API=3 etcdctl get /kubernetes.io/stable.example.com/testcrds/default/cr2 [...] | hexdump -C
其中
[...]
包含连接到 etcd 服务器的额外参数。
-
如下创建名为
migrate-crd.yaml
的 StorageVersionMigration 清单:kind: StorageVersionMigration apiVersion: storagemigration.k8s.io/v1alpha1 metadata: name: crdsvm spec: resource: group: stable.example.com version: v1 resource: SelfieRequest
使用如下 kubectl 命令创建此对象:
kubectl apply -f migrate-crd.yaml
-
使用 status 监控 Secret 的迁移。 若迁移成功,应在 status 字段中将
Succeeded
状况设置为 "True"。 获取迁移资源的方式如下:kubectl get storageversionmigration.storagemigration.k8s.io/crdsvm -o yaml
输出类似于:
kind: StorageVersionMigration apiVersion: storagemigration.k8s.io/v1alpha1 metadata: name: crdsvm uid: 13062fe4-32d7-47cc-9528-5067fa0c6ac8 resourceVersion: "111" creationTimestamp: "2024-03-12T22:40:01Z" spec: resource: group: stable.example.com version: v1 resource: testcrds status: conditions: - type: Running status: "False" lastUpdateTime: "2024-03-12T22:40:03Z" reason: StorageVersionMigrationInProgress - type: Succeeded status: "True" lastUpdateTime: "2024-03-12T22:40:03Z" reason: StorageVersionMigrationSucceeded resourceVersion: "106"
-
通过从 etcd 获取对象来验证之前创建的 cr1 是否现在以 v2 格式被写入和存储。
ETCDCTL_API=3 etcdctl get /kubernetes.io/stable.example.com/testcrds/default/cr1 [...] | hexdump -C
其中
[...]
包含连接到 etcd 服务器的额外参数。