Kasten k10 多云平台适配系列 07 – 利用 Kasten K10 保护 QingCloud QKE 云原生应用

内容提要

发展云原生生态圏是 Veeam 的又一重要战略,以 Kasten by Veeam 为圆心,这个战略又分为三个重要的组成部分,公有云厂商、K8S 分发版本和云原生存储厂商。大家都知道在云原生的领域中,公有云的K8S分发版本是市场占有率最高的,Veeam China 在中国的云原生生态战略部局中也积极在与国内多家公有云厂商合作。QingCloud KubeSphere Engine (QKE) 服务集成了云平台的主机、存储、网络等资源,可以在青云平台一键部署高可用的 KubeSphere 集群,支持集群自动巡检和修复,支持一键升级到新版本,工单 24 小时随时响应,并由 KubeSphere 核心团队提供专业支持和服务。本文将介绍如何在 QingCloud 上部署 Kasten K10 来保护云原生应用。

本文重要章节

20211209152459

1. 背景与验证目标

1.1 背景

发展云原生生态圏是 Veeam 的又一重要战略,以 Kasten by Veeam 为圆心,这个战略又分为三个重要的组成部分,公有云厂商、K8S 分发版本和云原生存储厂商。大家都知道在云原生的领域中,公有云的K8S分发版本是市场占有率最高的,Veeam China 在中国的云原生生态战略部局中也积极在与国内多家公有云厂商合作。青云容器引擎 KubeSphere 是在 Kubernetes 之上构建的以应用为中心的多租户容器平台,完全开源,支持多云与多集群管理,提供全栈的 IT 自动化运维的能力,简化企业的 DevOps 工作流。KubeSphere 提供了运维友好的向导式操作界面,帮助企业快速构建一个强大和功能丰富的容器云平台。

1.2 验证目标

在本次验证场景中,我们将结合 QingStor CSI 容器存储解决方案保护云原生应用的方式。

  • 利用 Kubestr 对云原生存储进行评测
  • 利用 K10 对存储 CSI API 进行调用生成快照,达成最快速的 RPO 与 RTO的备份与恢复
  • 利用 QingStor 对象存储,将快照数据导出到对象存储桶上,实现了异地容灾与数据长期保留

达成效果:

  1. 利用 QingStor CSI 快照,在本地 Kubenetes 环境,云原生应用的快速备份与恢复(利用CSI快照)
  2. 利用 QingStor 对象存储,在本地形成长期保留
  3. 利用 Kasten K10 直接将数据容灾到远端,或利用 QingStor 对象存储实现存储桶的复制,实现 3-2-1-1-0 的数据保护。

20211209151831

2. Kasten 与 青云 KubeSphere

Kasten K10 是 Veeam 在 Kubernetes 平台的数据管理解决方案,通过部署 Kasten K10 企业可以安全地备份和还原、执行灾难恢复以及迁移云原生的应用。Kubernetes 集群资源和持久卷等存储资源。解决用户备份、灾难恢复、迁移过程中的数据管理问题,提高云原生环境数据管理的便捷性,帮助用户降低灾备成本,提高生产执行效率。

20210821143120

KubeSphere 是在 Kubernetes 之上构建的以应用为中心的多租户容器平台,完全开源,支持多云与多集群管理,提供全栈的 IT 自动化运维的能力,简化企业的 DevOps 工作流。KubeSphere 提供了运维友好的向导式操作界面,帮助企业快速构建一个强大和功能丰富的容器云平台。

20210821143350

3.Kasten K10 部署规划

3.1 技术资源准备与要求

Kasten K10 部署在青云需要以下先决条件 :

  • QingCloud KubeSphere Engine (QKE) 青云 QKE 容器引擎是高性能的企业级 Kubernetes 集群,KubeSphere 是在 Kubernetes 之上构建的以应用为中心的多租户容器平台,完全开源,支持多云与多集群管理,提供全栈的 IT 自动化运维的能力,简化企业的 DevOps 工作流。
  • 青云平台镜像仓库(Docker Hub) 为您提供快速、稳定的 Docker 镜像集中存储与分发服务。您可以创建多个 Docker 命名空间和多个 Docker 用户,灵活地管理您的 Docker 镜像。镜像仓库的域名是 dockerhub.qingcloud.com。
  • QingStor-CSI组件 QingStor-CSI 组件支持 QKE 集群通过控制台快捷选择存储类型,并创建对应块存储云硬盘类型的 PV 和 PVC。
  • QingStor 对象存储, 用于存放备份的数据集,在本实例中也用于存储部署 Kasten K10 的自动化检测脚本
  • KubeSphere 控制台 EIP(可选) 如果希望通过公网 LoadBalancer 方式访问 KubeSphere 控制台,可在此选择可用的 EIP,将为此 EIP 自动创建一个负载均衡器并绑定;请保证集群至少有一个工作节点,否则无法通过此方法访问 KubeSphere 控制台;如果没安装 KubeSphere,无需设置此参数
  • K8s apiserver EIP(可选) 如果希望通过公网访问 K8s apiserver,请在此处填写可用的 Kubernetes EIP ID,系统将会自动创建一个 LB 并绑定此 EIP
  • VPC 的EIP(可选) 如果希望K8S clustr有上行访问公网的能力 ,需要配置 VPC 的 EIP以链接到公网。
  • 技术人员要求 部署人员除了对云基础架构有一定了解以外,还应该具备 K8S 或 QKE、KubeSphere 运维的相关知识。

3.2 K8S 集群资源需求

对于 Kasten K10 在 QKE 容器平台环境的部署,Kasten K10 将需要以下资源,鉴于 K10 所保护的应用数量不同,对应的数值也做相应的调整。

