k8s学习之路【04.配置应用程序】

简介: k8s学习之路【04.配置应用程序】

使用Docker部署应用程序时,一般常用的配置方式有:


  • 配置内嵌


  • 启动传参配置

  • 环境变量

经过前面容器持久化存储的介绍,我们很容易能想到是以挂载卷的形式,比如:


  • gitRepo

  • hostPath

  • NFS

再结合边车模式来进行配置文件的管控是可行的,然而有一种更加简便的方法能将配置数据置于Kubernetes的顶级资源对象中,那就是ConfigMap


传递命令行参数


在上一节容器持久化存储emptyDir概念介绍部分,我们引入了一个fortune-pod的例子,再回顾一下之前的配置文件吧,如下:

apiVersion: v1
kind: Pod
metadata:
  name: fortune
spec:
  containers:
  - image: luksa/fortune
    name: html-generator
    volumeMounts:
    - name: html
      mountPath: /var/htdocs
  - image: nginx:alpine
    name: web-server
    volumeMounts:
    - name: html
      mountPath: /usr/share/nginx/html
      readOnly: true
    ports:
    - containerPort: 80
      protocol: TCP
  volumes:
  - name: html
    emptyDir: {}

此应用程序设定了每隔10s就会自动生成输出到html,现在我们要做的是通过命令行参数,自行设定隔多少秒自动生成内容。


创建文件fortune-pod-args.yaml,输入以下内容:

apiVersion: v1
kind: Pod
metadata:
  name: fortune2s
spec:
  containers:
  - image: luksa/fortune:args
    args: ["2"]
    name: html-generator
    volumeMounts:
    - name: html
      mountPath: /var/htdocs
  - image: nginx:alpine
    name: web-server
    volumeMounts:
    - name: html
      mountPath: /usr/share/nginx/html
      readOnly: true
    ports:
    - containerPort: 80
      protocol: TCP
  volumes:
  - name: html
    emptyDir: {}

看到配置文件中的args字段了么?这个就是传给镜像luksa/fortune:args控制时间的参数,让我们启动看看吧。

kubectl create -f fortune-pod-args.yaml
# 输出
pod/fortune2s created
# 查看状态
kubectl get pods
# 输出
NAME      READY   STATUS    RESTARTS   AGE
fortune   2/2     Running   0          2m27s
# 暂时服务化
kubectl port-forward fortune2s 8080:80

访问127.0.0.1:8080就会发现输出的频率变成了2s

> curl 127.0.0.1:8080
Stay away from flying saucers today.

设置环境变量


与容器的命令和参数设置相同,环境变量列表无法在 pod 创建后被修改


设置环境变量非常简单,我们只需要在pod中指定环境变量即可;当然,这里有个前提是你需要将修改镜像让其支持读取环境变量。


我们直接使用书中的例子:vim fortune-pod-env.yaml

apiVersion: v1
kind: Pod
metadata:
  name: fortune-env
spec:
  containers:
  - image: luksa/fortune:env
    env:
    - name: INTERVAL
      value: "30"
    name: html-generator
    volumeMounts:
    - name: html
      mountPath: /var/htdocs
  - image: nginx:alpine
    name: web-server
    volumeMounts:
    - name: html
      mountPath: /usr/share/nginx/html
      readOnly: true
    ports:
    - containerPort: 80
      protocol: TCP
  volumes:
  - name: html
    emptyDir: {}

可以看到配置中声明了INTERVAL环境变量值为30,在终端中实践一下:

kubectl create -f fortune-pod-env.yaml
# 输出
pod/fortune-env created
# 查看状态
kubectl get pods
# 输出
NAME      READY   STATUS    RESTARTS   AGE
fortune-env   2/2     Running   0          10s
# 暂时服务化
kubectl port-forward fortune-env 8080:80

访问127.0.0.1:8080就会发现输出的频率变成了30s


现在应用程序的所有配置基本上可以说是硬编码的形式进行配置,并且yaml配置文件总是有配置相关的字段,有没有办法让镜像和配置文件解耦呢?


