示例:使用持久卷部署 WordPress 和 MySQL

本教程向你展示如何使用 Minikube 部署 WordPress 站点和 MySQL 数据库。这两个应用都使用 PersistentVolume 和 PersistentVolumeClaim 来存储数据。

一个 PersistentVolume (PV) 是集群中的一块存储,它或由管理员手动配置,或由 Kubernetes 使用 StorageClass 动态配置。一个 PersistentVolumeClaim (PVC) 是用户对存储的请求,可以由 PV 来满足。PersistentVolume 和 PersistentVolumeClaim 独立于 Pod 的生命周期,在 Pod 重启、重新调度甚至删除后仍保留数据。

目标

  • 创建 PersistentVolumeClaims 和 PersistentVolumes
  • 创建一个包含以下内容的 kustomization.yaml 文件
    • 一个 Secret 生成器
    • MySQL 资源配置
    • WordPress 资源配置
  • 通过 kubectl apply -k ./ 应用 kustomization 目录
  • 清理

开始之前

你需要有一个 Kubernetes 集群,并且 kubectl 命令行工具已经配置为与你的集群通信。建议你在至少有两个非控制平面节点的主机上运行本教程。如果你还没有集群,可以使用 minikube 创建一个,或者使用以下 Kubernetes 游乐场之一。

要检查版本,请输入 kubectl version

本页面所示示例适用于 kubectl 1.27 及更高版本。

下载以下配置文件

  1. mysql-deployment.yaml

  2. wordpress-deployment.yaml

创建 PersistentVolumeClaims 和 PersistentVolumes

MySQL 和 Wordpress 各需要一个 PersistentVolume 来存储数据。它们的 PersistentVolumeClaim 将在部署步骤中创建。

许多集群环境都安装了默认的 StorageClass。如果在 PersistentVolumeClaim 中没有指定 StorageClass,则会使用集群的默认 StorageClass。

创建 PersistentVolumeClaim 后,将根据 StorageClass 配置动态地配置 PersistentVolume。

创建一个 kustomization.yaml

添加一个 Secret 生成器

一个 Secret 是一个存储敏感数据(例如密码或密钥)的对象。从 1.14 版本开始,kubectl 支持使用 kustomization 文件来管理 Kubernetes 对象。你可以在 kustomization.yaml 中使用生成器来创建 Secret。

使用以下命令在 kustomization.yaml 中添加一个 Secret 生成器。你需要将 YOUR_PASSWORD 替换为你想要使用的密码。

cat <<EOF >./kustomization.yaml
secretGenerator:
- name: mysql-pass
  literals:
  - password=YOUR_PASSWORD
EOF

添加 MySQL 和 WordPress 的资源配置

以下清单描述了一个单实例的 MySQL Deployment。MySQL 容器将 PersistentVolume 挂载到 /var/lib/mysql。MYSQL_ROOT_PASSWORD 环境变量从 Secret 中设置数据库密码。

apiVersion: v1
kind: Service
metadata:
  name: wordpress-mysql
  labels:
    app: wordpress
spec:
  ports:
    - port: 3306
  selector:
    app: wordpress
    tier: mysql
  clusterIP: None
---
apiVersion: v1
kind: PersistentVolumeClaim
metadata:
  name: mysql-pv-claim
  labels:
    app: wordpress
spec:
  accessModes:
    - ReadWriteOnce
  resources:
    requests:
      storage: 20Gi
---
apiVersion: apps/v1
kind: Deployment
metadata:
  name: wordpress-mysql
  labels:
    app: wordpress
spec:
  selector:
    matchLabels:
      app: wordpress
      tier: mysql
  strategy:
    type: Recreate
  template:
    metadata:
      labels:
        app: wordpress
        tier: mysql
    spec:
      containers:
      - image: mysql:8.0
        name: mysql
        env:
        - name: MYSQL_ROOT_PASSWORD
          valueFrom:
            secretKeyRef:
              name: mysql-pass
              key: password
        - name: MYSQL_DATABASE
          value: wordpress
        - name: MYSQL_USER
          value: wordpress
        - name: MYSQL_PASSWORD
          valueFrom:
            secretKeyRef:
              name: mysql-pass
              key: password
        ports:
        - containerPort: 3306
          name: mysql
        volumeMounts:
        - name: mysql-persistent-storage
          mountPath: /var/lib/mysql
      volumes:
      - name: mysql-persistent-storage
        persistentVolumeClaim:
          claimName: mysql-pv-claim

