Лучшие практики безопасного управления учетными данными Jenkins
Безопасно храните секреты Jenkins с помощью Credentials Plugin, области видимости папок, withCredentials, RBAC, ротации и внешних хранилищ.
Лучшие практики безопасного управления учетными данными Jenkins
Заданиям Jenkins часто требуются секреты, близкие к производственным: облачные токены, пароли реестров, ключи развертывания, сертификаты подписи и учетные данные API. Если эти секреты окажутся в Jenkinsfile, консольном журнале или параметре задания, ваша система CI/CD станет прямым путем к компрометации.
Используйте Credentials Plugin, ограничивайте область видимости учетных данных и внедряйте их только для того шага, который в них нуждается.
Основа: Jenkins Credentials Plugin
Credentials Plugin — это стандартный механизм, который Jenkins использует для хранения конфиденциальных данных. Он предоставляет централизованное зашифрованное хранилище для учетных данных, гарантируя, что секреты никогда не будут раскрыты в журналах сборки, системе контроля версий или файлах конфигурации.
Когда Jenkins сохраняет учетные данные, он шифрует их, используя ключевой материал на контроллере Jenkins, включая файлы в JENKINS_HOME/secrets. Любой, имеющий широкий доступ к файловой системе контроллера и конфигурации Jenkins, потенциально может восстановить секреты, поэтому доступ к файловой системе и администраторам должен быть строго ограничен.
Ключевые типы учетных данных
Понимание доступных типов учетных данных — первый шаг к безопасной реализации. Выбирайте тип, который наиболее точно соответствует хранимому секрету:
- Secret Text (Секретный текст): Используется для общих коротких текстовых значений, таких как токены API, ключи доступа, OAuth-токены или секреты вебхуков.
- Username and Password (Имя пользователя и пароль): Стандартная пара для аутентификации в таких сервисах, как репозитории Maven, частные реестры (Docker Hub, Artifactory) или внутренние приложения.
- SSH Username with Private Key (SSH-имя пользователя с закрытым ключом): Необходим для доступа к удаленным агентам, клонирования частных Git-репозиториев или выполнения команд на удаленной инфраструктуре. Закрытый ключ можно ввести напрямую, указать путь или управлять им через контроллер Jenkins.
- Secret File (Секретный файл): Используется для загрузки целых файлов, которые являются конфиденциальными, таких как хранилища ключей, сертификаты (
.pem,.crt) или файлы конфигурации, содержащие секреты.
Совет: Всегда используйте максимально детализированный тип учетных данных. Например, если вам нужен только ключ API, используйте Secret Text, а не пытайтесь вписать его в поля имени пользователя и пароля.
Принцип наименьших привилегий: Область видимости учетных данных
Область видимости учетных данных определяет, где они доступны в среде Jenkins. Применение принципа наименьших привилегий — предоставление только того доступа, который необходим для работы, — имеет решающее значение.
1. Системная область видимости (System Scope)
Учетные данные с системной областью видимости (хранятся в Manage Jenkins > Manage Credentials > Jenkins) доступны глобально для всех заданий, папок и конвейеров в экземпляре Jenkins.
- Использование: Используйте системную область видимости только для секретов, необходимых для всей работы Jenkins, таких как учетные данные, используемые плагинами глобальной конфигурации, или секреты, необходимые для всех подключений агентов.
- Предупреждение: Сведите к минимуму использование системной области видимости. Любое скомпрометированное задание потенциально может получить доступ ко всем глобально доступным секретам.
2. Область видимости папки (Folder Scope)
Учетные данные с областью видимости папки определяются в конкретной папке (созданной с помощью плагина Folder или через папки организации). Эти секреты видны и могут использоваться только заданиями, находящимися в этой папке и ее подпапках.
- Рекомендация: Всегда предпочитайте область видимости папки. Это разделяет доступ и ограничивает радиус поражения в случае компрометации одного проекта.
Безопасное внедрение в декларативные конвейеры
Не жестко кодируйте учетные данные в скриптах конвейера. Переменные окружения приемлемы только тогда, когда Jenkins внедряет их для узкого блока и маскирует известные секретные значения в журналах.
Безопасный метод доступа к учетным данным в декларативном конвейере — использование встроенного шага withCredentials. Этот шаг загружает указанные учетные данные в переменную окружения с ограниченной областью видимости, которая доступна только во время выполнения блока.
Пример 1: Внедрение секретного текста (токен API)
Этот пример безопасно извлекает учетные данные Secret Text (MY_API_TOKEN) и присваивает их значение внутренней переменной SECRET_TOKEN. После завершения блока withCredentials переменная SECRET_TOKEN автоматически удаляется из окружения.
pipeline {
agent any
stages {
stage('Deploy via API') {
steps {
script {
withCredentials([string(credentialsId: 'MY_API_TOKEN', variable: 'SECRET_TOKEN')]) {
sh "echo 'Calling external API...'"
sh '''
curl -X POST \
-H "Authorization: Bearer $SECRET_TOKEN" \
https://api.mycorp.com/deploy
'''
}
}
}
}
}
}
Пример 2: Внедрение имени пользователя и пароля
При использовании учетных данных Username and Password шаг withCredentials разделяет секрет на две переменные: одну для имени пользователя и одну для пароля, обычно с суффиксами _USR и _PSW (или пользовательскими именами).
pipeline {
agent any
stages {
stage('Login to Registry') {
steps {
withCredentials([usernamePassword(credentialsId: 'DOCKER_REGISTRY_CRED', usernameVariable: 'DOCKER_USER', passwordVariable: 'DOCKER_PASS')]) {
sh '''
printf '%s' "$DOCKER_PASS" | docker login \
--username "$DOCKER_USER" \
--password-stdin my.registry.com
'''
}
}
}
}
}
Предупреждение безопасности: Подавление журнала
Jenkins пытается маскировать известные значения учетных данных в журналах сборки, но маскировка не заменяет тщательно написанные скрипты. Не выводите секреты на печать, не передавайте пароли в командной строке и не запускайте трассировку оболочки (
set -x) при использовании секретов.
Расширенная интеграция безопасности
Для сред с высокими требованиями к безопасности полагаться только на локальный мастер-ключ Jenkins часто недостаточно. Интеграция с внешней системой управления секретами обеспечивает разделение ответственности, централизованный аудит и расширенные возможности шифрования.
Внешние хранилища учетных данных
Популярные интеграции включают:
- HashiCorp Vault: Используя плагин Vault, Jenkins может динамически запрашивать секреты из Vault во время выполнения. Это означает, что секреты никогда не хранятся постоянно на контроллере Jenkins, а только временно в памяти во время фазы выполнения.
- AWS Secrets Manager/Azure Key Vault: Облачные плагины позволяют конвейерам извлекать секреты непосредственно из этих сервисов, используя IAM-роли или субъекты-службы, что сводит к минимуму статическое раскрытие учетных данных.
Использование внешних хранилищ соответствует лучшим практикам безопасности за счет:
- Разделения хранения: Инфраструктура секретов отделена от сервера CI/CD.
- Динамического доступа: Секреты можно часто ротировать без необходимости ручного обновления конфигурации Jenkins.
- Расширенного аудита: Все попытки доступа к секретам регистрируются во внешней системе хранилища.
Управление доступом на основе ролей (RBAC)
Внедрение плагина RBAC (например, Role-based Authorization Strategy) позволяет администраторам контролировать не только то, кто может запускать задание, но и кто может настраивать и просматривать определенные учетные данные.
- Ограничьте права на настройку заданий, чтобы только доверенные пользователи могли привязывать учетные данные в конвейерах.
- Ограничьте возможность изменения или создания учетных данных системного уровня небольшой группой администраторов безопасности или платформы.
Лучшие практики управления учетными данными
| Практика | Описание | Преимущество для безопасности |
|---|---|---|
| Используйте область видимости папки | Ограничьте доступ к учетным данным конкретными заданиями/папками, которым они нужны. | Ограничивает раскрытие и радиус поражения. |
| Избегайте жесткого кодирования | Никогда не помещайте секреты в Jenkinsfile, скрипты сборки или систему контроля версий. |
Устраняет уязвимость исходного кода. |
Используйте withCredentials |
Безопасно внедряйте секреты в шаги конвейера с помощью официального API Jenkins. | Обеспечивает автоматическое удаление из журналов и очистку окружения. |
| Интегрируйте внешнее хранилище | Используйте Vault, AWS Secrets Manager или Azure Key Vault для корпоративных развертываний. | Разделяет хранение и обеспечивает динамическую ротацию. |
| Применяйте RBAC | Используйте плагины авторизации, чтобы ограничить круг лиц, которые могут настраивать, просматривать и использовать учетные данные. | Обеспечивает соблюдение принципа наименьших привилегий среди пользователей. |
| Регулярная ротация | Регулярно меняйте ключи API и пароли (в идеале автоматически через внешнее хранилище). | Минимизирует временное окно для использования скомпрометированных секретов. |
| Защита контроллера | Обеспечьте строгие права доступа к файловой системе на контроллере Jenkins для защиты master.key. |
Защищает основной механизм шифрования. |
Относитесь к учетным данным Jenkins как к производственным секретам. Ограничивайте их область видимости, связывайте их ненадолго, регулярно меняйте и ограничивайте доступ к контроллеру только теми, кому разрешено восстанавливать эти секреты.