资源需求
K10 的资源需求总是与 Kubernetes 集群中的应用程序数量和正在执行的数据管理任务类型有关(例如,快照与备份)。一些资源需求是静态的,我们称之为基本资源需求,而其他资源的占用仅在完成某些数据管理工作时才被需要,因此我们称之为动态资源需求。K10 的自动扩展特性确保了在不执行任何工作时,动态需求资源的消耗缩减为零。虽然以下资源需求与限制的建议适用于大多数 K8S 集群,但需注意的是,最终需求将取决于您的集群和应用程序规模、数据总量、文件大小、分布和数据变化率。比较科学的方式是通过 Prometheus 或 Kubernetes Vertical Pod Autoscaling (VPA) 来检查您的资源需求。

需求类型

我们将需求分为三种类型,即基本工作需求,备份工作需求和灾难恢复需求,并做以下陈述:

  • 基本工作需求:这些是 K10 的内部调度和清理服务所需的资源,主要由监控和目录规模需求驱动。这些基本要求的资源占用通常是静态的,通常不会随着受保护的 Kubernetes 资源数量或受保护应用程序数量的增长而显着增长。

  • 备份工作需求:当数据从卷快照传输到对象存储或 NFS 文件存储时,需要调用备份工作所需的资源。虽然备份需求取决于您的数据量、变化率和文件系统布局,但这些需求并非没有限制,很容易适应相对廋供给的资源范围。当然在提供额外资源时,K10 还可以加快备份操作的完成。为了在保护大量工作负载时防止无限并行,K10 限制了同时备份作业的数量(默认为 9 个任务并行)。备份资源占用是动态的,在不执行备份时会缩减为零。

  • 灾难恢复需求:这些需求是在执行 K10 安装的灾难恢复所需的资源,主要用于压缩、重复数据删除、加密以及将 K10 目录传输到对象存储。提供额外资源还可以加快 DR 操作。DR 资源占用是动态的,并且在不执行 DR 时会缩减为零。

需求配置指南
下表列出了保护 100 个云原生应用程序或命名空间的 K10 安装的资源要求。需要注意的是,DR 作业也包含在最大并行度限制中,因此您只能 N 同时拥有备份作业 或 N-1 备份作业 + 1 个 DR 作业同时进行。

Type Requested CPU (Cores) Limit CPU (Cores) Requested Memory (GB) Limit Memory (GB)
Base 1 2 1 4
Dynamic (per parallel job) 1 1 0.4 0.4
DR 1 1 0.3 0.3
Total 3 4 1.8 4.8

4. 部署青云 Kubernetes 环境

4.1 部署青云 QKE 与 KubeSphere 集群管理器

创建集群 Kubernetes 服务

20211205194021

配置完毕可到集群管理中查看集群的状态

20211205200624

4.2 配置青云 QKE 集群的访问路径

在本实例中,我们需要通过公网访问青云的 QKE 集群,我们只要下载下图的kubeconifg 到 $HOME/.kube/config 就好了。

#获取集群信息
❯ kubectl config get-contexts 
CURRENT   NAME                          CLUSTER      AUTHINFO           NAMESPACE
*         kubernetes-admin@kubernetes   kubernetes   kubernetes-admin   

❯ kubectl get nodes -owide
NAME          STATUS   ROLES                  AGE   VERSION   INTERNAL-IP   EXTERNAL-IP   OS-IMAGE             KERNEL-VERSION       CONTAINER-RUNTIME
master1       Ready    control-plane,master   29m   v1.20.6   172.16.0.5    <none>        Ubuntu 18.04.6 LTS   4.15.0-162-generic   docker://20.10.6
worker-p001   Ready    worker                 27m   v1.20.6   172.16.0.3    <none>        Ubuntu 18.04.6 LTS   4.15.0-162-generic   docker://20.10.6
worker-p002   Ready    worker                 27m   v1.20.6   172.16.0.2    <none>        Ubuntu 18.04.6 LTS   4.15.0-162-generic   docker://20.10.6

#获取集群硬件配置
❯ kubectl describe nodes | grep -E 'Hostname|cpu|memory|ephemeral-storage'

  Hostname:    master1
  cpu:                4
  ephemeral-storage:  82045336Ki
  memory:             8167476Ki

  Hostname:    worker-p001
  cpu:                8
  ephemeral-storage:  82045336Ki
  memory:             16424260Ki

  Hostname:    worker-p002
  cpu:                8
  ephemeral-storage:  82045336Ki
  memory:             16424260Ki

4.3 部署 QingStor 对象存储

对象存储做为存储库,用于放置云原生应用的备份集

20211205202226

4.4 配置青云平台镜像仓库(Docker Hub)

确保镜像仓库(Docker Hub)配置完善, 镜像库的搭建十分重要。

详细情况请查看 Mars 之前的博客

20211205202511

4.5. 启用 QingStor CSI 与配置 snapshot 到 K10 插件

检查 api-versions 中与存储和快照相关的内容

❯ kubectl api-versions |grep storage
snapshot.storage.k8s.io/v1beta1
storage.k8s.io/v1
storage.k8s.io/v1beta1
storage.kubesphere.io/v1alpha1

建立快照类,设置为 K10 默认联动快照类型

❯ vim qingstor-snapshotter.yaml 
apiVersion: snapshot.storage.k8s.io/v1beta1
kind: VolumeSnapshotClass
metadata:
  annotations:
    k10.kasten.io/is-snapshot-class: "true"
  name: qingstor-snapshotter
driver: csi-qingcloud
deletionPolicy: Delete

❯ kubectl apply -f qingstor-snapshotter.yaml 
volumesnapshotclass.snapshot.storage.k8s.io/qingstor-snapshotter created

❯ kubectl get volumesnapshotclass
NAME                   DRIVER          DELETIONPOLICY   AGE
qingstor-snapshotter   csi-qingcloud   Delete           4m46s

为默认存储类配置 K10 快照联动功能

❯ kubectl get sc
NAME                          PROVISIONER     RECLAIMPOLICY   VOLUMEBINDINGMODE   ALLOWVOLUMEEXPANSION   AGE
csi-high-capacity (default)   csi-qingcloud   Delete          Immediate           true                   101m
csi-high-capacity-legacy      csi-qingcloud   Delete          Immediate           true                   101m
csi-high-perf                 csi-qingcloud   Delete          Immediate           true                   101m
<truncated..>