以下清单描述了一个单实例的 WordPress Deployment。WordPress 容器将 PersistentVolume 挂载到 /var/www/html 用于存放网站数据文件。WORDPRESS_DB_HOST 环境变量设置了上面定义的 MySQL Service 名称,WordPress 将通过 Service 访问数据库。WORDPRESS_DB_PASSWORD 环境变量从 kustomize 生成的 Secret 中设置数据库密码。

apiVersion: v1
kind: Service
metadata:
  name: wordpress
  labels:
    app: wordpress
spec:
  ports:
    - port: 80
  selector:
    app: wordpress
    tier: frontend
  type: LoadBalancer
---
apiVersion: v1
kind: PersistentVolumeClaim
metadata:
  name: wp-pv-claim
  labels:
    app: wordpress
spec:
  accessModes:
    - ReadWriteOnce
  resources:
    requests:
      storage: 20Gi
---
apiVersion: apps/v1
kind: Deployment
metadata:
  name: wordpress
  labels:
    app: wordpress
spec:
  selector:
    matchLabels:
      app: wordpress
      tier: frontend
  strategy:
    type: Recreate
  template:
    metadata:
      labels:
        app: wordpress
        tier: frontend
    spec:
      containers:
      - image: wordpress:6.2.1-apache
        name: wordpress
        env:
        - name: WORDPRESS_DB_HOST
          value: wordpress-mysql
        - name: WORDPRESS_DB_PASSWORD
          valueFrom:
            secretKeyRef:
              name: mysql-pass
              key: password
        - name: WORDPRESS_DB_USER
          value: wordpress
        ports:
        - containerPort: 80
          name: wordpress
        volumeMounts:
        - name: wordpress-persistent-storage
          mountPath: /var/www/html
      volumes:
      - name: wordpress-persistent-storage
        persistentVolumeClaim:
          claimName: wp-pv-claim
  1. 下载 MySQL 部署配置文件。

    curl -LO https://k8s.io/examples/application/wordpress/mysql-deployment.yaml
    
  2. 下载 WordPress 配置文件。

    curl -LO https://k8s.io/examples/application/wordpress/wordpress-deployment.yaml
    
  3. 将它们添加到 kustomization.yaml 文件中。

    cat <<EOF >>./kustomization.yaml
    resources:
      - mysql-deployment.yaml
      - wordpress-deployment.yaml
    EOF
    

应用并验证

kustomization.yaml 包含部署 WordPress 站点和 MySQL 数据库所需的所有资源。你可以通过以下方式应用该目录:

kubectl apply -k ./

现在你可以验证所有对象是否存在。

  1. 通过运行以下命令验证 Secret 是否存在:

    kubectl get secrets
    

    响应应该如下所示:

    NAME                    TYPE                                  DATA   AGE
    mysql-pass-c57bb4t7mf   Opaque                                1      9s
    
  2. 验证 PersistentVolume 是否被动态配置。

    kubectl get pvc
    

    响应应该如下所示:

    NAME             STATUS    VOLUME                                     CAPACITY   ACCESS MODES   STORAGECLASS       AGE
    mysql-pv-claim   Bound     pvc-8cbd7b2e-4044-11e9-b2bb-42010a800002   20Gi       RWO            standard           77s
    wp-pv-claim      Bound     pvc-8cd0df54-4044-11e9-b2bb-42010a800002   20Gi       RWO            standard           77s
    
  3. 通过运行以下命令验证 Pod 是否正在运行:

    kubectl get pods
    

    响应应该如下所示:

    NAME                               READY     STATUS    RESTARTS   AGE
    wordpress-mysql-1894417608-x5dzt   1/1       Running   0          40s
    
  4. 通过运行以下命令验证 Service 是否正在运行:

    kubectl get services wordpress
    

    响应应该如下所示:

    NAME        TYPE            CLUSTER-IP   EXTERNAL-IP   PORT(S)        AGE
    wordpress   LoadBalancer    10.0.0.89    <pending>     80:32406/TCP   4m
    
  5. 运行以下命令获取 WordPress Service 的 IP 地址:

    minikube service wordpress --url
    

    响应应该如下所示:

    http://1.2.3.4:32406
    
  6. 复制 IP 地址,并在浏览器中加载该页面以查看你的站点。

    你应该会看到类似于以下截图的 WordPress 设置页面。

    wordpress-init

清理

  1. 运行以下命令删除你的 Secret、Deployments、Services 和 PersistentVolumeClaims:

    kubectl delete -k ./
    

下一步

最后修改于太平洋标准时间 2023 年 8 月 24 日下午 6:38:使用 code_sample Shortcode 替代 code Shortcode (e8b136c3b3)