当前位置: 首页 > news >正文

Kubernetes配置管理全攻略:ConfigMap与Secret详解

目录

一、Configmap 概述

什么是 Configmap?

Configmap 能解决哪些问题?

Configmap 应用场景

使用 ConfigMap 的限制条件

二、Configmap 创建方法

命令行直接创建

通过文件创建(常用)

指定目录创建 configmap(常用)

编写 configmap 资源清单 YAML 文件

三、使用 Configmap

通过环境变量引入

通过环境变量引入

把 configmap 做成 volume,挂载到 pod(常用)

四、Configmap 热更新

一、Secret概述

二、Secret 类型

kubectl 创建类型

三、Secret 使用

Opaque 类型 Secret 的使用

创建

挂载

作为环境变量

作为文件挂载及设置 POSIX 权限

Secret 绑定 serviceAccount(不用做)

查看 secret

TLS Secret

yaml 方式创建

kubectl 创建

Docker 镜像仓库 Secret

yaml 方式创建

kubectl 方式创建

ssh 类型 secret

通过文件创建

pod 挂载 ssh secret


一、Configmap 概述

什么是 Configmap?

Configmap 是 k8s 中的资源对象,用于保存非机密性的配置的,数据可以用 key/value 键值对的形式保存,也可通过文件的形式保存。

Configmap 能解决哪些问题?

ConfigMap 的主要作用就是为了让镜像和配置文件解耦,以便实现镜像的可移植性和可复用性。

我们在部署服务的时候,每个服务都有自己的配置文件,如果一台服务器上部署多个服务:nginx、nginx、apache 等,那么这些配置都存在这个节点上,假如一台服务器不能满足线上高并发的要求,需要对服务器扩容,扩容之后的服务器还是需要部署多个服务:nginx、nginx、apache,新增加的服务器上还是要管理这些服务的配置, 如果有一个服务出现问题,需要修改配置文件,每台物理节点上的配置都需要修改, 这种方式肯定满足不了线上大批量的配置变更要求。 所以,k8s 中引入了 Configmap 资源对象,可以当成 volume 挂载到 pod 中,实现统一的配置管理。

1、Configmap 是 k8s 中的资源, 相当于配置文件,可以有一个或者多个 Configmap;

2、Configmap 可以做成 Volume,k8s pod 启动之后,通过 volume 形式映射到容器内部指定目录上;

3、容器中应用程序按照原有方式读取容器特定目录上的配置文件。

4、在容器看来,配置文件就像是打包在容器内部特定目录,整个过程对应用没有任何侵入。

Configmap 应用场景

1、使用 k8s 部署应用,当你将应用配置写进代码中,更新配置时也需要打包镜像,configmap 可以将配置信息和 docker 镜像解耦,以便实现镜像的可移植性和可复用性,因为一个 configMap 其实就是一系列配置信息的集合,可直接注入到 Pod 中给容器使用。configmap 注入方式有两种,一种将 configMap 做为存储卷,一种是将configMap 通过 env 中 configMapKeyRef 注入到容器中。

2、使用微服务架构的话,存在多个服务共用配置的情况,如果每个服务中单独一份配置的话,那么更新配置就很麻烦,使用 configmap 可以友好的进行配置共享。

使用 ConfigMap 的限制条件

  • ConfigMap 需要在 Pod 启动前创建出来;

  • 并且只有当 ConfigMap 和 Pod 处于同一命名空间时,才可以被 Pod 引用;

  • 当 Pod 挂载 ConfigMap 绑定的目录时,目录下的目录并不会挂载到 Pod 内,只有目录下的文件会被挂载。

  • ConfigMap 在设计上不是用来保存大量数据的。在 ConfigMap 中保存的数据不可超过 1MiB。如果你需要保存超出此尺寸限制的数据,可以考虑挂载存储卷或者使用独立的数据库或者文件服务。

二、Configmap 创建方法

命令行直接创建

直接在命令行中指定 configmap 参数创建,通过--from-literal 指定参数

[root@k8s-master01 ~]# kubectl create configmap nginx-config --from-literal=nginx_port=8080 --from-literal=server_name=myapp.nginx.com
​
[root@k8s-master01 ~]# kubectl get configmap
​
NAME               DATA   AGE
​
kube-root-ca.crt   1      13d
​
nginx-config      2      51s
​
[root@k8s-master01 ~]# kubectl get cm
​
NAME               DATA   AGE
​
kube-root-ca.crt   1      13d
​
nginx-config      2      66s
​
[root@k8s-master01 ~]# kubectl describe configmap nginx-config
​
Name:         nginx-config
Namespace:    default
Labels:       <none>
Annotations:  <none>
​
Data
====
server_name:
----
nginx.jx.com
nginx_port:
----
8080
​
BinaryData
====
​
Events:  <none>
​
###查看创建的configmap的yaml信息
[root@k8s-master01 ~]# kubectl get cm nginx-config -o yaml
apiVersion: v1
data:server_name: nginx.jx.comnginx_port: "8080"
kind: ConfigMap
metadata:creationTimestamp: "2024-02-01T06:57:54Z"name: nginx-confignamespace: defaultresourceVersion: "616425"uid: 062bd992-202a-4ac3-a578-32542792a43a

创建选项解析:

--allow-missing-template-keys

含义:如果设置为true,当模板中的字段或映射键在数据来源中缺失时,忽略模板中的任何错误。

--append-hash

含义:将configmap的哈希值附加到它的名称后面。

--as-group

含义:指定操作时要模拟的组。这个标志可以重复使用,以指定多个组,用于在操作中进行权限模拟。

--as-uid

含义:指定操作时要模拟的用户ID(UID)。

--as

含义:指定操作时要模拟的用户名。这个用户可以是普通用户或者服务账户,用于在操作中进行权限模拟。

--cache-dir

含义:默认的缓存目录路径。

--certificate-authority

含义:指向证书颁发机构(CA)证书文件的路径,用于验证服务器证书的合法性。

--client-certificate

含义:指向用于TLS(传输层安全协议)的客户端证书文件的路径。

--client-key

含义:指向用于TLS的客户端密钥文件的路径。

--cluster

含义:指定要使用的kubeconfig中的集群名称。kubeconfig是Kubernetes用于配置客户端访问集群的文件。

--context

含义:指定要使用的kubeconfig中的上下文名称。上下文包含了集群、用户和命名空间等信息,用于确定如何与集群进行交互。

--disable-compression

含义:如果设置为true,对发送到服务器的所有请求都不使用响应压缩。

--dry-run

含义:必须是“none”、“server”或“client”之一。如果是“client”策略,仅打印出将要发送到服务器的对象,而不实际执行创建操作;“server”可能在服务器端进行一些验证但不持久化;“none”则是正常执行操作。

--field-manager

含义:用于跟踪字段所有权的管理器名称。

--from-env-file

含义:指定一个文件路径,用于读取以键值对(key=val)形式的行来创建configmap。

--from-file

含义:可以使用文件路径来指定键文件,在这种情况下,文件的基本名称(不含路径)将被用作configmap中的键,文件内容作为值。

--from-literal

含义:指定一个键和一个字面量值,用于插入到configmap中(例如mykey=somevalue)。

--help

含义:显示configmap相关的帮助信息。

--insecure-skip-tls-verify

含义:如果设置为true,将不会检查服务器证书的有效性。这会使你的连接变得不安全,但在某些测试或特殊环境下可能会用到。

--kubeconfig

含义:指向用于命令行接口(CLI)请求的kubeconfig文件的路径。

--log-flush-frequency

含义:日志刷新的最大间隔秒数,即多久将日志缓冲区中的内容刷新输出一次。

--match-server-version

含义:要求服务器版本与客户端版本匹配。

--namespace

含义:如果存在此选项,它指定了这个命令行请求的命名空间范围。命名空间用于在Kubernetes集群中对资源进行隔离和分组。

--output

含义:输出格式。可以是以下之一:(json、yaml、name、go-template、go-template-file、template等),用于指定命令执行结果的输出格式。

--password

含义:用于对API服务器进行基本身份验证的密码。

--profile

含义:要捕获的性能分析(profile)名称。可以是(none、cpu、heap、goroutine、threadcreate、block、mutex)之一,用于对Kubernetes组件的性能进行分析。

--profile-output

含义:指定要将性能分析结果写入的文件名。

--request-timeout

含义:在放弃单个服务器请求之前等待的时间长度。非零值会设置请求超时时间,避免长时间等待无响应的服务器。

--save-config

含义:如果设置为true,当前对象的配置将保存在其注释中。否则,不会保存配置。

--server

含义:Kubernetes API服务器的地址和端口,用于指定客户端连接的服务器位置。

--show-managed-fields

含义:如果设置为true,在以JSON或YAML格式打印对象时,保留managedFields字段。这些字段通常用于记录资源的管理信息。

--template

含义:当-o=go-template、-o=go-template-file等输出格式选项被使用时,指定要使用的模板字符串或模板文件路径。

--tls-server-name

含义:用于服务器证书验证的服务器名称。如果未提供,将使用主机名进行验证。

--token

含义:用于对API服务器进行身份验证的承载令牌(Bearer Token)。

--username

含义:用于对API服务器进行基本身份验证的用户名。

--user

含义:指定要使用的kubeconfig用户的名称。

--validate

含义:必须是以下之一:strict(或true)、warn、ignore(或false),用于指定对资源配置的验证级别。

--vmodule

含义:逗号分隔的pattern=N设置列表,用于基于文件过滤的日志记录(仅适用于特定的日志系统)。

--v

含义:日志级别详细程度的数字表示,用于控制日志输出的信息量。

--warnings-as-errors

含义:将从服务器接收到的警告视为错误,并以非零退出码退出命令执行。

通过文件创建(常用)

通过指定文件创建一个 configmap,--from-file=<文件>,若没有定义key,则使用文件名作为key,文件内容作为value。