k8s提供了名为ConfigMap的资源对象解决这个问题。


ConfigMap


资源对象ConfigMap提供了向容器中注入配置信息的机制,它本质上就是一个键/值对映射,可以用来保存单个值或者配置文件。


ConfigMap是不需要被读取的,它映射的内容通过环境变量或者卷文件的形式传给容器。一般直接在pod的定义里面就可以声明ConfigMap,这样就可以根据不同的环境创建不同的配置,流程交互如下图所示:

2.png

创建


还是用之前应用程序为例,配置专注于环境变量INTERVAL,创建命令如下所示:

kubectl create configmap fortune-config --from-literal=sleep-interval=25
# 输出
configmap/fortune-config created
# 获取相关描述
kubectl get configmap fortune-config -o yaml
# 查看 configmap
kubectl get configmap
# 删除
kubectl delete configmap fortune-config

此外,k8s还可以直接填写配置文件来进行创建vim fortune-config.yaml,输入如下内容:

apiVersion: v1
kind: ConfigMap
metadata:
  name: fortune-config
data:
  sleep-interval: "25"

然后执行:

kubectl create -f fortune-config.yaml
# 输出
configmap/fortune-config created

其实还有更多的创建方式,大概提一下:

# 从文件内容创建ConfigMap条目
kubectl create configmap my-config --from-file=config-file.conf
# 从文件夹创建ConfigMap
kubectl create configmap my-config --from-file=/path/to/dir
# 合并不同选项
kubectl create configmap my-config
 --from-file=foo.json
 --from-file=bar=foobar.conf
 --from-file=config-opts/
 --from-literal=some=thing

作为环境变量传入容器


如何将映射中的值传递给pod的容器?最简单的方法是给容器设置环境变量,通过在配置中声明valueFrom,具体操作vim fortune-pod-env-configmap.yaml:

apiVersion: v1
kind: Pod
metadata:
  name: fortune-env-from-configmap
spec:
  containers:
  - image: luksa/fortune:env
    env:
    - name: INTERVAL
      valueFrom:
        configMapKeyRef:
          name: fortune-config
          key: sleep-interval
    name: html-generator
    volumeMounts:
    - name: html
      mountPath: /var/htdocs
  - image: nginx:alpine
    name: web-server
    volumeMounts:
    - name: html
      mountPath: /usr/share/nginx/html
      readOnly: true
    ports:
    - containerPort: 80
      protocol: TCP
  volumes:
  - name: html
    emptyDir: {}

让我们启动pod实践看看:

kubectl create -f fortune-pod-env-configmap.yaml
# 输出
pod/fortune-env-from-configmap created
# 查看状态
kubectl get pods
# 输出
NAME                         READY   STATUS    RESTARTS   AGE
fortune-env-from-configmap   2/2     Running   0          19s
# 暂时服务化
kubectl port-forward fortune-env-from-configmap 8080:80
# 删除pod
kubectl delete pods fortune-env-from-configmap

现在我们已经成功在pod中使用了ConfigMap资源,不过这种使用方式是比较低效的,考虑这样一个情况:如果环境变量比较多,这样单独一个个环境变量的设置方式是个程序员都没法忍受的。


一般在框架里面加载一些环境变量都会利用前缀机制来进行批量加载,比如Sanic框架会读取SANIC_开头的环境变量自动加载。


k8s也提供了这样类似的机制,配置声明如下图示:

3.png

ConfigMap 卷


环境变量或者命令行参数值作为配置值通常适用于变量值较短的场景。由于 ConfigMap 中可以包含完整的配置文件内容,当你想要将其暴露给容器时,可以借助前面章节提到过的一种称为 configMap 卷的特殊卷格式。


首先删除前面声明建立的cf资源:kubectl delete configmap fortune-config。然后建立文件夹configmap-files,首先建立Nginx配置文件:vim my-nginx-config.conf