❯ kubectl annotate storageclass csi-high-capacity k10.kasten.io/volume-snapshot-class=qingstor-snapshotter
storageclass.storage.k8s.io/csi-high-capacity annotated

5. 用 Kasten kubestr 对 QingStor 云原生存储进行评测

Kubestr 是一个简单的轻量级云原生存储跑分工具,用于评估集群中的存储选项。它可以帮助您发现、验证和评估 您的云原生存储,以明确当前配置的状态与存储能力是否满足应用的要求。当比较跨多个集群、云平台与存储选项的性能时,还可以通过切换 Kubeconfig 使其跨多个集群运行。

5.1. Kubestr 的安装

下载 Kubestr, 从如下链接可以直接下载您所需要的 Kubestr 版本

https://github.com/kastenhq/kubestr/releases/tag/v0.4.17

20210628183141

用 wget 可以直接获取 Kubestr 软件包, 并解包

$ wget https://github.com/kastenhq/kubestr/releases/download/v0.4.17/kubestr-v0.4.17-linux-amd64.tar.gz

$ tar -zxvf kubestr-v0.4.17-linux-amd64.tar.gz
LICENSE
README.md
kubestr

5.2. 检查 Kubenetes 环境 与 Storage Provisioners

$ ./kubestr 
**************************************
  _  ___   _ ___ ___ ___ _____ ___
  | |/ / | | | _ ) __/ __|_   _| _ \
  | ' <| |_| | _ \ _|\__ \ | | |   /
  |_|\_\\___/|___/___|___/ |_| |_|_\
Explore your Kubernetes storage options
**************************************
Kubernetes Version Check:
  Valid kubernetes version (v1.20.6)  -  OK
RBAC Check:
  Kubernetes RBAC is enabled  -  OK
Aggregated Layer Check:
  The Kubernetes Aggregated Layer is enabled  -  OK
Available Storage Provisioners:
  csi-qingcloud:
    This might be a CSI Driver. But it is not publicly listed.
    Storage Classes:
      * csi-high-capacity
      * csi-high-capacity-legacy
      * csi-high-perf
      * csi-neonsan
      * csi-ssd-enterprise
      * csi-standard
      * csi-super-high-perf
    To perform a FIO test, run-
      ./kubestr fio -s <storage class>

5.3. 进行快照功能测试

经过 Kubestr 测试,可以看到 QingStor CSI 快照功能与Kasten 联动正常,详细情况见如下的测试结果

❯ ./kubestr csicheck -s csi-high-capacity -v qingstor-snapshotter
Creating application
  -> Created pod (kubestr-csi-original-podpt79w) and pvc (kubestr-csi-original-pvcpjqvc)
Taking a snapshot
  -> Created snapshot (kubestr-snapshot-20211209141701)
Restoring application
  -> Restored pod (kubestr-csi-cloned-pod2p8bv) and pvc (kubestr-csi-cloned-pvcff52v)
Cleaning up resources
CSI checker test:
  CSI application successfully snapshotted and restored.  -  OK

5.4. 对 CSI 存储进行性能测试

性能测试的默认用例将涉及如下场景,同时默认的存储性能测试会创建一个100G的卷, 如果您希望调整测试场景与卷大小,可使用 -f 来写配置文件, -z 选项来指定卷的大小。详细情况见如下的帮助提示。

  • blocksize=4K filesize=2G iodepth=64 rw=randread
  • blocksize=4K filesize=2G iodepth=64 rw=randwrite
  • blocksize=128K filesize=2G iodepth=64 rw=randread
  • blocksize=128k filesize=2G iodepth=64 rw=randwrite
$ ./kubestr fio -s csi-high-capacity
PVC created kubestr-fio-pvc-54s7n
Pod created kubestr-fio-pod-b472n
Running FIO test (default-fio) on StorageClass (csi-high-capacity) with a PVC of Size (100Gi)
Elapsed time- 57.851431502s
FIO test results:

FIO version - fio-3.20
Global options - ioengine=libaio verify=0 direct=1 gtod_reduce=1

JobName: read_iops
  blocksize=4K filesize=2G iodepth=64 rw=randread
read:
  IOPS=1461.274292 BW(KiB/s)=5861
  iops: min=748 max=2106 avg=1473.066650
  bw(KiB/s): min=2992 max=8424 avg=5892.266602

JobName: write_iops
  blocksize=4K filesize=2G iodepth=64 rw=randwrite
write:
  IOPS=665.825806 BW(KiB/s)=2680
  iops: min=368 max=998 avg=667.733337
  bw(KiB/s): min=1472 max=3992 avg=2670.933350

JobName: read_bw
  blocksize=128K filesize=2G iodepth=64 rw=randread
read:
  IOPS=856.020569 BW(KiB/s)=110102
  iops: min=468 max=994 avg=862.266663
  bw(KiB/s): min=59904 max=127232 avg=110370.132812

JobName: write_bw
  blocksize=128k filesize=2G iodepth=64 rw=randwrite
write:
  IOPS=486.629242 BW(KiB/s)=62820
  iops: min=174 max=926 avg=487.733337
  bw(KiB/s): min=22272 max=118528 avg=62429.867188

Disk stats (read/write):
  vdh: ios=40399/19856 merge=0/389 ticks=1607052/554588 in_queue=2157716, util=99.813736%
  -  OK

6. 安装 Kasten K10 到青云 QKE

6.1. 就绪检查 Pre-Flight Checks

通过 Pre-Flight Checks 脚本,我们可以验证部署的前提条件是否满足,在国内区域我们可以将脚本部署在 QingStor 存储桶中,如下图。

20211209111647

您自己也可以自己按照自身的环境定义您这个脚本,注意以下的修改项目

$ curl -O https://docs.kasten.io/tools/k10_primer.sh | bash