[root@k8s-master01 configmap]# cat nginx.conf
​
server {
​
server_name www.nginx.com;
​
listen 80;
​
root /home/nginx/www/
​
}
​
[root@k8s-master01 configmap]# kubectl create configmap nginx-conf --from-file=www.conf=./nginx.conf 
configmap/nginx-conf created    
​
[root@k8s-master01 configmap]#  kubectl describe configmap nginx-config
​
Name:         nginx-conf
Namespace:    default
Labels:       <none>
Annotations:  <none>
​
Data
====
www.conf:
----
server {
​
server_name www.nginx.com;
​
listen 80;
​
root /home/nginx/www/
​
}
​
​
BinaryData
====
​
Events:  <none>
​
​
[root@k8s-master01 configmap]# kubectl get cm nginx-conf -o yaml
apiVersion: v1
data:www.conf: |  server {
​server_name www.nginx.com;
​listen 80;
​root /home/nginx/www/
​}
kind: ConfigMap
metadata:creationTimestamp: "2024-02-01T07:12:53Z"name: nginx-confnamespace: defaultresourceVersion: "618054"uid: 3ee6f787-9372-4bda-b0f6-d350b2235d50##www.conf: | 作用是表示www.conf这个可以的内容是多行的。

指定目录创建 configmap(常用)

[root@k8s-master01 configmap]# mkdir mysql-test
[root@k8s-master01 configmap]# cd mysql-test/
[root@k8s-master01 mysql-test]# echo server_id=1 > mysql.cnf
[root@k8s-master01 mysql-test]# echo server_id=2 > mysql2.cnf
​
[root@k8s-master01 configmap]# kubectl create configmap mysql-cnf --from-file=/root/configmap/mysql-test/
configmap/mysql-cnf created
​
#查看 configmap 详细信息
​
[root@k8s-master01 configmap]# kubectl describe cm mysql-cnf 
Name:         mysql-cnf
Namespace:    default
Labels:       <none>
Annotations:  <none>
​
Data
====
mysql.cnf:
----
server_id=1
​
mysql2.cnf:
----
server_id=2
​
​
BinaryData
====
​
Events:  <none>
​
[root@k8s-master01 configmap]# kubectl get cm mysql-cnf -o yaml
apiVersion: v1
data:mysql.cnf: |server_id=1mysql2.cnf: |server_id=2
kind: ConfigMap
metadata:creationTimestamp: "2024-02-01T07:16:32Z"name: mysql-cnfnamespace: defaultresourceVersion: "618449"uid: 3fc1c8ef-5ddd-477b-bc52-2ecf2de86e25

编写 configmap 资源清单 YAML 文件

[root@k8s-master01 configmap]# cat mysql-configmap.yaml
​
apiVersion: v1
kind: ConfigMap
metadata:name: mysqllabels:app: mysql
data:master.cnf: |[mysqld]log-binlog_bin_trust_function_creators=1lower_case_table_names=1slave.cnf: |[mysqld]super-read-onlylog_bin_trust_function_creators=1
​
#上面中的 | 表示master.cnf文件是多行文件
[root@k8s-master01 configmap]# kubectl get cm mysql -o yaml
apiVersion: v1
data:master.cnf: |[mysqld]log-binlog_bin_trust_function_creators=1lower_case_table_names=1slave.cnf: |[mysqld]super-read-onlylog_bin_trust_function_creators=1
kind: ConfigMap
metadata:annotations:kubectl.kubernetes.io/last-applied-configuration: |{"apiVersion":"v1","data":{"master.cnf":"[mysqld]\nlog-bin\nlog_bin_trust_function_creators=1\nlower_case_table_names=1\n","slave.cnf":"[mysqld]\nsuper-read-only\nlog_bin_trust_function_creators=1\n"},"kind":"ConfigMap","metadata":{"annotations":{},"labels":{"app":"mysql"},"name":"mysql","namespace":"default"}}creationTimestamp: "2024-02-01T07:39:13Z"labels:app: mysqlname: mysqlnamespace: defaultresourceVersion: "620920"uid: acad5d26-6692-4c1b-a389-cd37bbe81d7d

三、使用 Configmap

通过环境变量引入

使用 configMapKeyRef变量

