k8s之configmap

文章目录

  • k8s之configmap
    • [什么是 ConfigMap?](#什么是 ConfigMap?)
    • [为什么需要 ConfigMap?](#为什么需要 ConfigMap?)
    • [ConfigMap 的创建方式](#ConfigMap 的创建方式)
    • [ConfigMap 的使用方式](#ConfigMap 的使用方式)
    • 实际应用场景
    • [ConfigMap 最佳实践](#ConfigMap 最佳实践)
    • 参考

k8s之configmap

什么是 ConfigMap?

ConfigMap 是 Kubernetes 中用于存储非机密配置数据的 API 对象。它允许你将配置信息与容器镜像解耦,使应用程序更加灵活和可移植。ConfigMap 以键值对的形式存储数据,可以被 Pod 以多种方式消费。

为什么需要 ConfigMap?

在传统的应用部署中,配置通常硬编码在应用程序中或通过环境变量传递。这种方式存在以下问题:

  1. 配置与代码耦合:修改配置需要重新构建镜像
  2. 环境差异:不同环境需要不同的配置
  3. 安全性:敏感配置可能暴露在镜像中
  4. 维护困难:配置分散在各个地方,难以统一管理

ConfigMap 解决了这些问题,提供了一种集中化、声明式的配置管理方案。

ConfigMap 的创建方式

  1. 通过 kubectl 命令行创建
bash 复制代码
# 从字面值创建
kubectl create configmap app-config \
  --from-literal=database.host=mysql.example.com \
  --from-literal=database.port=3306

# 从文件创建
kubectl create configmap app-config --from-file=config.properties

# 从目录创建
kubectl create configmap app-config --from-file=config-dir/
  1. 通过 YAML 文件创建
yaml 复制代码
apiVersion: v1
kind: ConfigMap
metadata:
  name: app-config
  namespace: default
data:
  # 简单的键值对
  database.host: "mysql.example.com"
  database.port: "3306"
  
  # 多行配置文件
  app.properties: |
    server.port=8080
    logging.level.root=INFO
    spring.datasource.url=jdbc:mysql://mysql:3306/mydb
    
  # JSON 格式配置
  config.json: |
    {
      "server": {
        "port": 8080,
        "host": "0.0.0.0"
      },
      "database": {
        "host": "mysql.example.com",
        "port": 3306
      }
    }

ConfigMap 的使用方式

  1. 作为环境变量
yaml 复制代码
apiVersion: v1
kind: Pod
metadata:
  name: app-pod
spec:
  containers:
  - name: app
    image: myapp:latest
    env:
    # 引用单个键
    - name: DB_HOST
      valueFrom:
        configMapKeyRef:
          name: app-config
          key: database.host
    # 引用所有键作为环境变量
    envFrom:
    - configMapRef:
        name: app-config
  1. 作为命令行参数
yaml 复制代码
apiVersion: v1
kind: Pod
metadata:
  name: app-pod
spec:
  containers:
  - name: app
    image: myapp:latest
    command: ["/bin/sh"]
    args: ["-c", "echo $(DB_HOST):$(DB_PORT)"]
    env:
    - name: DB_HOST
      valueFrom:
        configMapKeyRef:
          name: app-config
          key: database.host
    - name: DB_PORT
      valueFrom:
        configMapKeyRef:
          name: app-config
          key: database.port
  1. 作为卷挂载
yaml 复制代码
apiVersion: v1
kind: Pod
metadata:
  name: app-pod
spec:
  containers:
  - name: app
    image: myapp:latest
    volumeMounts:
    - name: config-volume
      mountPath: /etc/config
  volumes:
  - name: config-volume
    configMap:
      name: app-config
      # 可选:指定特定的键和文件名
      items:
      - key: app.properties
        path: application.properties
      - key: config.json
        path: config.json

实际应用场景

场景1:Web 应用配置

复制代码
apiVersion: v1
kind: ConfigMap
metadata:
  name: webapp-config
data:
  nginx.conf: |
    server {
        listen 80;
        server_name localhost;
        
        location / {
            proxy_pass http://backend:8080;
            proxy_set_header Host $host;
            proxy_set_header X-Real-IP $remote_addr;
        }
    }
  
  app.env: |
    NODE_ENV=production
    PORT=8080
    LOG_LEVEL=info
    REDIS_URL=redis://redis:6379

场景2:数据库配置

yaml 复制代码
apiVersion: v1
kind: ConfigMap
metadata:
  name: db-config
data:
  mysql.cnf: |
    [mysqld]
    max_connections=200
    innodb_buffer_pool_size=1G
    slow_query_log=1
    long_query_time=2
    
  init.sql: |
    CREATE DATABASE IF NOT EXISTS myapp;
    USE myapp;
    CREATE TABLE IF NOT EXISTS users (
        id INT AUTO_INCREMENT PRIMARY KEY,
        username VARCHAR(50) NOT NULL,
        email VARCHAR(100) NOT NULL
    );

ConfigMap 最佳实践

  1. 命名规范
bash 复制代码
# 好的命名方式
kubectl create configmap app-database-config
kubectl create configmap frontend-nginx-config
kubectl create configmap backend-app-config

# 避免的命名方式
kubectl create configmap config
kubectl create configmap data
  1. 环境分离
yaml 复制代码
# 开发环境
apiVersion: v1
kind: ConfigMap
metadata:
  name: app-config
  namespace: development
data:
  database.host: "dev-mysql.internal"
  log.level: "debug"

---
# 生产环境
apiVersion: v1
kind: ConfigMap
metadata:
  name: app-config
  namespace: production
data:
  database.host: "prod-mysql.internal"
  log.level: "warn"

使用 namespace 来区分开发和生产环境是 Kubernetes 中常见和推荐的做法。这是最常见的方式,适用于同一个集群内的环境分离:主要用于小型团队。

缺点:

安全风险:生产和开发环境在同一个集群,存在潜在的安全风险

资源竞争:可能存在资源争用的情况

故障影响:集群级别的故障会影响所有环境

更严格的环境分离方式,每个环境使用独立的集群。主要用于中大型团队,并且对安全和隔离性要求比较高场景。

实际生产中,很多公司采用混合策略:

bash 复制代码
# 集群规划示例
# dev-cluster: 开发和测试环境
#   - namespace: development
#   - namespace: testing
#   - namespace: integration

# prod-cluster: 预生产和生产环境
#   - namespace: staging
#   - namespace: production

注意事项和限制

  1. 大小限制
    ConfigMap 的总大小不能超过 1MB
    单个键的值不能超过 1MB
  2. 安全考虑
    ConfigMap 中的数据是明文存储的
  3. ConfigMap 更新不会自动触发 Pod 重启,需要手动重启

参考

推荐:【k8s教程】薪享宏福Kubernetes v1.29 |2024最新版!B站最强!百万播放汪洋授课,轻松拿捏k8s

参考URL: https://www.bilibili.com/video/BV1PbeueyE8V

相关推荐
乌托邦的逃亡者6 小时前
Docker的/var/lib/docker/目录占用100%的处理方法
运维·docker·容器
OKUNP10 小时前
Docker高级管理--容器通信技术与数据持久化
docker·容器·php
洁辉11 小时前
Spring Cloud 全栈指南:构建云原生微服务的终极武器
spring cloud·微服务·云原生
阿里云云原生13 小时前
加工进化论:SPL 一键加速日志转指标
云原生
阿里云云原生14 小时前
破解异构日志清洗五大难题,全面提升运维数据可观测性
云原生
果子⌂19 小时前
Docker-构建镜像并实现LNMP架构
mysql·nginx·docker·容器·架构·php
无敌糖果19 小时前
K8S数据流核心底层逻辑剖析
docker·容器·kubernetes·k8s架构·底层逻辑·k8s数据流
阿里云云原生20 小时前
从 Python 演进探寻 AI 与云对编程语言的推动
云原生
亲爱的非洲野猪20 小时前
关于k8s Kubernetes的10个面试题
云原生·容器·kubernetes