$ vim k10_primer.sh  
~~~
    if version_gt_eq ${k10ver} ${MIN_K10_VERSION}; then
      image=gcr.io/kasten-images/k10tools:${k10ver}     # 把这一行改成 dockerhub.qingcloud.com/kasten/k10tools
    else
~~~

执行 Pre-Flight Checks,查看结果,让我们分析一下


$ curl https://kasten-beijing.pek3b.qingstor.com/k10_primer.sh | bash
  % Total    % Received % Xferd  Average Speed   Time    Time     Time  Current
                                 Dload  Upload   Total   Spent    Left  Speed
100  7058  100  7058    0     0  20765      0 --:--:-- --:--:-- --:--:-- 21584
Namespace option not provided, using default namespace
# 检查所需要的工具 kubectl 和 helm
Checking for tools
 --> Found kubectl
 --> Found helm
Checking if the Kasten Helm repo is present
 --> The Kasten Helm repo was found
Checking for required Helm version (>= v3.0.0)
 --> No Tiller needed with Helm v3.6.1
# K10Primer image 已经重新定向
K10Primer image
 --> Using Image (dockerhub.qingcloud.com/kasten/k10tools:4.5.4) to run test
Checking access to the Kubernetes context kubernetes-admin@kubernetes
 --> Able to access the default Kubernetes namespace
K10 Kanister tools image
 --> Using Kanister tools image (dockerhub.qingcloud.com/kasten/kanister-tools:k10-0.69.0) to run test
# 创建 k10Primer pod 运行检查程序 

Running K10Primer Job in cluster with command- 
     ./k10tools primer 
serviceaccount/k10-primer created
clusterrolebinding.rbac.authorization.k8s.io/k10-primer created
job.batch/k10primer created
Waiting for pod k10primer-wf6zg to be ready - ContainerCreating
Waiting for pod k10primer-wf6zg to be ready - ContainerCreating
Pod Ready!
# 版本支持
Kubernetes Version Check:
  Valid kubernetes version (v1.20.6)  -  OK
# 访问权限检查 
RBAC Check:
  Kubernetes RBAC is enabled  -  OK
# Aggregated Layer
Aggregated Layer Check:
  The Kubernetes Aggregated Layer is enabled  -  OK

# CSI存储集成检查 
CSI Capabilities Check:
  Using CSI GroupVersion snapshot.storage.k8s.io/v1beta1  -  OK

Validating Provisioners: 
csi-qingcloud:
  Is a CSI Provisioner  -  OK
  Storage Classes:
    csi-high-capacity
      Valid Storage Class  -  OK
    csi-high-capacity-legacy
      Valid Storage Class  -  OK
    csi-high-perf
      Valid Storage Class  -  OK
    csi-neonsan
      Valid Storage Class  -  OK
    csi-ssd-enterprise
      Valid Storage Class  -  OK
    csi-standard
      Valid Storage Class  -  OK
    csi-super-high-perf
      Valid Storage Class  -  OK
  Volume Snapshot Classes:
    qingstor-snapshotter
      Has k10.kasten.io/is-snapshot-class annotation set to true  -  OK
      Has deletionPolicy 'Delete'  -  OK
# 检查通用卷影快照
Validate Generic Volume Snapshot:
  Pod Created successfully  -  OK
  GVS Backup command executed successfully  -  OK
  Pod deleted successfully  -  OK
# 清场。。。
serviceaccount "k10-primer" deleted
clusterrolebinding.rbac.authorization.k8s.io "k10-primer" deleted
job.batch "k10primer" deleted

6.2 安装 Kasten K10 到 QKE 集群

1. 获取 Helm Chart 供本地使用

添加 Kasten Helm charts 存储库
$ helm repo add kasten https://charts.kasten.io/

$ helm repo list   
NAME            URL   ls
kasten          https://charts.kasten.io/         

$ helm repo update
# 以下这条命令会把 k10-4.0.x.tgz 包下载下来,如果不加任何参数,则会下载最新的版本
# 在Air Gapped 的环境中安装时,可以先行下载再使用。
$ helm fetch kasten/k10 --version=4.5.4
Hang tight while we grab the latest from your chart repositories...
...Successfully got an update from the "kasten" chart repository
Update Complete. ⎈Happy Helming!⎈

2.建立名空间

$ kubectl create namespace kasten-io
namespace/kasten-io created

3. 安装 Kasten K10

在选择青云 qingstor-csi 的云硬盘时,有个最小为 10GB 的限制,对于 Kasten 来说,有些 PVC 的要求仅为 1GB ,所以我们将其更改为 10G 以上为青云部署作适配, 同时配置的参数还有为扩展 gateway 的 LB 用于外网访问 Kasten 图形界面。

helm install k10 k10-4.5.4.tgz --namespace kasten-io --set global.airgapped.repository=dockerhub.qingcloud.com/kasten \
  --set global.persistence.metering.size=20Gi \
  --set prometheus.server.persistentVolume.size=20Gi \
  --set global.persistence.catalog.size=20Gi \
  --set auth.basicAuth.enabled=true \
  --set auth.basicAuth.htpasswd='mars:$apr1$Cgu1sGVZ$w/8aLHZkVT73OqYZ06C0v.' \
  --set externalGateway.create=true \
  --set metering.mode=airgap \
  --set global.persistence.storageClass=csi-high-capacity

目前在不同的 K8S 环境下部署 K10 有很多参数需要设置,此时我们需要查阅部署参数。

查看 Kasten Helm 部署的参数
Complete List of K10 Helm Options
https://docs.kasten.io/latest/install/advanced.html

4. 确认 Kasten K10 Pod 的部署情况