#创建一个存储 mysql 配置的 configmap
​
[root@k8s-master01 ~]# cat mysql-configmap.yaml
apiVersion: v1
kind: ConfigMap
metadata:name: mysqllabels:app: mysql
data:log: "1"lower: "1"
[root@k8s-master01 ~]# kubectl apply -f mysql-configmap.yaml
​
configmap/mysql created
​
[root@k8s-master01 ~]# kubectl get cm
​
NAME               DATA   AGE
​
kube-root-ca.crt   1      13d
​
mysql              2      82s
​
#创建 pod,引用 Configmap 中的内容
​
[root@k8s-master01 ~]# cat mysql-pod.yaml
​
apiVersion: v1
kind: Pod
metadata:name: mysql-pod
spec:containers:- name: mysqlimage: busybox:1.28imagePullPolicy: IfNotPresentcommand: [ "/bin/sh", "-c", "sleep 3600" ]env:- name: log_bin #定义环境变量 log_binvalueFrom:configMapKeyRef:name: mysql #指定 configmap 的名字key: log #指定 configmap 中的 key- name: lower #定义环境变量 lowervalueFrom:configMapKeyRef:name: mysqlkey: lowerrestartPolicy: Never
​
​
#更新资源清单文件
​
[root@k8s-master01 ~]# kubectl apply -f mysql-pod.yaml
​
[root@k8s-master01 ~]#  kubectl exec -it mysql-pod -- /bin/sh
​
/ # env
log_bin=1
KUBERNETES_PORT=tcp://10.10.0.1:443
KUBERNETES_SERVICE_PORT=443
HOSTNAME=mysql-pod
NGINX_SVC_NODEPORT_PORT_8000_TCP_ADDR=10.10.166.16
SHLVL=1
HOME=/root
NGINX_SVC_NODEPORT_PORT_8000_TCP_PORT=8000
NGINX_SVC_NODEPORT_PORT_8000_TCP_PROTO=tcp
SERVICE_BLUE_SERVICE_HOST=10.10.157.201
NGINX_SVC_NODEPORT_SERVICE_HOST=10.10.166.16
SERVICE_BLUE_SERVICE_PORT=80
SERVICE_BLUE_PORT=tcp://10.10.157.201:80
NGINX_SVC_NODEPORT_PORT_8000_TCP=tcp://10.10.166.16:8000
TERM=xterm
lower=1
KUBERNETES_PORT_443_TCP_ADDR=10.10.0.1
NGINX_SVC_NODEPORT_PORT=tcp://10.10.166.16:8000
NGINX_SVC_NODEPORT_SERVICE_PORT=8000
PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin
SERVICE_BLUE_PORT_80_TCP_ADDR=10.10.157.201
KUBERNETES_PORT_443_TCP_PORT=443
KUBERNETES_PORT_443_TCP_PROTO=tcp
SERVICE_BLUE_PORT_80_TCP_PORT=80
SERVICE_BLUE_PORT_80_TCP_PROTO=tcp
KUBERNETES_SERVICE_PORT_HTTPS=443
KUBERNETES_PORT_443_TCP=tcp://10.10.0.1:443
KUBERNETES_SERVICE_HOST=10.10.0.1
PWD=/
SERVICE_BLUE_PORT_80_TCP=tcp://10.10.157.201:80

通过环境变量引入

#使用 envfrom变量
​
[root@k8s-master01 ~]# cat  mysql-pod-envfrom.yaml
​
apiVersion: v1
kind: Pod
metadata:name: mysql-pod-envfrom
spec:containers:- name: mysqlimage: busybox:1.28imagePullPolicy: IfNotPresentcommand: [ "/bin/sh", "-c", "sleep 3600" ]envFrom:- configMapRef:name: mysql  #指定configmap的名字restartPolicy: Never
​
#更新资源清单文件
​
[root@k8s-master01 ~]# kubectl apply -f mysql-pod-envfrom.yaml
​
pod/mysql-pod-envfrom created
​
[root@k8s-master01 ~]# kubectl get pods
​
NAME                               READY   STATUS    RESTARTS   AGE
​
mysql-pod                          1/1     Running   0          13m
​
mysql-pod-envfrom                  1/1     Running   0          107s
​
[root@k8s-master01 ~]#  kubectl exec -it mysql-pod-envfrom -c mysql -- /bin/sh
​
/ # env
KUBERNETES_PORT=tcp://10.10.0.1:443
KUBERNETES_SERVICE_PORT=443
HOSTNAME=mysql-pod-envfrom
NGINX_SVC_NODEPORT_PORT_8000_TCP_ADDR=10.10.166.16
SHLVL=1
HOME=/root
NGINX_SVC_NODEPORT_PORT_8000_TCP_PORT=8000
NGINX_SVC_NODEPORT_PORT_8000_TCP_PROTO=tcp
SERVICE_BLUE_SERVICE_HOST=10.10.157.201
NGINX_SVC_NODEPORT_SERVICE_HOST=10.10.166.16
SERVICE_BLUE_SERVICE_PORT=80
SERVICE_BLUE_PORT=tcp://10.10.157.201:80
NGINX_SVC_NODEPORT_PORT_8000_TCP=tcp://10.10.166.16:8000
TERM=xterm
lower=1
KUBERNETES_PORT_443_TCP_ADDR=10.10.0.1
NGINX_SVC_NODEPORT_PORT=tcp://10.10.166.16:8000
NGINX_SVC_NODEPORT_SERVICE_PORT=8000
PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin
log=1
KUBERNETES_PORT_443_TCP_PORT=443
SERVICE_BLUE_PORT_80_TCP_ADDR=10.10.157.201
KUBERNETES_PORT_443_TCP_PROTO=tcp
SERVICE_BLUE_PORT_80_TCP_PORT=80
SERVICE_BLUE_PORT_80_TCP_PROTO=tcp
KUBERNETES_PORT_443_TCP=tcp://10.10.0.1:443
KUBERNETES_SERVICE_PORT_HTTPS=443
KUBERNETES_SERVICE_HOST=10.10.0.1
PWD=/
SERVICE_BLUE_PORT_80_TCP=tcp://10.10.157.201:80
/ # 

把 configmap 做成 volume,挂载到 pod(常用)

