k8s(14)-- Helm
Helm
地址:https://github.com/helm/helm
Helm 对于 Kubernetes 来说就相当于 yum 对于 Centos 来说,如果没有 yum 的话,我们在 Centos 下面要安装一些应用程序是极度麻烦的,同样的,对于越来越复杂的 Kubernetes 应用程序来说,如果单纯依靠我们去手动维护应用程序的 YAML 资源清单文件来说,成本也是巨大的。
Helm是Deis (https://deis.com/) 开发的一个用于kubernetes的包管理器。每个包称为一个Chart,一个Chart是一个目录(一般情况下会将目录进行打包压缩,形成name-version.tgz格式的单一文件,方便传输和存储)。
对于应用发布者而言,可以通过Helm打包应用,管理应用依赖关系,管理应用版本并发布应用到软件仓库。
除此以外,Helm还提供了kubernetes上的软件部署,删除,升级,回滚应用的强大功能
1. 诞生背景
k8s是一个分布式的容器集群管理系统,它将集群中的所有资源都抽象成 API 对象,并且使用声明的方式来创建、修改、删除这些对象。在微服务盛行的今天,如果使用这种方式将导致大量API声明文件的编写维护,使运维工作量爆发式增长,并且对每个微服务应用都需要编写对应的yaml配置文件,极容易出错,维护困难。helm就是为解决这些问题而诞生的。
在云 (Kubernetes)上,部署一个应用往往不是那么简单。如果想要部署一个应用程序到云上,首先要准备好它所需要的环境,打包成 Docker 镜像,进而把镜像放在部署文件 (Deployment) 中、配置服务 (Service)、应用所需的账户 (ServiceAccount) 及权限 (Role)、命名空间 (Namespace)、密钥信息 (Secret)、可持久化存储 (PersistentVolumes) 等资源。也就是编写一系列互相相关的 YAML 配置文件,将它们部署在 Kubernetes 集群上。
即便应用的开发者可以把这些 Docker 镜像存放在公共仓库中,并且将所需的 YAML 资源文件提供给用户,用户仍然需要自己去寻找这些资源文件,并把它们一一部署。倘若用户希望修改开发者提供的默认资源,比如使用更多的副本 (Replicas) 或是修改服务端口 (Port),他还需要自己去查需要在这些资源文件的哪些地方修改,更不用提版本变更与维护会给开发者和用户造成多少麻烦了。
2. 主要功能
Helm主要功能如下:
查找要安装和使用的预打包软件(Chart);
轻松创建和托管自己的软件包;
将软件包安装到任何K8s集群中;
查询集群已安装和正在运行的程序包;
更新、删除、回滚或查看已安装软件包的历史记录;
从使用方角度看:
应用发布者:可以通过Helm打包应用,管理应用依赖关系,管理应用版本并发布应用到软件仓库。Helm还提供了kubernetes上的软件部署,删除,升级,回滚应用的强大功能。
使用者:使用Helm后不用需要了解Kubernetes的Yaml语法并编写应用部署文件,可以通过Helm下载并在kubernetes上安装需要的应用。
3. Helm 相关概念
helm :
是一个命令行工具,用于本地开发及管理chart,chart仓库管理等chart:
Helm 的软件包,采用 TAR 格式,所谓chart就是一系列文件, 它描述了一组相关的 k8s 集群资源release:
是运行在 Kubernetes 集群中的 chart 的实例,一个 chart 通常可以在同一个集群中安装多次。每一次安装都会创建一个新的 release。以 MySQL chart为例,如果你想在你的集群中运行两个数据库,你可以安装该chart两次。每一个数据库都会拥有它自己的 release 和 release name。Repoistory:
Helm 的软件仓库,Repository 本质上是一个 Web 服务器,该服务器保存了一系列的 Chart 软件包以供用户下载,并且提供了一个该 Repository 的 Chart 包的清单文件以供查询。Helm 可以同时管理多个不同的 Repository。Tiller
:Tiller 是 Helm 的服务端,部署在 Kubernetes 集群中。Tiller 用于接收 Helm 的请求,并根据 Chart 生成 Kubernetes 的部署文件( Helm 称为 Release ),然后提交给 Kubernetes 创建应用。Tiller 还提供了 Release 的升级、删除、回滚等一系列功能。
4. 安装
Helm的版本用 x.y.z 描述,x是主版本,y是次版本,z是补丁版本。
不推荐将Helm用于比编译它所依赖的版本更高的Kubernetes版本,因为Helm并没有做出任何向前兼容的保证。如果您选择了一个Kubernetes版本不支持的Helm,需自负风险。
wget https://get.helm.sh/helm-v3.9.0-linux-amd64.tar.gz
tar -zxvf helm-v3.9.0-linux-amd64.tar.gz
mv linux-amd64/helm /usr/local/bin/
所有节点都安装。
#校验是否安装成功
helm version
#帮助
helm --help
注意:由于 Helm V2 版本必须在 Kubernetes 集群中安装一个 Tiller 服务进行通信,这样大大降低了其安全性和可用性,所以在 V3 版本中移除了,helm 3版本,没有Tiller,也就不用安装Tiller
在Helm 2开发周期中,Helm团队引入了Tiller(Helm2是C/S架构,主要分为客户端helm和服务端 Tiller)。它使多个不同的操作员可以与同一组发行版进行交互,对于在共享集群中工作的团队非常有用。但Kubernetes v1.6默认启用基于角色的访问控制(RBAC),这之后在生产环境中用Tiller会变得难以管理。同时出于安全策略考虑,Helm 3移除了Tiller,helm 直接和 Kubernetes API 进行通信,安全模型从根本上得以简化。这样做带来的好处有如下几点:
Helm 的架构变的更为简单和灵活
不再需要创建 ServiceAccount,直接使用当前环境中的 kubeconfig 配置
可以直接和 Kubernetes API 交互,更为安全
不再需要使用 helm init 来进行初始化(以前的版本需要使用该命令来向 K8S 集群中安装 Tiller)
6. 仓库
一旦 Helm 客户端准备成功后,我们就可以添加一个 chart 仓库,当然最常用的就是官方的 Helm stable charts 仓库,但是由于官方的 charts 仓库地址需要科学上网,我们可以使用阿里云的 charts 仓库代替:
# 查看仓库
helm repo list
# 移除原先的仓库
helm repo remove stable
# 添加新的仓库地址
helm repo add stable https://kubernetes.oss-cn-hangzhou.aliyuncs.com/charts
# 更新仓库
helm repo update
安装完成后可以用 search 命令来搜索可以安装的 chart 包:
helm search repo stable
6.1 查找Charts
helm search hub
从 Artifact Hub 中查找并列出 helm charts。 Artifact Hub中存放了大量不同的仓库helm search repo
从你添加(使用helm repo add
)到本地 helm 客户端中的仓库中进行查找。该命令基于本地数据进行搜索,无需连接互联网。
# 从添加的本地仓库查找
helm search repo mongo
# 从远端仓库查找
helm search hub wordpress
Helm 搜索使用模糊字符串匹配算法,所以你可以只输入名字的一部分
[root@master ctx]# helm search repo mongo
NAME CHART VERSION APP VERSION DESCRIPTION
bitnami/mongodb 13.1.2 6.0.1 MongoDB(R) is a relational open source NoSQL da...
bitnami/mongodb-sharded 6.1.1 6.0.1 MongoDB(R) is an open source NoSQL database tha...
stable/mongodb 0.4.27 3.7.1 NoSQL document-oriented database that stores JS...
stable/mongodb-replicaset 2.3.1 3.6 NoSQL document-oriented database that stores JS...
6.2 仓库添加
可以从官网chart新地址:https://artifacthub.io/,查找仓库。
通过 helm repo add
命令添加一个 chart 仓库:
helm repo add bitnami https://charts.bitnami.com/bitnami
当添加完成后,通过 helm search repo
命令能够看到可以被您安装的charts列表:
[root@master ctx]# helm search repo bitnami
NAME CHART VERSION APP VERSION DESCRIPTION
bitnami/airflow 13.1.4 2.3.4 Apache Airflow is a tool to express and execute...
bitnami/apache 9.2.3 2.4.54 Apache HTTP Server is an open-source HTTP serve...
bitnami/argo-cd 4.1.3 2.4.11 Argo CD is a continuous delivery tool for Kuber...
bitnami/argo-workflows 2.4.3 3.3.9 Argo Workflows is meant to orchestrate Kubernet...
bitnami/aspnet-core 3.5.2 6.0.8 ASP.NET Core is an open-source framework for we...
7. 使用
7.1 安装一个helm包(helm install)
使用 helm install
命令来安装一个新的 helm 包。
helm install 命令可以从多个来源进行安装:
chart 的仓库
本地 chart 压缩包(helm install foo foo-0.1.1.tgz)
解压后的 chart 目录(helm install foo path/to/foo)
完整的 URL(helm install foo https://example.com/charts/foo-1.2.3.tgz)
从仓库安装
最简单的使用方法只需要传入两个参数:你命名的release名字和你想安装的chart的名称。
可以使用helm repo update
命令来获取最新的chart列表。
安装chart时创建了一个新的 release 对象。如果想让Helm生成一个名称,发布时使用
--generate-name
。在安装过程中,helm 客户端会打印一些有用的信息,其中包括:哪些资源已经被创建,release当前的状态,以及你是否还需要执行额外的配置步骤。
Helm 客户端不会等到所有资源都运行才退出。许多 charts 需要大小超过 600M 的 Docker 镜像,可能需要很长时间才能安装到集群中。
# 手动指定名字
helm install msmysql bitnami/mysql
#自动生成名字
helm install bitnami/mysql --generate-name
比如:
[root@master helm]# helm install bitnami/mysql --generate-name
NAME: mysql-1662808138
LAST DEPLOYED: Sat Sep 10 19:09:00 2022
NAMESPACE: default
STATUS: deployed
REVISION: 1
TEST SUITE: None
NOTES:
CHART NAME: mysql
CHART VERSION: 9.3.2
APP VERSION: 8.0.30
** Please be patient while the chart is being deployed **
Tip:
Watch the deployment status using the command: kubectl get pods -w --namespace default
Services:
echo Primary: mysql-1662808138.default.svc.cluster.local:3306
Execute the following to get the administrator credentials:
echo Username: root
MYSQL_ROOT_PASSWORD=$(kubectl get secret --namespace default mysql-1662808138 -o jsonpath="{.data.mysql-root-password}" | base64 -d)
To connect to your database:
1. Run a pod that you can use as a client:
kubectl run mysql-1662808138-client --rm --tty -i --restart='Never' --image docker.io/bitnami/mysql:8.0.30-debian-11-r15 --namespace default --env MYSQL_ROOT_PASSWORD=$MYSQL_ROOT_PASSWORD --command -- bash
2. To connect to primary service (read/write):
mysql -h mysql-1662808138.default.svc.cluster.local -uroot -p"$MYSQL_ROOT_PASSWORD"
运行命令之后,bitnami/mysql这个chart被发布。
您可以通过执行
helm show chart bitnami/mysql
命令简单的了解到这个chart的基本信息。 或者您可以执行helm show all bitnami/mysql
获取关于该chart的所有信息。每当您执行
helm install
的时候,都会创建一个新的发布版本。 所以一个chart在同一个集群里面可以被安装多次,每一个都可以被独立的管理和升级。
[root@master helm]# helm show chart bitnami/mysql
annotations:
category: Database
apiVersion: v2
appVersion: 8.0.30
dependencies:
- name: common
repository: https://charts.bitnami.com/bitnami
tags:
- bitnami-common
version: 2.x.x
description: MySQL is a fast, reliable, scalable, and easy to use open source relational
database system. Designed to handle mission-critical, heavy-load production applications.
home: https://github.com/bitnami/charts/tree/master/bitnami/mysql
icon: https://bitnami.com/assets/stacks/mysql/img/mysql-stack-220x234.png
keywords:
- mysql
- database
- sql
- cluster
- high availability
maintainers:
- name: Bitnami
url: https://github.com/bitnami/charts
name: mysql
sources:
- https://github.com/bitnami/containers/tree/main/bitnami/mysql
- https://mysql.com
version: 9.3.2
7.2 查看release
通过 helm list
或 helm ls
命令会列出所有被发布的Chart:
helm list --all 会展示 Helm 保留的所有 release 记录,包括失败或删除的条目(指定了 --keep-history)
[root@master helm]# helm list
NAME NAMESPACE REVISION UPDATED STATUS CHART APP VERSION
mysql-1662808138 default 1 2022-09-10 19:09:00.680841397 +0800 CST deployed mysql-9.3.2 8.0.30
7.3 卸载release
可以使用 helm uninstall
命令卸载你发布的版本
[root@master helm]# helm uninstall mysql-1662808138
release "mysql-1662808138" uninstalled
该命令会从Kubernetes卸载 mysql-1662808138, 它将删除和该版本相关的所有相关资源(service、deployment、 pod等等)甚至版本历史。
如果您在执行 helm uninstall 的时候提供
--keep-history
选项, Helm将会保存版本历史。 您可以通过命令查看该版本的信息
7.4 查看release状态
您可以使用 helm status
命令查看 release 的状态,或是重新读取配置信息:
若卸载Chart时使用了
--keep-history
选项,helm会跟踪你的版本(即使你卸载了他们),所以你可以审计集群历史甚至使用helm rollback
回滚版本。
[root@master helm]# helm status mysql-1662808138
Error: release: not found
[root@master helm]# helm install bitnami/mysql --generate-name
[root@master helm]# helm uninstall mysql-1662808602 --keep-history
release "mysql-1662808602" uninstalled
[root@master helm]# helm status mysql-1662808602
NAME: mysql-1662808602
LAST DEPLOYED: Sat Sep 10 19:16:43 2022
NAMESPACE: default
STATUS: uninstalled
REVISION: 1
TEST SUITE: None
NOTES:
CHART NAME: mysql
CHART VERSION: 9.3.2
APP VERSION: 8.0.30
7.5 查看配置的仓库
Helm3 不再附带一个默认的 chart 仓库。helm repo 提供了一组命令用于添加、列出和移除仓库。
使用 helm repo list 来查看配置的仓库:
[root@master helm]# helm repo list NAME URL stable https://kubernetes.oss-cn-hangzhou.aliyuncs.com/charts bitnami https://charts.bitnami.com/bitnami
使用 helm repo add 来添加新的仓库:
helm repo add xxx
因为 chart 仓库经常在变化,在任何时候你都可以通过执行 helm repo update
命令来确保你的 Helm 客户端是最新的。
使用 helm repo remove
命令来移除仓库。
7.6 自定义安装chart
上述安装方式只会使用chart的默认配置选项,很多时候,我们需要自定义 chart 来指定我们想要的配置
# 查看 chart 中的可配置选项
$ helm show values bitnami/wordpress
然后,你可以使用 YAML 格式的文件覆盖上述任意配置项,并在安装过程中使用该文件
mariadb:
auth:
database: testdb
username: testuser
$ helm install -f values.yaml bitnami/wordpress --generate-name
上述命令将为 MariaDB 创建一个名称为 testuser
的默认用户,并且授予该用户访问新建的 testdb
数据库的权限。chart 中的其他默认配置保持不变。
安装过程中有两种方式传递配置数据
--values
(或-f
):使用 YAML 文件覆盖配置。可以指定多次,优先使用最右边的文件--set
:通过命令行的方式对指定项进行覆盖
如果同时使用两种方式,则 --set
中的值会被合并到 --values
中,但是 --set
中的值优先级更高。在--set
中覆盖的内容会被被保存在 ConfigMap 中。可以通过 helm get values <release-name>
来查看指定 release 中 --set
设置的值。也可以通过运行 helm upgrade
并指定 --reset-values
字段来清除 --set
中设置的值。
--set
的格式和限制
--set
选项使用0或多个 name/value 对。最简单的用法类似于:--set name=value
,等价于如下 YAML 格式:
name: value
多个值使用逗号分割,因此 --set a=b,c=d
的 YAML 表示是:
a: b
c: d
支持更复杂的表达式。例如,--set outer.inner=value
被转换成了:
outer:
inner: value
列表使用花括号({}
)来表示。例如,--set name={a, b, c}
被转换成了:
name:
- a
- b
- c
从 2.5.0 版本开始,可以使用数组下标的语法来访问列表中的元素。例如 --set servers[0].port=80
就变成了:
servers:
- port: 80
多个值也可以通过这种方式来设置。--set servers[0].port=80,servers[0].host=example
变成了:
servers:
- port: 80
host: example
如果需要在 --set
中使用特殊字符,你可以使用反斜线来进行转义;--set name=value1\,value2
就变成了:
name: "value1,value2"
7.7 升级release(helm upgrade)
首先创建好wp-update.yaml
mariadb:
auth:
password: "123456"
rootPassword: "123456"
username: user1
wordpressPassword: "123456"
执行命令
helm upgrade
[root@master helm]# helm upgrade -f wp-update.yaml wordpress-1662809924 bitnami/wordpress
Release "wordpress-1662809924" has been upgraded. Happy Helming!
NAME: wordpress-1662809924
LAST DEPLOYED: Sat Sep 10 19:42:11 2022
NAMESPACE: default
STATUS: deployed
REVISION: 2
TEST SUITE: None
NOTES:
CHART NAME: wordpress
CHART VERSION: 15.2.0
APP VERSION: 6.0.2
查看结果
helm get values
[root@master helm]# helm get values wordpress-1662809924
USER-SUPPLIED VALUES:
mariadb:
auth:
password: "123456"
rootPassword: "123456"
username: user1
wordpressPassword: "123456"
7.8 回滚release(helm rollback)
格式:helm rollback [RELEASE] [REVISION]
$ helm rollback wordpress-1662809924 1
上面这条命令将我们的 wordpress-1662809924
回滚到了它最初的版本。release 版本其实是一个增量修订(revision)。 每当发生了一次安装、升级或回滚操作,revision 的值就会加1。第一次 revision 的值永远是1。
我们可以使用 helm history [RELEASE]
命令来查看一个特定 release 的修订版本号
[root@master helm]# helm history wordpress-1662809924
REVISION UPDATED STATUS CHART APP VERSION DESCRIPTION
1 Sat Sep 10 19:38:45 2022 superseded wordpress-15.2.0 6.0.2 Install complete
2 Sat Sep 10 19:42:11 2022 deployed wordpress-15.2.0 6.0.2 Upgrade complete
查看回滚结果:
[root@master helm]# helm get values wordpress-1662809924
USER-SUPPLIED VALUES:
mariadb:
auth:
database: testdb
username: testuser
7.9 安装、升级、回滚的有用选项
要查看所有参数的说明,请执行 helm <command> --help
命令。
--timeout
:一个 Go duration类型的值, 用来表示等待 Kubernetes 命令完成的超时时间,默认值为5m0s
。--wait
:表示必须要等到所有的 Pods 都处于 ready 状态,PVC 都被绑定,Deployments 都至少拥有最小 ready 状态 Pods 个数(Desired
减去maxUnavailable
),并且 Services 都具有 IP 地址(如果是LoadBalancer
, 则为 Ingress),才会标记该 release 为成功。最长等待时间由--timeout
值指定。如果达到超时时间,release 将被标记为FAILED
。注意:当 Deployment 的replicas
被设置为1,但其滚动升级策略中的maxUnavailable
没有被设置为0时,--wait
将返回就绪,因为已经满足了最小 ready Pod 数。--no-hooks
:不运行当前命令的钩子--recreate-pods
(仅适用于upgrade
和rollback
):这个参数会导致重建所有的 Pod(deployment中的Pod 除外)。(在 Helm 3 中已被废弃)
8. 解决Pending问题
[root@master helm]# kubectl describe pod mywp-wordpress-f67667857-7ljph
Events:
Type Reason Age From Message
---- ------ ---- ---- -------
Warning FailedScheduling 58s (x21 over 20m) default-scheduler 0/3 nodes are available: 3 pod has unbound immediate PersistentVolumeClaims.
直接安装wordpress并不会成功,因为需要做pvc相关的操作,实际上就是wordpress的包并不会自动创建pv,没有也就是pvc没法和pv绑定造成的问题。
[root@master helm]# kubectl get pvc
NAME STATUS VOLUME CAPACITY ACCESS MODES STORAGECLASS AGE
data-mywp-mariadb-0 Pending 9s
mywp-wordpress Pending 9s
#有pvc但是没有pv
[root@master helm]# kubectl get pv
No resources found
这里涉及到一个k8s新的资源StorageClass
9. StorageClass
Kubernetes提供了一套可以自动创建PV的机制,即:Dynamic Provisioning。而这个机制的核心在于StorageClass这个API对象。
大规模集群中可能会有很多PV,如果这些PV都需要运维手动来处理这也是一件很繁琐的事情(想象一下PVC不停的被提交,运维人员手动去创建符合要求的PV)所以就有了动态供给概念
StorageClass对象会定义下面两部分内容:
PV的属性。比如,存储类型,Volume的大小等。
创建这种PV需要用到的存储插件。
有了这两个信息之后,Kubernetes就能够根据用户提交的PVC,找到一个对应的StorageClass,之后Kubernetes就会调用该StorageClass声明的存储插件,进而创建出需要的PV。
通过 StorageClass 的定义,管理员可以将存储资源定义为某种类型的资源,比如快速存储、慢速存储等,用户根据 StorageClass 的描述就可以非常直观的知道各种存储资源的具体特性了,这样就可以根据应用的特性去申请合适的存储资源了。
apiVersion: storage.k8s.io/v1
kind: StorageClass
metadata:
name: standard
provisioner: kubernetes.io/aws-ebs
parameters:
type: gp2
reclaimPolicy: Retain
allowVolumeExpansion: true
mountOptions:
- debug
volumeBindingMode: Immediate
每个 StorageClass 都包含 provisioner
、parameters
和 reclaimPolicy
字段, 这些字段会在 StorageClass 需要动态分配 PersistentVolume 时会使用到。
provisioner
由那个存储器来提供,比如亚马逊,阿里云,nfs,ceph存储等
parameters
参数,不同的存储提供者,参数也不相同
reclaimPolicy
动态创建的pv的回收策略,默认是Delete,可以是
Delete
或者Retain
每个 StorageClass 都有一个制备器(Provisioner),用来决定使用哪个卷插件制备 PV。 该字段必须指定。
9.1 案例
还是使用nfs,虽然不默认支持,但是其简单,适合做为例子
前面的课程中已经安装过nfs了
[root@master helm]# more /etc/exports
/mnt/data/nfs 192.168.200.0/24(rw,no_root_squash)
/mnt/data/pv1 192.168.200.0/24(rw,no_root_squash)
/mnt/data/pv2 192.168.200.0/24(rw,no_root_squash)
/mnt/data/pv3 192.168.200.0/24(rw,no_root_squash)
1. 创建Service Account
vim nfs-client-rbac.yaml,管理nfs-Provisioner在集群中的权限
apiVersion: v1 #创建 Service Account 账户,用来管理 NFS Provisioner 在 k8s 集群中运行的权限
kind: ServiceAccount
metadata:
name: nfs-client-provisioner
---
apiVersion: rbac.authorization.k8s.io/v1 #创建集群角色
kind: ClusterRole
metadata:
name: nfs-client-provisioner-clusterrole
rules:
- apiGroups: [""]
resources: ["persistentvolumes"]
verbs: ["get", "list", "watch", "create", "delete"]
- apiGroups: [""]
resources: ["persistentvolumeclaims"]
verbs: ["get", "list", "watch", "update"]
- apiGroups: ["storage.k8s.io"]
resources: ["storageclasses"]
verbs: ["get", "list", "watch"]
- apiGroups: [""]
resources: ["events"]
verbs: ["list", "watch", "create", "update", "patch"]
- apiGroups: [""]
resources: ["endpoints"]
verbs: ["create", "delete", "get", "list", "watch", "patch", "update"]
---
apiVersion: rbac.authorization.k8s.io/v1 #集群角色绑定
kind: ClusterRoleBinding
metadata:
name: nfs-client-provisioner-clusterrolebinding
subjects:
- kind: ServiceAccount
name: nfs-client-provisioner
namespace: default
roleRef:
kind: ClusterRole
name: nfs-client-provisioner-clusterrole
apiGroup: rbac.authorization.k8s.io
[root@master helm]# kubectl apply -f nfs-client-rbac.yaml
serviceaccount/nfs-client-provisioner created
clusterrole.rbac.authorization.k8s.io/nfs-client-provisioner-clusterrole created
clusterrolebinding.rbac.authorization.k8s.io/nfs-client-provisioner-clusterrolebinding created
2. Deployment创建NFS Provisioner
vim /etc/kubernetes/manifests/kube-apiserver.yaml
spec:
containers:
- command:
- kube-apiserver
- --feature-gates=RemoveSelfLink=false #添加这行
vim nfs-client-provisioner.yaml
kind: Deployment
apiVersion: apps/v1
metadata:
name: nfs-client-provisioner
spec:
replicas: 1
selector:
matchLabels:
app: nfs-client-provisioner
strategy:
type: Recreate
template:
metadata:
labels:
app: nfs-client-provisioner
spec:
serviceAccountName: nfs-client-provisioner #指定Service Account账户
containers:
- name: nfs-client-provisioner
image: quay.io/external_storage/nfs-client-provisioner:latest
imagePullPolicy: IfNotPresent
volumeMounts:
- name: nfs-client-root
mountPath: /persistentvolumes
env:
- name: PROVISIONER_NAME
value: nfs-storage #配置provisioner的Name,确保该名称与StorageClass资源中的provisioner名称保持一致
- name: NFS_SERVER
value: 192.168.200.104 #配置绑定的nfs服务器
- name: NFS_PATH
value: /mnt/data/nfs #配置绑定的nfs服务器目录
volumes: #申明nfs数据卷
- name: nfs-client-root
nfs:
server: 192.168.200.104
path: /mnt/data/nfs
[root@master helm]# kubectl apply -f nfs-client-provisioner.yaml
deployment.apps/nfs-client-provisioner created
3. 创建storageclass
vim nfs-client-storageclass.yaml
apiVersion: storage.k8s.io/v1
kind: StorageClass
metadata:
name: nfs-client-storageclass
provisioner: nfs-storage #这里的名称要和provisioner配置文件中的环境变量PROVISIONER_NAME保持一致
parameters:
archiveOnDelete: "false" #false表示在删除PVC时不会对数据进行存档,即删除数据
[root@master helm]# kubectl apply -f nfs-client-storageclass.yaml
storageclass.storage.k8s.io/nfs-client-storageclass created
[root@master helm]# kubectl get storageclasses
NAME PROVISIONER RECLAIMPOLICY VOLUMEBINDINGMODE ALLOWVOLUMEEXPANSION AGE
nfs-client cluster.local/nfs-client-provisioner Delete Immediate true 122m
nfs-client-storageclass nfs-storage Delete Immediate false 25s
4. 测试
创建pvc
vim test-pvc-pod.yaml
apiVersion: v1 kind: PersistentVolumeClaim metadata: name: test-nfs-pvc spec: accessModes: - ReadWriteOnce storageClassName: nfs-client-storageclass #关联StorageClass对象 resources: requests: storage: 2Gi
应用
[root@master helm]# kubectl get pvc NAME STATUS VOLUME CAPACITY ACCESS MODES STORAGECLASS AGE test-nfs-pvc Bound pvc-15628120-6425-4223-8558-ffcd3fd43c96 2Gi RWO nfs-client-storageclass 13s [root@master helm]# kubectl get pv NAME CAPACITY ACCESS MODES RECLAIM POLICY STATUS CLAIM STORAGECLASS REASON AGE pvc-15628120-6425-4223-8558-ffcd3fd43c96 2Gi RWO Delete Bound default/test-nfs-pvc nfs-client-storageclass 85s
自动进行了绑定,自动创建了pv
使用pod进行测试
[root@master helm]# ls /mnt/data/nfs/ access.log default-test-nfs-pvc-pvc-15628120-6425-4223-8558-ffcd3fd43c96 error.log
vim test-pv-pod.yaml
apiVersion: v1 kind: Pod metadata: name: test-pv-pod spec: volumes: - name: test-pv-storage persistentVolumeClaim: claimName: test-nfs-pvc containers: - name: test-pv-container image: nginx ports: - containerPort: 80 name: "http-server" volumeMounts: - mountPath: "/usr/share/nginx/html" name: test-pv-storage #与PVC名称保持一致
[root@master helm]# kubectl apply -f test-pv-pod.yaml pod/test-pv-pod created [root@master helm]# kubectl get pods NAME READY STATUS RESTARTS AGE nfs-client-provisioner-7c74fbb898-vmns7 1/1 Running 0 34m test-pv-pod 1/1 Running 0 11s [root@master helm]# kubectl get pods -o wide NAME READY STATUS RESTARTS AGE IP NODE NOMINATED NODE READINESS GATES nfs-client-provisioner-7c74fbb898-vmns7 1/1 Running 0 34m 10.244.2.5 node2 <none> <none> test-pv-pod
在NFS中编辑index.html
[root@master default-test-nfs-pvc-pvc-15628120-6425-4223-8558-ffcd3fd43c96]# vim index.html this is storage class [root@node1 nfs]# curl 10.244.1.13 this is storage class
完成测试
10. helm安装wordpress
安装是设置pvc参数即可:
[root@master helm]# helm install wordpress bitnami/wordpress --set mariadb.primary.persistence.enabled=true --set mariadb.primary.persistence.storageClass=nfs-client-storageclass --set persistence.storageClass=nfs-client-storageclass --set service.type=NodePort
[root@master helm]# kubectl get pods
NAME READY STATUS RESTARTS AGE
nfs-client-provisioner-7c74fbb898-vmns7 1/1 Running 0 51m
wordpress-5cd4785cdf-l5fsq 1/1 Running 1 (5m4s ago) 6m18s
wordpress-mariadb-0 1/1 Running 0 6m18s
[root@master helm]# kubectl get service
NAME TYPE CLUSTER-IP EXTERNAL-IP PORT(S) AGE
kubernetes ClusterIP 10.96.0.1 <none> 443/TCP 7d20h
wordpress NodePort 10.96.15.73 <none> 80:31775/TCP,443:30439/TCP 6s
wordpress-mariadb ClusterIP 10.96.137.48 <none> 3306/TCP 6s
访问:http://192.168.200.105:31775/ ,发现可以访问