Отделение конфигурации от кода — это базовый принцип DevOps, который повышает безопасность, гибкость и управляемость приложений в Kubernetes. ConfigMap и Secret — два ключевых объекта для реализации этого подхода. Они позволяют выносить настройки и чувствительные данные из Docker-образов, делая развертывания универсальными для разных сред: development, staging, production.
Что вы получите из этого руководства:
- Готовые YAML-манифесты для создания ConfigMap и Secret, которые можно сразу использовать в своих проектах.
- Пошаговую настройку шифрования секретов в etcd (Encryption at Rest) для production-кластеров.
- Практический кейс развертывания приложения с нуля, где конфигурация и секреты полностью отделены от кода.
Зачем отделять конфигурацию от кода: основы DevOps в Kubernetes
Конфигурация, «зашитая» в код приложения, создает несколько критических проблем. Для переключения между средами (dev/stage/prod) требуется пересборка Docker-образа. Чувствительные данные, такие как пароли от базы данных, могут попасть в систему контроля версий, что приводит к утечкам. Изменение любого параметра, даже порта приложения, требует полного цикла CI/CD.
Kubernetes решает эти проблемы через объекты ConfigMap и Secret. ConfigMap хранит конфигурационные данные в формате «ключ-значение» или целыми файлами. Secret предназначен для чувствительной информации, хранящейся в закодированном виде. Оба объекта существуют независимо от Pod'ов и Deployment'ов. Вы можете обновлять их без перезапуска приложений, а также использовать одни и те же настройки для множества подов.
В 2026 году этот подход стал стандартом для production-сред. Он обеспечивает согласованность окружений, упрощает соблюдение требований безопасности и ускоряет процессы развертывания.
Создание и управление ConfigMap: хранение обычных настроек
ConfigMap — основной инструмент для хранения неконфиденциальных данных: уровней логирования, URL сервисов, конфигурационных файлов приложений.
Быстрый старт: создание ConfigMap через kubectl
Для быстрого тестирования или работы в командной строке используйте kubectl create configmap.
# Создание из литералов (key=value)
kubectl create configmap app-config --from-literal=LOG_LEVEL=INFO --from-literal=API_ENDPOINT=http://api.service
# Создание из файла конфигурации
kubectl create configmap nginx-config --from-file=./nginx.conf
# Просмотр созданного объекта
kubectl get configmap app-config -o yaml
Вывод команды покажет YAML с данными в поле data. Этот метод удобен для ad-hoc задач, но для production рекомендуется декларативный подход через YAML-файлы.
Правильный подход: декларативный YAML-манифест ConfigMap
Хранение манифестов в Git обеспечивает версионирование, контроль изменений и воспроизводимость развертываний. Вот структура ConfigMap в YAML:
apiVersion: v1
kind: ConfigMap
metadata:
name: app-config
namespace: default
data:
# Простые ключ-значение
LOG_LEVEL: "DEBUG"
CACHE_TTL: "300"
# Многострочный конфигурационный файл
application.properties: |
server.port=8080
spring.datasource.url=jdbc:postgresql://localhost:5432/mydb
logging.level.root=INFO
Примените манифест командой kubectl apply -f configmap.yaml. Для обновления конфигурации измените файл и выполните команду apply снова — Kubernetes обновит объект. Приложения, использующие этот ConfigMap, получат новые значения, хотя механизм обновления зависит от способа подключения.
Безопасная работа с чувствительными данными: Kubernetes Secret
Secret — это объект Kubernetes для хранения конфиденциальных данных: паролей, OAuth-токенов, SSH-ключей, TLS-сертификатов. Данные в Secret хранятся в кодировке base64, что обеспечивает лишь базовое сокрытие от случайного просмотра, но не является шифрованием.
Создание Secret: от базовых команд до best practices
Создать Secret можно через kubectl или YAML. Для безопасности никогда не коммитите сырые секреты в Git.
# Создание через kubectl (данные кодируются автоматически)
kubectl create secret generic db-credentials --from-literal=username=admin --from-literal=password='S3cr3tP@ss!'
# Просмотр (пароль будет показан в base64)
kubectl get secret db-credentials -o yaml
Для работы с YAML данные нужно предварительно закодировать в base64:
echo -n 'S3cr3tP@ss!' | base64
# UzNjcjN0UEBzcyE=
Используйте полученное значение в манифесте:
apiVersion: v1
kind: Secret
metadata:
name: db-credentials
type: Opaque
data:
username: YWRtaW4=
password: UzNjcjN0UEBzcyE=
Более удобная альтернатива — поле stringData. Оно позволяет записывать данные в чистом виде, и Kubernetes сам выполнит кодировку при создании объекта. Это безопаснее, так как чистый текст не попадает в итоговый YAML, который может быть сохранен в логах.
apiVersion: v1
kind: Secret
metadata:
name: db-credentials
type: Opaque
stringData:
username: admin
password: S3cr3tP@ss!
Регулярно меняйте секреты (ротация). Автоматизируйте этот процесс с помощью инструментов вроде External Secrets Operator или настроек вашего CI/CD.
Безопасность Secret: что важно знать в 2026 году
По умолчанию данные в etcd, где хранятся Secrets, не зашифрованы. Любой, кто имеет доступ к etcd или права администратора кластера, может их прочитать. Для production-сред это неприемлемо.
Современные best practices включают три уровня защиты:
- Шифрование на rest (Encryption at Rest). Настройте провайдер шифрования для etcd через API-ресурс
EncryptionConfiguration. Это гарантирует, что секреты на диске хранятся в зашифрованном виде. - Строгий RBAC (Role-Based Access Control). Минимизируйте права. Давайте Pod'ам доступ к секретам только через ServiceAccount с минимально необходимыми ролями. Ограничьте доступ администраторов.
- Внешние секрет-менеджеры. Для высоких требований безопасности используйте специализированные системы: HashiCorp Vault, AWS Secrets Manager, Azure Key Vault. Интегрируйте их с Kubernetes через CSI-провайдер (например, Secrets Store CSI Driver) или сторонние операторы. Это позволяет централизовать управление, аудит и ротацию секретов для всего предприятия.
Подробнее о комплексном подходе к безопасности в конвейерах развертывания читайте в нашем руководстве по DevSecOps в 2026 году.
Подключение конфигурации к Pod: переменные окружения и монтирование томов
Созданные ConfigMap и Secret бесполезны, пока не подключены к контейнерам. Kubernetes предлагает три основных способа.
Использование переменных окружения (env и envFrom)
Самый простой способ — инжектировать значения как переменные окружения. Используйте env для отдельных значений и envFrom для массового импорта.
# В манифесте Pod или Deployment
spec:
containers:
- name: app
image: myapp:latest
env:
# Одиночная переменная из ConfigMap
- name: LOG_LEVEL
valueFrom:
configMapKeyRef:
name: app-config
key: LOG_LEVEL
# Секрет как переменная окружения
- name: DB_PASSWORD
valueFrom:
secretKeyRef:
name: db-credentials
key: password
# Импорт всех ключей из ConfigMap как переменных
envFrom:
- configMapRef:
name: app-config
Метод env подходит для простых строковых настроек и секретов, которые приложение ожидает получить в переменных окружения.
Монтирование конфигурационных файлов через Volume
Если приложение читает конфигурацию из файла (например, Nginx, Postgres, системные демоны), используйте монтирование томов.
spec:
containers:
- name: nginx
image: nginx:alpine
volumeMounts:
- name: config-volume
mountPath: /etc/nginx/nginx.conf
subPath: nginx.conf
readOnly: true
volumes:
- name: config-volume
configMap:
name: nginx-config
items:
- key: nginx.conf
path: nginx.conf
Ключевая особенность: при изменении ConfigMap Kubernetes автоматически обновляет файлы в смонтированном томе. Задержка составляет от нескольких секунд до минуты (контролируется Kubelet). Secret монтируются аналогично.
Когда использовать env, а когда volumeMount?
Выбор метода зависит от требований приложения:
- env/envFrom: для настроек уровня приложения (логи, флаги функциональности, адреса служб), простых секретов.
- volumeMount: для конфигурационных файлов со сложным синтаксисом, бинарных данных (сертификаты), когда приложение требует именно файл.
Для глубокого погружения в настройку рабочих нагрузок изучите наше полное руководство по Kubernetes Secrets, где разобраны тонкости работы с TLS-сертификатами и интеграцией с Ingress.
Практический кейс: от манифеста до работающего приложения
Соберем все знания воедино и развернем простое веб-приложение с централизованной конфигурацией.
Шаг за шагом: развертывание с централизованной конфигурацией
1. ConfigMap (configmap.yaml): Храним настройки приложения и конфигурационный файл.
apiVersion: v1
kind: ConfigMap
metadata:
name: webapp-config
data:
APP_COLOR: "blue"
appsettings.json: |
{
"Features": {
"CacheEnabled": true
}
}
2. Secret (secret.yaml): Храним пароль от базы данных. Используем stringData.
apiVersion: v1
kind: Secret
metadata:
name: webapp-secret
type: Opaque
stringData:
db_password: "MyDbP@ss2026"
3. Deployment (deployment.yaml): Подключаем конфигурацию разными способами.
apiVersion: apps/v1
kind: Deployment
metadata:
name: webapp-deployment
spec:
replicas: 2
selector:
matchLabels:
app: webapp
template:
metadata:
labels:
app: webapp
spec:
containers:
- name: webapp
image: nginxdemos/hello:latest
env:
# Переменная из ConfigMap
- name: APP_COLOR
valueFrom:
configMapKeyRef:
name: webapp-config
key: APP_COLOR
# Секрет как переменная
- name: DB_PASSWORD
valueFrom:
secretKeyRef:
name: webapp-secret
key: db_password
volumeMounts:
- name: config-volume
mountPath: /usr/share/nginx/html/config/appsettings.json
subPath: appsettings.json
volumes:
- name: config-volume
configMap:
name: webapp-config
items:
- key: appsettings.json
path: appsettings.json
Примените манифесты:
kubectl apply -f configmap.yaml -f secret.yaml -f deployment.yaml
Проверьте, что конфигурация загрузилась:
# Узнайте имя одного из Pod'ов
kubectl get pods -l app=webapp
# Проверьте переменные окружения внутри контейнера
kubectl exec -- printenv | grep -E "APP_COLOR|DB_PASSWORD"
# Проверьте наличие смонтированного файла
kubectl exec -- cat /usr/share/nginx/html/config/appsettings.json
Вы увидите, что переменные APP_COLOR=blue и DB_PASSWORD=MyDbP@ss2026 доступны в контейнере, а файл appsettings.json смонтирован по указанному пути.
Задание для самопроверки: Измените значение APP_COLOR в ConfigMap на "green" и повторно выполните kubectl apply -f configmap.yaml. Через некоторое время проверьте переменную окружения в поде снова — она должна обновиться. Это демонстрирует динамическое обновление конфигурации без перезапуска приложения.
Часто задаваемые вопросы (FAQ)
Можно ли обновить ConfigMap без перезапуска Pod?
Да, но механизм зависит от способа подключения. При монтировании через том (volumeMount) Kubernetes автоматически обновляет файлы в поде с задержкой до минуты. Переменные окружения (env), заданные при старте контейнера, не обновляются динамически — для их применения требуется перезапуск Pod.
В чем разница между Secret и ConfigMap с точки зрения безопасности?
Secret хранит данные в base64 и поддерживает шифрование в etcd, но сам по себе не обеспечивает надежной защиты без дополнительных настроек. ConfigMap хранит данные в открытом виде и не предназначен для паролей или токенов. Для production-сред обязательно настраивайте Encryption at Rest и строгий RBAC.
Как передать в Pod целый конфигурационный файл?
Используйте монтирование тома (volumeMount) с указанием ConfigMap или Secret в качестве источника. В манифесте определите том типа configMap или secret и смонтируйте его в нужный путь внутри контейнера. Это стандартный подход для Nginx, баз данных и других приложений, читающих конфигурацию из файлов.
Итоги и рекомендации: ваша шпаргалка по ConfigMap и Secret
ConfigMap и Secret — фундамент управляемой конфигурации в Kubernetes. Вот краткая памятка по их использованию.
| Критерий | ConfigMap | Secret |
|---|---|---|
| Назначение | Обычные настройки (логи, URL, флаги) | Чувствительные данные (пароли, токены, ключи) |
| Хранение данных | Plain text или файлы | Закодировано в base64 (не шифрование!) |
| Безопасность по умолчанию | Низкая (данные открыты) | Базовая (кодирование) |
Правила выбора способа подключения:
- Используйте
envилиenvFromдля простых строковых параметров, которые приложение читает из окружения. - Используйте
volumeMountдля конфигурационных файлов, бинарных данных (сертификаты) или когда формат данных требует именно файл.
Топ-3 best practices на 2026 год:
- Всегда используйте YAML-манифесты для production. Храните их в Git. Команды
kubectl createоставьте для тестирования и отладки. - Не полагайтесь только на base64 в Secrets. Для production кластера обязательно настройте Encryption at Rest для etcd и строгий RBAC. Для высоких стандартов безопасности внедрите внешний секрет-менеджер, такой как HashiCorp Vault.
- Следите за актуальностью стека. Регулярно обновляйте знания и инструменты. Например, для автоматизации инфраструктуры и управления конфигурацией в масштабе ознакомьтесь с обязанностями современного DevOps-инженера в 2026 году.
Начните с рефакторинга одного из ваших Deployment'ов: вынесите хотя бы одну настройку в ConfigMap и один секрет в Secret. Это первый шаг к созданию гибкой, безопасной и легко управляемой инфраструктуры.
Для автоматизации работы с множеством API и моделей ИИ, что часто требует управления ключами и конфигурацией, может пригодиться сервис AiTunnel. Он агрегирует доступ к более чем 200 нейросетям через единый API с оплатой в рублях и управлением бюджетами, что упрощает интеграцию ИИ в ваши приложения.