[root@k8s-master01 ~]# cat mysql-configmap.yaml
​
apiVersion: v1
kind: ConfigMap
metadata:name: mysqllabels:app: mysql
data:log: "1"lower: "1"my.cnf: |[mysqld]welcome=duoduo
​
[root@k8s-master01 ~]# kubectl apply -f mysql-configmap.yaml
​
configmap/mysql configured
​
#查看详细配置信息
​
[root@k8s-master01 ~]# kubectl describe configmap mysql
​
Name:         mysql
Namespace:    default
Labels:       app=mysql
Annotations:  <none>
​
Data
====
log:
----
1
lower:
----
1
my.cnf:
----
[mysqld]
welcome=duoduo
​
​
BinaryData
====
​
Events:  <none>
​
#创建pod资源清单文件,挂载configmap卷
​
[root@k8s-master01 ~]# cat mysql-pod-volume.yaml
​
apiVersion: v1
kind: Pod
metadata:name: mysql-pod-volume
spec:containers:- name: mysqlimage: busybox:1.28imagePullPolicy: IfNotPresentcommand: [ "/bin/sh","-c","sleep 3600" ]volumeMounts:- name: mysql-configmountPath: /tmp/configvolumes:- name: mysql-configconfigMap:name: mysqlrestartPolicy: Never
​
[root@k8s-master01 ~]# kubectl apply -f mysql-pod-volume.yaml
​
pod/mysql-pod-volume created
​
[root@k8s-master01 configmap]# kubectl exec -it mysql-pod-volume -- /bin/sh
/ # 
/ # 
/ # 
/ # cd /tmp/config/
/tmp/config # ls
log     lower   my.cnf
/tmp/config # ls -l
total 0
lrwxrwxrwx    1 root     root            10 Feb  1 08:12 log -> ..data/log
lrwxrwxrwx    1 root     root            12 Feb  1 08:12 lower -> ..data/lower
lrwxrwxrwx    1 root     root            13 Feb  1 08:12 my.cnf -> ..data/my.cnf

四、Configmap 热更新

仅限于卷的形式,如果是环境变量的形式则不更新!!!

限于应用程序能够对配置文件进行动态感知。nginx不行,需要在apply之后对pod执行命令:

nginx -s reload
[root@k8s-master01 ~]# kubectl edit configmap mysql
​
#将log:1 变成 log:2
apiVersion:v1
data:log:"2"lower:"1"
重新执行一次资源清单文件[root@k8s-master01 test1]# kubectl apply -f mysql-pod-volume.yaml
​
pod/mysql-pod-volume configured
​
[root@k8s-master01 ~]# kubectl exec -it mysql-pod-volume -- /bin/sh
​
/ # cat /tmp/config/log
​
2/ #
​
#一次构建镜像,通过配置管理中心configmap 实现了 多场景运行

在 Kubernetes 1.24 版本中,如果 ConfigMap 无法进行热更新,可能有以下几种原因及解决方法:

一、检查更新方式

  1. 对于环境变量方式

- 如果是通过环境变量的方式将 ConfigMap 中的值注入到容器中,那么 Kubernetes 本身是不支持自动热更新环境变量的。这种情况下,应用程序需要自己有重新读取环境变量的机制。例如,应用可以定期重新读取环境变量或者通过监听文件系统变化等方式来实现类似的效果,但这需要在应用层面进行开发。

- 示例代码(在应用中实现定期重新读取环境变量的伪代码):

python

   import time
​​def reload_environment_variables():

# 重新获取环境变量的逻辑

pass

while True:
​
reload_environment_variables()
​
time.sleep(60)  # 每分钟重新加载一次环境变量

- 注意,这只是一个简单的示例,实际实现可能因应用程序的编程语言和运行环境而有所不同。

  1. 对于挂载文件方式

- 当以文件形式挂载 ConfigMap 到容器中时,Kubernetes 支持一定程度的热更新。但这也依赖于应用程序是否能够检测到文件内容的变化并重新加载。一些应用程序(如 NGINX)可以自动检测并重新加载配置文件的变化,而有些应用可能需要通过发送信号(如 SIGHUP)等方式来触发重新加载。

- 例如,对于 NGINX,当它检测到挂载的配置文件(来自 ConfigMap)发生变化时,它会自动重新加载配置。但如果应用没有这种自动检测和重新加载的机制,你可能需要在容器内编写一个脚本或使用工具来监控文件变化并触发应用的重新加载。

- 以下是一个使用 inotifywait(Linux 下的文件变化监控工具)来监控文件变化并执行重新加载命令的示例脚本(假设应用的重新加载命令是myapp reload):

   #!/bin/bash
​​while true; do
​
•    inotifywait -e modify /path/to/config/file  # 将/path/to/config/file替换为实际的挂载文件路径
​
•    myapp reload  # 执行应用的重新加载命令
​done

- 这个脚本需要在容器内运行,并且需要安装 inotify-tools。你可以将其添加到容器的启动命令或者作为一个单独的进程运行。

二、检查相关组件和配置

  1. 确保 Kubernetes 版本和功能正常

- 虽然 1.24 版本理论上应该支持 ConfigMap 的挂载文件热更新,但可能存在一些特定的配置或环境因素导致问题。确保你的 Kubernetes 集群是正确安装和配置的,并且相关的组件(如 kubelet 等)运行正常。可以检查 kubelet 的日志,看是否有任何与 ConfigMap 处理相关的错误或警告信息。

- 查看 kubelet 日志的命令(在节点上执行):

   journalctl -u kubelet -f  # -f 选项用于实时跟踪日志
  1. 检查 Pod 和容器配置

- 确认 Pod 的配置正确地将 ConfigMap 挂载到容器中。检查 Pod 的 YAML 配置文件,确保挂载路径和方式正确。