$ kubectl get pods -n kasten-io 
NAME                                  READY   STATUS    RESTARTS   AGE
aggregatedapis-svc-688c8cf4dd-fwm2n   1/1     Running   0          5h9m
auth-svc-6f49c98d89-425hr             1/1     Running   0          5h9m
catalog-svc-6bf9b4d6c-p52js           2/2     Running   0          5h9m
config-svc-79986d4b65-hlns4           1/1     Running   0          5h9m
crypto-svc-5bcf79d5d7-kldzb           2/2     Running   0          5h9m
dashboardbff-svc-679d4b7999-hvx4n     1/1     Running   0          5h9m
executor-svc-55b7db676b-hf5dp         2/2     Running   0          5h9m
executor-svc-55b7db676b-j96wn         2/2     Running   0          5h9m
executor-svc-55b7db676b-wqgt4         2/2     Running   0          5h9m
frontend-svc-5b854bdd79-k4529         1/1     Running   0          5h9m
gateway-5bd849ff-x5j8q                1/1     Running   0          5h9m
jobs-svc-58695b74f9-vgv64             1/1     Running   0          5h9m
k10-grafana-7d7c6c46d-djhvz           1/1     Running   0          5h9m
kanister-svc-6cf8997594-qvntl         1/1     Running   0          5h9m
logging-svc-7fcbb994dd-hpcnd          1/1     Running   0          5h9m
metering-svc-854b899698-927bn         1/1     Running   0          5h9m
prometheus-server-fc8fb9bb7-xmdsc     2/2     Running   0          5h9m
state-svc-856458c47f-572h7            1/1     Running   0          5h9m

5. 访问 K10 控制台

通过查看 Kasten Service,我们可以看到 K10 的 ingress 配置,其中的 Gateway-ext ,中可以查看到外网的访问 K10 的 IP 地址。

❯ kubectl get svc -n kasten-io
gateway                 ClusterIP      10.96.89.34     <none>           8000/TCP                       39m
gateway-admin           ClusterIP      10.96.128.91    <none>           8877/TCP                       39m
gateway-ext             LoadBalancer   10.96.105.201   139.198.18.152   80:31164/TCP                   39m

浏览器访问如下地址,就可看到 K10 的管理界面
http://139.198.18.152/k10/#/

20211209112257

如果设置不成功,需要手动设置 external gateway,命令行会有如下提示, 公网 IP 为 pending 状态 ,这时就需要手动配置 gateway 外网访问的服务。

❯ kubectl get svc -n kasten-io
gateway                 ClusterIP      10.96.89.34     <none>        8000/TCP                       31m
gateway-admin           ClusterIP      10.96.128.91    <none>        8877/TCP                       31m
gateway-ext             LoadBalancer   10.96.105.201   <pending>     80:31164/TCP                   31m

我们登录 KubeSphere 的控制台,找到 Kasten 的 gateway-ext 服务,点击“编辑外网访问”

20211209105825

添加名为 service.beta.kubernetes.io/qingcloud-load-balancer-eip-ids 的键,其值设置为 EIP 的 id。

20211209110840

有关 Kubesphere Service 外网访问请参考如下文档
《Kubesphere Service 外网访问》
https://v2-1.docs.kubesphere.io/docs/zh-CN/project-setting/project-gateway/

7. 配置青云 QingStor 对象存储作为备份库

我们可以能过设置 S3 Compatible 存储库的方式,将青云 QingStor 对象存储设置成为备份存储库,满足 3-2-1-1-0 的备份黄金法则。
注意,QingStor 对象存储支持 S3 兼容模式,访问形式为每个 Zone 提供一个 s3 的子域:

Virtual-host Style: <bucket_name>.s3.<zone_id>.qingstor.com/<object_key>
Path Style: s3.<zone_id>.qingstor.com/<bucket_name>/<object_key>

点击 Settings -> Locations -> New Profile 新建云存储库

20211209115426

存储库连接建立好,如下图

20211209115937

8. 云原生应用的备份与还原

8.1 云原生应用的备份

点击 Create Policy, 让我们创建一个数据备份策略,在这个数据保护策略中 Kasten 不仅创建本地的快照对应用进行保护,还会将应用数据备份到青云 QingStor 对象存储,以实现数据的长期保留

20211209120925

点击 Run Once 执行备份任务

20211209120949

观察 Dashboard 可以看到应用已经备份完成

20211209121549

观察 QingStor 的存储快照, k10-csi-snap 开头的就是 Kasten 生成的快照

20211209123110

观察 QingStor 存储桶,说明快照数据已经 Export 到存储桶了

20211209123223

8.2 云原生应用的还原

在 Dashboard 中找到 Applications 点击 Restore

20211209130848

选择还原的时间点

20211209130923

新建一个 Namespace 进行还原,这里我们命名为 mysql-restore

20211209131123

在控制台观察还原操作已经顺利完成

20211209132006

在青云 KubeSphere 控制台中我们已经看到还原的应用在正常的运行了

20211209132108

8.3 利用 QingStor 存储桶复制的方法避免逻辑错误

在日常运维过程中,有时会因为人为的原因导致本地的存储桶数据丢失。这时我们可以使用 QingStor 对象存储的桶复制功能,直接将存储桶的数据复制到远端,在设置桶复制规则时,可以设置为禁用删除操作,这样我们就可以避免人为或逻辑错误,从远端的存储桶恢复数据了。复制规则在 跨区域复制 中进行定义

20211209132322

这样在恢复时,我们只要选择 Alternate Location Profile 并选择目标存储桶即可,本次的实验环境,与操作方法如下:

条目 Bucket Name Region 访问链接
源端存储桶 kasten-beijing 北京3区 https://kasten-beijing.pek3b.qingstor.com
目标端存储桶 kasten-shanghai 上海1区 https://kasten-shanghai.sh1a.qingstor.com
  1. 添加上海区域的存储桶

20211209133037

添加完毕如下图所示

20211209133103

  1. 在恢复时,我们只要选择 Alternate Location Profile 并选择目标存储桶 kasten-shanghai

20211209133341

  1. 在青云 KubeSphere 控制台中我们已经看到还原的应用在正常的运行了

20211209141446

9. 总结

随着云原生生态的越发成熟,越来越多的企业将有状态的工作负载部署到青云 KubeSphere 集群里,Kasten K10 by Veeam 解决方案 ,利用青云的 KubeSphere 生态环境中的多项目云服务,Dockerhub 镜像库, QingStor 对象存储, QingStor CSI 容器存储接口, 打造了基于青云的原生环境的数据管理平台,可助力企业达成云原生应用灾备、迁移和 DevOps 等目标,从而保证了企业云原生应用的弹性和可靠性。