server {
    listen              80;
    server_name         www.kubia-example.com;
    gzip on;
    gzip_types text/plain application/xml;
    location / {
        root   /usr/share/nginx/html;
        index  index.html index.htm;
    }
}

另外在该文件夹中添加一个名为sleep-interval的文本文件,输入25,类似前面声明环境变量。


接下来从文件夹创建ConfigMap

kubectl create configmap fortune-config --from-file=configmap-files
# 输出
configmap/fortune-config created
# 验证
kubectl get configmap fortune-config -o yaml

4.png

创建包含ConfigMap条目内容的卷只需要创建一个引用ConfigMap名称的卷并挂载到容器中:

5.png

创建配置文件:vim fortune-pod-configmap-volume.yaml,输入如下内容:

apiVersion: v1
kind: Pod
metadata:
  name: fortune-configmap-volume
spec:
  containers:
  - image: luksa/fortune:env
    env:
    - name: INTERVAL
      valueFrom:
        configMapKeyRef:
          name: fortune-config
          key: sleep-interval
    name: html-generator
    volumeMounts:
    - name: html
      mountPath: /var/htdocs
  - image: nginx:alpine
    name: web-server
    volumeMounts:
    - name: html
      mountPath: /usr/share/nginx/html
      readOnly: true
    - name: config
      mountPath: /etc/nginx/conf.d
      readOnly: true
    - name: config
      mountPath: /tmp/whole-fortune-config-volume
      readOnly: true
    ports:
      - containerPort: 80
        name: http
        protocol: TCP
  volumes:
  - name: html
    emptyDir: {}
  - name: config
    configMap:
      name: fortune-config

Secret


前面说的,都是针对非敏感信息的配置数据,对于一些敏感数据,例如:密码、OAuth token、ssh 密钥等,就可以使用Secret资源了。


Secret结构和使用方法都与ConfigMap类似,k8s通过仅仅将Secret分发到需要访问Secretpod所在的机器节点来保障其安全性。另外,Secret只会存储在节点的内存中,永不写入物理存储。


创建


以创建一个包含用户名密码的secret资源为例:

# 创建文件
echo -n 'admin' > ./username.txt
echo -n '1f2d1e2e67df' > ./password.txt
# 创建资源
kubectl create secret generic db-user-pass --from-file=./username.txt --from-file=./password.txt
# 输出
secret/db-user-pass created
# 查看
kubectl get secrets
# 输出
NAME                  TYPE                                  DATA   AGE
db-user-pass          Opaque                                2      23s
default-token-nlxkq   kubernetes.io/service-account-token   3      54d

db-user-pass很好理解,就是刚才创建的sevret资源,default-token-nlxkq是什么呢?这是一种默认被挂载至所有容器的Secret


参考


本章关于配置应用程序就介绍到这里了,谢谢!本部分内容有参考如下文章:


  • 配置 Pod 使用 ConfigMap[1]

  • Secret 概述[2]

  • Kubernetes in Action[3]中文版:可以算是第 7 章的读书笔记

参考资料


[1]

配置 Pod 使用 ConfigMap: https://kubernetes.io/zh/docs/tasks/configure-pod-container/configure-pod-configmap/


[2]

Secret概述: https://kuboard.cn/learning/k8s-intermediate/config/secrets/


[3]

Kubernetes in Action: https://github.com/luksa/kubernetes-in-action