- 例如,以下是一个 Pod 配置中挂载 ConfigMap 的示例片段:

   apiVersion: v1
​kind: Pod
​metadata:
​
•    name: myapp-pod
​spec:
​
•    containers:
​
•    \- name: myapp-container
​
•     image: myapp-image
​
•     volumeMounts:
​
•     \- name: config-volume
​
•      mountPath: /etc/config  # 挂载路径
​
•      readOnly: true
​
•    volumes:
​
•    \- name: config-volume
​
•     configMap:
​
•      name: my-configmap

- 确保mountPath是应用程序预期的路径,并且configMap的名称正确指向你想要更新的 ConfigMap。

  1. 检查应用程序自身的行为

- 有些应用程序可能在启动时读取配置文件并缓存了内容,之后不再重新读取。这种情况下,即使 ConfigMap 的文件内容更新了,应用程序也不会感知到变化。需要检查应用程序的文档或代码,了解它是否有这种行为,并根据需要进行调整。

- 例如,如果应用是用 Java 编写的,并且使用了类似 Spring 的框架,可能需要配置 Spring 的相关属性来支持配置文件的热更新。具体配置可能因应用架构和使用的技术栈而异。

三、其他可能的问题和解决方法

  1. 网络和存储问题

- 如果 ConfigMap 的更新在存储后端(如 etcd)成功,但容器无法及时获取到更新后的内容,可能是网络或存储相关的问题。检查节点之间的网络连接,确保容器能够正常访问存储 ConfigMap 的 etcd 或其他存储系统。

- 可以使用网络诊断工具(如 ping、traceroute 等)来检查网络连通性。如果是存储系统的问题,可能需要进一步检查存储的配置和状态,看是否有性能瓶颈或错误。

  1. 权限问题

- 容器内的应用程序可能没有足够的权限来读取更新后的 ConfigMap 文件。确保容器运行的用户或进程有对挂载目录的读取权限。

- 可以检查容器的安全上下文(security context)设置,确保它允许对挂载文件的正确访问。例如,在 Pod 的 YAML 配置文件中可以设置容器的安全上下文如下:

   apiVersion: v1
​kind: Pod
​metadata:
​
•    name: myapp-pod
​spec:
​
•    containers:
​
•    \- name: myapp-container
​
•     image: myapp-image
​
•     volumeMounts:
​
•     \- name: config-volume
​
•      mountPath: /etc/config
​
•      readOnly: true
​
•     securityContext:
​
•      runAsUser: 1000  # 设置容器内运行的用户 ID
​
•      readOnlyRootFilesystem: false  # 根据需要设置根文件系统的只读属性

- 这里的runAsUser设置了容器内运行的用户 ID,你需要根据实际情况调整。

如果以上方法都无法解决问题,可能需要更深入地分析应用程序和 Kubernetes 环境的具体情况,或者考虑使用其他方式来实现配置的动态更新,例如使用一些专门的配置管理工具或框架来与 Kubernetes 集成。

一、Secret概述

k8s secrets用于存储和管理一些敏感数据,比如密码,token,密钥等敏感信息。它把 Pod 想要访问的加密数据存放到 Etcd 中。然后用户就可以通过在 Pod 的容器里挂载 Volume 的方式或者环境变量的方式访问到这些 Secret 里保存的信息了。

Secret 类似于 ConfigMap,但专门用于保存机密数据。

二、Secret 类型

内置类型用法
Opaque用户定义的任意数据
kubernetes.io/service-account-tokensymotion服务账号令牌
kubernetes.io/dockercfg~/.dockercfg 文件的序列化形式
kubernetes.io/dockerconfigjson~/.docker/config.json 文件的序列化形式
kubernetes.io/basic-auth用于基本身份认证的凭据
kubernetes.io/ssh-auth用于 SSH 身份认证的凭据
kubernetes.io/tls用于 TLS 客户端或者服务器端的数据
bootstrap.kubernetes.io/token启动引导令牌数据

kubectl 创建类型

[root@k8s-master01 ~]# kubectl create secret dotfile -h
Create a secret using specified subcommand.
​
Available Commands:docker-registry   创建一个给 Docker registry 使用的 secretgeneric           Create a secret from a local file, directory, or literal valuetls               创建一个 TLS secret
​
Usage:kubectl create secret [flags] [options]
​
Use "kubectl <command> --help" for more information about a given command.
Use "kubectl options" for a list of global command-line options (applies to all commands).
  • docker-registry: 连接私有镜像仓库的凭证(据)

  • generic: 常见 secret, 该类型 secret 与 configmap使用相同

  • tls: 提供 tls 证书, 在 service mesh 中自动挂载

三、Secret 使用

使用场景:

  • 设置容器的环境变量

  • 向 Pod 提供 SSH 密钥或密码等凭据

  • 允许 kubelet 从私有镜像仓库中拉取镜像

Opaque 类型 Secret 的使用

创建
  1. kubectl create