10. 参考链接

Complete List of K10 Helm Options
https://docs.kasten.io/latest/install/advanced.html
Kasten k10 实战系列 03 CSI 存储快照适配
http://www.data2clouds.com/index.php/archives/33/
Kasten K10 实战系列 02 - 利用腾讯 TCR 搭建镜像库
http://www.data2clouds.com/index.php/archives/32/
参考 Helm3 部署安装
https://cloud.tencent.com/developer/article/1705549
Helm3 releases
https://github.com/helm/helm/releases
Kasten K10 系统需求
https://docs.kasten.io/latest/operating/footprint.html
青云 KubeSphere 容器引擎(QingCloud Kubernetes Engine
https://www.qingcloud.com/products/kubesphereqke/
关于 QingCloud csi 请参考如下文档
https://kubesphere.io/zh/docs/installing-on-linux/persistent-storage-configurations/install-qingcloud-csi/

Kasten k10 提高系列3 – Kasten k10 多集群管理器

1.前言

在不断增长的 Kubernetes 多租户和多集群环境中,统一进行数据管理的操作,如备份和灾难恢复是纷繁复杂的。根据行业消息,大约有 20% 的企业生产环境中 Kubernetes 部署规模已经超越了 50 个 Kubernetes 集群,预计到 2021 年会更加速采用。

Kasten k10 by Veeam 从 v3.0 版本开始引入多集群管理支持,并可扩展到多租户环境。这一功能的引入满足了客户的需求,提高了生产力。在本篇文章中我将进一步解释 Kasten K10 多集群管理器的应用。

[TOC]

1.前言

  1. Kasten k10 多集群管理器的定义
  2. Kasten k10 多集群管理器特性
  3. k10multicluster 工具的使用
  4. 关于的 Primary 实例的参数设置
  5. 准备工作 - kubeconfig 的定义
  6. 启用多集群管理
    • 7.1 配置主实例
    • 7.2 绑定从属实例
    • 7.3 删除从属实例(如果需要)
  7. 设置 RBAC Entries
  8. Multi-Cluster 多集群管理操作
    • 9.1 集群切换
    • 9.2 创建 Global K10 Resources
  9. 总结
    参考文献
    附录

2. Kasten k10 多集群管理器的定义

K10 多集群管理器简化了跨多个 Kubernetes 集群的 K10 操作。管理员定义其 K10 实例之间的主从关系。Primary Cluster 的 K10 实例为管理员提供单一入口和仪表板来管理辅助实例,K10 资源,如策略和配置文件等,在主实例中定义并分发到辅助实例,为辅助实例制定其策略,并使辅助实例的操作和指标汇总在主要实例中。

3. Kasten k10 多集群管理器特性

Kasten K10 多集群管理器可以快速部署,且易于使用。通过 K10 多集群管理器仪表板,用户可以实现高度自动化和云原生应用的可移植性。因此云和运营团队可以更有信心地确保生产力、可扩展性和安全性。Kasten k10 多集群管理器特性包括:

多集群仪表板视图
当存在多个集群时,K10 多集群仪表板可提供简单的方法来获取关键参数,以形成聚合与实时的数据状态,包括集群总数、策略、应用程序等。

指定集群视图切换
K10 能够轻松搜索单个集群并无缝切换到该集群以查看集群相关资源的其他视图,以及定义和操作特定于该集群的策略的能力。

K8S 原生安全认证
K10 支持多种认证方式,包括 Token-based、OIDC、Red Hat OpenShift OAuth Proxy 等,因此可以使用细粒度的基于角色的访问控制 (RBAC) 来确保适当的访问级别和集群内与集群间的行动。

跨多集群策略实施
K10 提供了在主集群上定义全局策略的能力,这些策略可以有选择地应用于辅助集群,以通过自动化简化大规模备份的管理。

按需定义集群分组
利用 K10 用户能够创建自己的分组和属于多个发行版的单个集群。这使得只需单击一个按钮即可轻松地将全局策略分发到任何逻辑集群组。

4. k10multicluster 工具的使用

k10multicluster Cluster 管理的工具,我们需要在 Github 网站 kastenhq/external-tools 中下载,注意,目前 Kasten 最新版本为 4.0.8。 在使用时,请下载与你的 K10 版本相匹配的 Version

下载地址如下:

Kasten k10multicluster Tools
https://github.com/kastenhq/external-tools/releases

下载后我们需要将这个工具赋予执行的能力,并放到 /usr/local/bin/ 中以便随时都可以调用。

$ mv k10multicluster_4.0.5_linux_amd64 k10multicluster
$ sudo chmod +x k10multicluster
$ sudo cp k10multicluster /usr/local/bin/k10multicluster

5. 关于的 Primary 实例的参数设置

注意在 Primary 安装时,一定设置为 --set auth.basicAuth.enabled=true , 这样进入到 管理器中,将是 k10-admin 用户

helm install k10 k10-4.0.5.tgz --namespace kasten-io --set global.airgapped.repository=ccr.ccs.tencentyun.com/kasten-k10 \
  --set global.persistence.metering.size=20Gi \
  --set prometheus.server.persistentVolume.size=20Gi \
  --set global.persistence.catalog.size=20Gi \
  --set externalGateway.create=true \
  --set auth.basicAuth.enabled=true \
  --set auth.basicAuth.htpasswd='mars:$apr1$Cgu1sGVZ$w/8aLHZkVT73OqYZ06C0v.' \
  --set metering.mode=airgap \
  --set injectKanisterSidecar.enabled=true \
  --set-string injectKanisterSidecar.namespaceSelector.matchLabels.k10/injectKanisterSidecar=true \
  --set global.persistence.storageClass=cbs-csi

当然,对于已经安装好 K10 的环境是不用重装的, 我们用 helm upgrade 加相关参数即可。

# Upgrade 之前把目前的 parameters 都导入到 yaml 文件中
$ helm get values k10 --output yaml --namespace=kasten-io > k10_val.yaml

# 之后再 
$ helm upgrade k10 k10-<版本号>.tgz --namespace=kasten-io -f k10_val.yaml \ 
# 后面接入要加的参数即可
  --set auth.basicAuth.enabled=true \
  --set auth.basicAuth.htpasswd='mars:$apr1$Cgu1sGVZ$w/8aLHZkVT73OqYZ06C0v.' \

6. 准备工作 - kubeconfig 的定义

kubeconfig 是用于配置集群访问信息的文件,在开启了 TLS 的集群中,每次与集群交互时都需要身份认证,生产环境一般使用证书进行认证,其认证所需要的信息会放在 kubeconfig 中。此外,k8s 的组件都可以使用 kubeconfig 连接 apiserver,client-go 、operator、helm 等,其他组件也使用 kubeconfig 访问 apiserver。如下图,Mars的环境中有两个 K8s cluster。我将它们的两个文件分别放置在 cls1-config 与 cls2-config 中

20210727215730

# kubeconfig 列表
$ ls -l $HOME/.kube/ 
-rw-r--r--  1 zhangcong  staff  5545 Jul 27 19:54 cls1-config
-rw-r--r--  1 zhangcong  staff  5545 Jul 27 19:55 cls2-config

# 查看 cls-0gbjg2c9 即 k8s-cls1 的 kubeconfig 文件
kubectl config view --kubeconfig=$HOME/.kube/cls1-config  
apiVersion: v1
clusters:
- cluster:
    certificate-authority-data: DATA+OMITTED
    server: https://cls-0gbjg2c9.ccs.tencent-cloud.com
  name: cls-0gbjg2c9
contexts:
- context:
    cluster: cls-0gbjg2c9
    user: "100006537440"
  name: cls-0gbjg2c9-100006537440-context-default
current-context: cls-0gbjg2c9-100006537440-context-default
kind: Config
preferences: {}
users:
- name: "100006537440"
  user:
    client-certificate-data: REDACTED
    client-key-data: REDACTED

# 查看 cls-dyz4mksf 即 k8s-cls2 的 kubeconfig 文件
kubectl config view --kubeconfig=$HOME/.kube/cls2-config
apiVersion: v1
clusters:
- cluster:
    certificate-authority-data: DATA+OMITTED
    server: https://cls-dyz4mksf.ccs.tencent-cloud.com
  name: cls-dyz4mksf
contexts:
- context:
    cluster: cls-dyz4mksf
    user: "100006537440"
  name: cls-dyz4mksf-100006537440-context-default
current-context: cls-dyz4mksf-100006537440-context-default
kind: Config
preferences: {}
users:
- name: "100006537440"
  user:
    client-certificate-data: REDACTED
    client-key-data: REDACTED

7. 启用多集群管理

7.1 配置主实例

配置您需要做为主实例的集群,将 K8S Cluster 的 context 与 Name 做为参数。

k10multicluster setup-primary \
--kubeconfig=$HOME/.kube/cls1-config \
--context=cls-0gbjg2c9-100006537440-context-default \
--name=cls-0gbjg2c9

Bootstrapping Primary Cluster...
Getting Primary Cluster Config...
Verifying cluster parameters: cls-0gbjg2c9
Setting up primary multicluster configuration: cls-0gbjg2c9
Setting up Primary Cluster Complete!

7.2 绑定从属实例

绑定您需要做为从属实例的集群,将 K8S Cluster 的 context 与 Name 和 ingress 做为参数,注意将 tls 设置为 insecure 是在初始化是加大成功率的,在投入生产后需要恢复成安全设置。

$ k10multicluster bootstrap \  
  --primary-context=cls-0gbjg2c9-100006537440-context-default  \
  --primary-name=cls-0gbjg2c9 \
  --primary-kubeconfig=$HOME/.kube/cls1-config \
  --secondary-context=cls-dyz4mksf-100006537440-context-default \
  --secondary-name=cls-dyz4mksf \
  --secondary-kubeconfig=$HOME/.kube/cls2-config \
  --secondary-cluster-ingress=http://111.231.213.171/k10/#/ \
  --secondary-cluster-ingress-tls-insecure=true

Bootstrapping Clusters...
Getting Primary Cluster Config...
Verifying cluster parameters: cls-0gbjg2c9
Getting Secondary Cluster Config...
Verifying cluster parameters: cls-dyz4mksf
Setting up secondary multicluster configuration: cls-dyz4mksf
Updating Prometheus configuration: cls-0gbjg2c9
Bootstrapping Clusters Complete!

#查看已经被管理的多个K8S 集群
kubectl get clusters -n kasten-io-mc  
NAME           AGE
cls-0gbjg2c9   70m
cls-dyz4mksf   65m

此时我们可以 Web 界面中直接访问 Clusters 的图形界面,地址如,K10-ingress/10/#/Clusters, 这个界面会将所有被管理的 K8S Cluster 的信息集中展示。

20210727215935

7.3 删除从属实例(如果需要)

$ k10multicluster remove \  
 --primary-context=cls-0gbjg2c9-100006537440-context-default  \
 --primary-name=cls-0gbjg2c9 \
 --primary-kubeconfig=$HOME/.kube/cls1-config \
 --secondary-context=cls-dyz4mksf-100006537440-context-default \
 --secondary-name=cls-dyz4mksf \
  --secondary-kubeconfig=$HOME/.kube/cls2-config

Removing Secondary Cluster...
Getting Primary Cluster Config...
Verifying cluster parameters: cls-0gbjg2c9
Getting Secondary Cluster Config...
Verifying cluster parameters: cls-dyz4mksf
Cleaning up secondary multicluster configuration cls-dyz4mksf from primary cls-0gbjg2c9
Removing Clusters Complete!

8. 设置 RBAC Entries

为其它的 K8S Cluster 设置 RBCA Entries,注意,此时,主实例为基本认证方式,用户为k10-admin,而从属实例为 Token 认证方式,用户为k10-k10。 我们的目的是让从属实例可以被 k10-admin 所管理。

在主界面上,找到 RBCA Entries, 点击 New K10 Cluster Role Binding。
K10 Cluster Role 设置为: K10-multi-cluster-admin
Subjects: User 为 : k10-admin

20210727220626

9. Multi-Cluster 多集群管理操作

9.1 集群切换

您可以方便地在管理界面中切换,被 K10 所保护的 K8S 集群

20210727223407

9.2 创建 Global K10 Resources

通过集群的管理,我们可以统一建立 Global Resources,然后再将其分发,这样就可以节省我们在配置K10作业的时间。

  1. 建立存储库配置

20210727224201

  1. 建立统一的备份策略
    当多个集群中有相同的应用时,我们可以定义统一的备份策略。

20210727224752

  1. 分发备份策略
    分发备份策略的方式有两种:
    一是在如下策略上直接分发
    20210727224838

二是,建立分发策略进行分发
20210727225307

我们可以在建立分发策略时,指定多个 Cluster,如下图 status: synced a few seconds ago. 说明分发已经成功
20210727225345

我们到 Cluster1 上查看备份策略
20210727225500

我们再到 Cluster2 上查看备份策略
20210727225740

策略运行后的结果

20210727231513

10.总结

Kasten k10 的多实例管理功能,可使您可以在 K10 仪表板中快速轻松地定义策略、管理多个集群并查看整个 Kubernetes 部署队列中的关键参数状态,在不牺牲敏捷性、性能和安全性的情况下,轻松管理更大规模的数据。凭借增强的灵活性和可移植性,帮助 ITOps 和 CloudOps 团队保护和扩展 Kubernetes 部署。

参考文献

Kasten-io Multi-Cluster
https://docs.kasten.io/latest/multicluster/index.html

Kubernetes Multi-cluster and Multi-tenancy with Kasten K10 3.0
https://blog.kasten.io/kubernetes-multi-cluster-and-multi-tenancy-with-kasten-k10

kasten-external-tools
https://github.com/kastenhq/external-tools

附录

查看集群状态

$ kubectl get clusters -n kasten-io-mc -o yaml 
apiVersion: v1
items:
- apiVersion: dist.kio.kasten.io/v1alpha1
  kind: Cluster
  metadata:
    creationTimestamp: "2021-07-27T12:42:43Z"
    generation: 1
    labels:
      dist.kio.kasten.io/cluster-type: primary
    managedFields:
    - apiVersion: dist.kio.kasten.io/v1alpha1
      fieldsType: FieldsV1
      fieldsV1:
        f:status:
          .: {}
          f:id: {}
      manager: config-server
      operation: Update
      time: "2021-07-27T12:42:43Z"
    - apiVersion: dist.kio.kasten.io/v1alpha1
      fieldsType: FieldsV1
      fieldsV1:
        f:metadata:
          f:labels:
            .: {}
            f:dist.kio.kasten.io/cluster-type: {}
        f:spec:
          .: {}
          f:apiserver:
            .: {}
            f:url: {}
          f:k10:
            .: {}
            f:ingress:
              .: {}
              f:url: {}
            f:namespace: {}
            f:releaseName: {}
          f:primary: {}
      manager: k10multicluster
      operation: Update
      time: "2021-07-27T12:42:43Z"
    name: cls-0gbjg2c9
    namespace: kasten-io-mc
    resourceVersion: "6322587134"
    selfLink: /apis/dist.kio.kasten.io/v1alpha1/namespaces/kasten-io-mc/clusters/cls-0gbjg2c9
    uid: 9fde9f76-fcf5-4299-b750-9eb941876fb9
  spec:
    apiserver:
      url: https://cls-0gbjg2c9.ccs.tencent-cloud.com
    k10:
      ingress:
        url: ""
      namespace: kasten-io
      releaseName: k10
    primary: true
  status:
    id: 11b78bf0-39e3-4077-9f0c-9fc5bb035b15
- apiVersion: dist.kio.kasten.io/v1alpha1
  kind: Cluster
  metadata:
    creationTimestamp: "2021-07-27T15:52:03Z"
    generation: 2
    labels:
      dist.kio.kasten.io/cluster-type: secondary
    managedFields:
    - apiVersion: dist.kio.kasten.io/v1alpha1
      fieldsType: FieldsV1
      fieldsV1:
        f:status:
          .: {}
          f:id: {}
      manager: config-server
      operation: Update
      time: "2021-07-27T15:52:03Z"
    - apiVersion: dist.kio.kasten.io/v1alpha1
      fieldsType: FieldsV1
      fieldsV1:
        f:metadata:
          f:labels:
            .: {}
            f:dist.kio.kasten.io/cluster-type: {}
        f:spec:
          .: {}
          f:apiserver:
            .: {}
            f:url: {}
          f:k10:
            .: {}
            f:ingress:
              .: {}
              f:url: {}
            f:namespace: {}
            f:releaseName: {}
          f:secret: {}
      manager: k10multicluster
      operation: Update
      time: "2021-07-27T15:52:03Z"
    name: cls-dyz4mksf
    namespace: kasten-io-mc
    resourceVersion: "6325814295"
    selfLink: /apis/dist.kio.kasten.io/v1alpha1/namespaces/kasten-io-mc/clusters/cls-dyz4mksf
    uid: 672da008-2c93-4f4d-8d12-f0d7f517bf50
  spec:
    apiserver:
      url: https://cls-dyz4mksf.ccs.tencent-cloud.com
    k10:
      ingress:
        url: http://111.231.213.171/k10/#/
      namespace: kasten-io
      releaseName: k10
    secret: cls-dyz4mksf-45xrj
  status:
    id: 2b4aff74-811d-4b16-af76-72a5cdeaa7f7
kind: List
metadata:
  resourceVersion: ""
  selfLink: ""