相关实践学习
通过Ingress进行灰度发布
本场景您将运行一个简单的应用,部署一个新的应用用于新的发布,并通过Ingress能力实现灰度发布。
容器应用与集群管理
欢迎来到《容器应用与集群管理》课程,本课程是“云原生容器Clouder认证“系列中的第二阶段。课程将向您介绍与容器集群相关的概念和技术,这些概念和技术可以帮助您了解阿里云容器服务ACK/ACK Serverless的使用。同时,本课程也会向您介绍可以采取的工具、方法和可操作步骤,以帮助您了解如何基于容器服务ACK Serverless构建和管理企业级应用。 学习完本课程后,您将能够: 掌握容器集群、容器编排的基本概念 掌握Kubernetes的基础概念及核心思想 掌握阿里云容器服务ACK/ACK Serverless概念及使用方法 基于容器服务ACK Serverless搭建和管理企业级网站应用
相关文章
|
1天前
|
Kubernetes 持续交付 开发工具
阿里云协同万兴科技落地ACK One GitOps方案,全球多机房应用自动化发布,效率提升50%
阿里云协同万兴科技落地ACK One GitOps方案,全球多机房应用自动化发布,效率提升50%
|
29天前
|
存储 监控 对象存储
ACK 容器监控存储全面更新:让您的应用运行更稳定、更透明
针对本地存储和 PVC 这两种容器存储使用方式,我们对 ACK 的容器存储监控功能进行了全新升级。此次更新完善了对集群中不同存储类型的监控能力,不仅对之前已有的监控大盘进行了优化,还针对不同的云存储类型,上线了全新的监控大盘,确保用户能够更好地理解和管理容器业务应用的存储资源。
117 21
|
1月前
|
存储 监控 对象存储
ACK容器监控存储全面更新:让您的应用运行更稳定、更透明
介绍升级之后的ACK容器监控体系,包括各大盘界面展示和概要介绍。
|
1月前
|
缓存 Kubernetes Docker
GitLab Runner 全面解析:Kubernetes 环境下的应用
GitLab Runner 是 GitLab CI/CD 的核心组件,负责执行由 `.gitlab-ci.yml` 定义的任务。它支持多种执行方式(如 Shell、Docker、Kubernetes),可在不同环境中运行作业。本文详细介绍了 GitLab Runner 的基本概念、功能特点及使用方法,重点探讨了流水线缓存(以 Python 项目为例)和构建镜像的应用,特别是在 Kubernetes 环境中的配置与优化。通过合理配置缓存和镜像构建,能够显著提升 CI/CD 流水线的效率和可靠性,助力开发团队实现持续集成与交付的目标。
|
2月前
|
存储 Kubernetes 关系型数据库
阿里云ACK备份中心,K8s集群业务应用数据的一站式灾备方案
本文源自2024云栖大会苏雅诗的演讲,探讨了K8s集群业务为何需要灾备及其重要性。文中强调了集群与业务高可用配置对稳定性的重要性,并指出人为误操作等风险,建议实施周期性和特定情况下的灾备措施。针对容器化业务,提出了灾备的新特性与需求,包括工作负载为核心、云资源信息的备份,以及有状态应用的数据保护。介绍了ACK推出的备份中心解决方案,支持命名空间、标签、资源类型等维度的备份,并具备存储卷数据保护功能,能够满足GitOps流程企业的特定需求。此外,还详细描述了备份中心的使用流程、控制台展示、灾备难点及解决方案等内容,展示了备份中心如何有效应对K8s集群资源和存储卷数据的灾备挑战。
|
2月前
|
人工智能 Kubernetes 安全
赋能加速AI应用交付,F5 BIG-IP Next for Kubernetes方案解读
赋能加速AI应用交付,F5 BIG-IP Next for Kubernetes方案解读
82 13
|
3月前
|
Kubernetes 监控 安全
容器化技术:Docker与Kubernetes的实战应用
容器化技术:Docker与Kubernetes的实战应用
|
3月前
|
Java Docker 微服务
利用Docker容器化部署Spring Boot应用
利用Docker容器化部署Spring Boot应用
72 0
|
3月前
|
存储 运维 Kubernetes
K8s业务迁移最佳实践: 灵活管理资源备份与调整策略,实现高效简便的应用恢复
在当今快速变化的云原生领域,Kubernetes(K8s)集群的运维面临着诸多挑战,其中灾备与业务迁移尤为关键。ACK备份中心支持丰富的资源调整策略,在数据恢复阶段即可自动适配目标集群环境,确保业务无缝重启。
|
3月前
|
监控 持续交付 Docker
Docker 容器化部署在微服务架构中的应用有哪些?
Docker 容器化部署在微服务架构中的应用有哪些?

热门文章

最新文章