[root@k8s-master01 ~]# kubectl create secret generic dotfile --from-literal=username=admin --from-literal=password=123456
​
[root@k8s-master01 ~]# kubectl get secret dotfile -o yaml
apiVersion: v1
data:password: MTIzNDU2username: YWRtaW4=
kind: Secret
metadata:creationTimestamp: "2024-01-09T07:45:19Z"name: dotfilenamespace: defaultresourceVersion: "621858"uid: ce3a3332-5b97-4af0-8312-ced355786e64
type: Opaque
​
[root@k8s-master01 ~]# echo -n "YWRtaW4=" | base64 -d
admin
  1. yaml

以 yaml 方式创建需要你提前进行 base64

[root@k8s-master01 ~]# echo -n "admin" | base64
YWRtaW4=
[root@k8s-master01 ~]# echo -n "123456" | base64
MTIzNDU2
​
apiVersion: v1
kind: Secret
metadata:name: secret-volumenamespace: default
type: Opaque
data:password: MTIzNDU2username: YWRtaW4=
immutable: true
####警告信息
Warning: resource secrets/dotfile is missing the kubectl.kubernetes.io/last-applied-configuration annotation which is required by kubectl apply. kubectl apply should only be used on resources created declaratively by either kubectl create --save-config or kubectl apply. The missing annotation will be patched automatically.
#表示存在同名的secret

你可以通过将 Secret 的 immutable 字段设置为 true 创建不可更改的 Secret。

创建

$ kubectl create -f dotfile-secret.yaml
挂载
  1. 作为环境变量

创建 pod

[root@k8s-master01 secret]# cat secret-pod.yaml
apiVersion: v1
kind: Pod
metadata:name: pod1
spec:containers:- image: busybox:1.28name: busyboxcommand: ["/bin/sh","-c","echo $username && env"]env:- name: usernamevalueFrom:secretKeyRef:key: usernamename: secret-volume    # secret 名称
####pod不会运行,测试时需要查看日志####          ######或者########
[root@k8s-master01 secret]# cat secret-pod.yaml 
apiVersion: v1
kind: Pod
metadata:name: pod1
spec:containers:- image: busybox:1.28name: busyboxcommand: ["/bin/sh","-c","sleep 3600"]env:- name: usernamevalueFrom:secretKeyRef:key: usernamename: secret-volume    # secret 名称
####pod会启动,需要进入容器中查看####

获取容器日志

# 创建
[root@k8s-master01 secret]# kubectl create -f pod1.yaml
​
[root@k8s-master01 secret]# kubectl logs pod1
admin
KUBERNETES_PORT=tcp://10.10.0.1:443
KUBERNETES_SERVICE_PORT=443
HOSTNAME=pod1
NGINX_SVC_NODEPORT_PORT_8000_TCP_ADDR=10.10.166.16
SHLVL=1
username=admin
HOME=/root
NGINX_SVC_NODEPORT_PORT_8000_TCP_PORT=8000
SERVICE_BLUE_SERVICE_HOST=10.10.157.201
NGINX_SVC_NODEPORT_PORT_8000_TCP_PROTO=tcp
NGINX_SVC_NODEPORT_SERVICE_HOST=10.10.166.16RVICE_BLUE_SERVICE_PORT=80
SERVICE_BLUE_PORT=tcp://10.10.157.201:80
NGINX_SVC_NODEPORT_PORT_8000_TCP=tcp://10.10.166.16:8000
KUBERNETES_PORT_443_TCP_ADDR=10.10.0.1
NGINX_SVC_NODEPORT_PORT=tcp://10.10.166.16:8000
NGINX_SVC_NODEPORT_SERVICE_PORT=8000
PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin
SERVICE_BLUE_PORT_80_TCP_ADDR=10.10.157.201
KUBERNETES_PORT_443_TCP_PORT=443
KUBERNETES_PORT_443_TCP_PROTO=tcp
SERVICE_BLUE_PORT_80_TCP_PORT=80
SERVICE_BLUE_PORT_80_TCP_PROTO=tcp
KUBERNETES_PORT_443_TCP=tcp://10.10.0.1:443
KUBERNETES_SERVICE_PORT_HTTPS=443
KUBERNETES_SERVICE_HOST=10.10.0.1
PWD=/
SERVICE_BLUE_PORT_80_TCP=tcp://10.10.157.201:80
  1. 作为文件挂载及设置 POSIX 权限

创建 pod

apiVersion: v1
kind: Pod
metadata:name: pod2
spec:volumes:- name: secsecret:secretName: secret-volumedefaultMode: 0400  # 设置文件权限containers:- image: busybox:1.28name: busyboxcommand: ["sleep", "24h"]volumeMounts:- mountPath: /etc/configname: sec

注意: secret 挂载到容器后自动 base64 解码

$ kubectl exec pod2 -- ls -l /etc/config/
total 0
lrwxrwxrwx    1 root     root            15 Jan  9 08:00 password -> ..data/password
lrwxrwxrwx    1 root     root            15 Jan  9 08:00 username -> ..data/username
​
$ kubectl exec pod2 -- cat /etc/config/username
admin
Secret 绑定 serviceAccount(不用做)

k8s 中 pod 会挂载 serviceAccount

  • 挂载路径: /var/run/secrets/kubernetes.io/serviceaccount

  • 挂载内容该 serviceAccount 的: ca.crt, namespace , token

secret:

apiVersion: v1
kind: Secret
metadata:name: sa-secretannotations:kubernetes.io/service-account.name: "tdd"
type: kubernetes.io/service-account-token
data:password: MTIzNDU2username: YWRtaW4=

我们为 secret 添加了 kubernetes.io/service-account.name字段, 为其指定的 serviceAccount, 创建了 Secret 之后,等待 Kubernetes 在 data 字段中填充 token 主键。

查看 secret

可以看到 kubernetes 控制器自动为其填充了 namespace, token, ca

TLS Secret

创建方式

yaml 方式创建
apiVersion: v1
kind: Secret
metadata:name: secret-tls
type: kubernetes.io/tls
data:# 值为 base64 编码,这样会掩盖它们,但不会提供任何有用的机密性级别tls.crt: |LS0tLS1CRUdJTiBDRVJUSUZJQ0FURS0tLS0tCk1JSUNVakNDQWJzQ0FnMytNQTBHQ1NxR1NJYjNEUUVCQlFVQU1JR2JNUXN3Q1FZRFZRUUdFd0pLVURFT01Bd0cKQTFVRUNCTUZWRzlyZVc4eEVEQU9C......    # 在这个例子中,密钥数据不是真正的 PEM 编码的私钥tls.key: |RXhhbXBsZSBkYXRhIGZvciB0aGUgVExTIGNydCBmaWVsZA==     
kubectl 创建
$ kubectl create secret tls my-tls-secret \--cert=path/to/cert/file \--key=path/to/key/file

Docker 镜像仓库 Secret

yaml 方式创建
apiVersion: v1
kind: Secret
metadata:name: secret-dockercfg
type: kubernetes.io/dockercfg
data:.dockercfg: |eyJhdXRocyI6eyJodHRwczovL2V4YW1wbGUvdjEvIjp7ImF1dGgiOiJvcGVuc2VzYW1lIn19fQo=
kubectl 方式创建
$ kubectl create secret docker-registry secret-tiger-docker \--docker-email=tiger@acme.example \--docker-username=tiger \--docker-password=pass1234 \--docker-server=my-registry.example:5000
​
$ kubectl get secret secret-tiger-docker -o jsonpath='{.data.*}' | base64 -d

输出等价于以下 JSON 文档(这也是一个有效的 Docker 配置文件):

{"auths": {"my-registry.example:5000": {"username": "tiger","password": "pass1234","email": "tiger@acme.example","auth": "dGlnZXI6cGFzczEyMzQ="}}
}

ssh 类型 secret

通过文件创建
$ kubectl create secret generic ssh-key-secret --from-file=ssh-privatekey=/path/to/.ssh/id_rsa --from-file=ssh-publickey=/path/to/.ssh/id_rsa.pub
pod 挂载 ssh secret
apiVersion: v1
kind: Pod
metadata:name: secret-test-podlabels:name: secret-test
spec:volumes:- name: secret-volumesecret:secretName: ssh-key-secretcontainers:- name: ssh-test-containerimage: mySshImagevolumeMounts:- name: secret-volumereadOnly: truemountPath: "/etc/secret-volume"

容器命令执行时,秘钥的数据可以在下面的位置访问到:

/etc/secret-volume/ssh-publickey
/etc/secret-volume/ssh-privatekey

容器就可以随便使用 Secret 数据来建立 SSH 连接。

http://www.dtcms.com/a/336883.html

相关文章:

  • [机器学习]10-基于ID3决策树算法的西瓜数据集分类
  • Apache RocketMQ,构建云原生统一消息引擎
  • 如何用github记录mit6s081-2020-labs学习过程
  • SQL注入防御
  • MacOS 安全机制与“文件已损坏”排查完整指南
  • 【前端】使用Vue3过程中遇到加载无效设置点击方法提示不存在的情况,原来是少加了一个属性
  • 动态规划:入门思考篇
  • SQL详细语法教程(五)事务和视图
  • zsh 使用笔记 命令行智能提示 bash智能
  • mac查看nginx安装位置 mac nginx启动、重启、关闭
  • 我的第一个开源项目:从0到1,我在GitHub写下的成长印记
  • OpenCV Python——Numpy基本操作(Numpy 矩阵操作、Numpy 矩阵的检索与赋值、Numpy 操作ROI)
  • 母猪姿态转换行为识别:计算机视觉与行为识别模型调优指南
  • 使用 ipconfig /all 获取电脑 IP 地址
  • Django 请求生命周期
  • TCP网络编程
  • Json A12 计算总和
  • Git版本控制与协作
  • 【秋招笔试】2025.08.16美团算法岗秋招机考真题
  • Cell Metab. (IF=30.9)|上海交大刘军力研究员团队:DLAT抑制亮氨酸分解驱动肿瘤发生
  • 朝花夕拾(七)--------从混淆矩阵到分类报告全面解析​
  • LeetCode 刷题【45. 跳跃游戏 II】
  • 云计算-云上实例部署 RocketChat:Mongodb、主从数据库、Node 环境配置指南
  • 生信分析自学攻略 | R软件和Rstudio的安装
  • 今日行情明日机会——20250818
  • 华为服务器设置bios中cpu为性能模式
  • week2-[循环结构]找出正数
  • element-plus:el-tree ref初始化异常记录
  • 【前端面试题】JavaScript 核心知识点解析(第一题到第三十题)
  • MQTT(轻量级消息中间件)基本使用指南