emmetog.jenkins
Jenkins 的 Ansible 角色
使用 Ansible 安装并完全配置 Jenkins。
当你希望将所有的 Jenkins 配置放在版本控制中,以便可以可靠地重复部署 Jenkins,并且将 Jenkins 视为牛而不是宠物时,可以使用这个角色。
如果你只是想安装 Jenkins,并通过网页界面配置一切,而不在乎是否可以重复部署这个完全配置的 Jenkins,那么你不需要这个角色。相反,可以看看geerlingguy/ansible-role-jenkins角色。
要求
如果使用 Docker 部署,则需要在服务器上安装 Docker。目前支持的仅有 Docker、apt-get 和 yum,尽管可以轻松添加更多方法,欢迎提交 PR。
安装
通过 Ansible Galaxy 安装:
$ ansible-galaxy install emmetog.jenkins
角色变量
以下变量影响 Jenkins 的安装方式:
jenkins_install_via
:控制 Jenkins 的安装方式。 重要:此变量必须被定义为以下值之一:docker
:在 Docker 容器中安装apt
:在 Ubuntu/Debian Linux 系统上直接安装 Jenkinsyum
:在 RedHat/CentOS Linux 系统上直接安装 Jenkins
jenkins_version
:要安装的 Jenkins 的确切版本
以下变量影响 Jenkins 的配置方式:
jenkins_url
:Jenkins 可访问的 URLjenkins_port
:Jenkins 监听的端口jenkins_home
:服务器上 Jenkins 配置文件的目录jenkins_admin
:Jenkins 服务器管理员的电子邮件地址jenkins_java_opts
:传递给 Java 可执行文件的选项jenkins_config_owner
:Jenkins 配置文件的所有者jenkins_config_group
:Jenkins 配置文件的组jenkins_auth
:Ansible 应如何进行 Jenkins 认证(参见下面的“认证和安全”部分)jenkins_url_health_check
:Jenkins 启动后用于健康检查的 URL(默认为jenkins_url
)jenkins_health_check_user
:如果定义,将使用基本认证(见 API 令牌部分)进行健康检查,使用此用户名(如果您设置了比如 Google OAuth,则很有用)jenkins_health_check_password
:如果定义,将使用基本认证(见 API 令牌部分)进行健康检查,使用此密码(如果您设置了比如 Google OAuth,则很有用)
以下列表变量影响将在 Jenkins 中安装的作业/插件:
jenkins_jobs
:要复制到 Jenkins 的作业名称列表。config.xml
文件必须存在于jenkins_source_dir_jobs/<job_name>
下jenkins_plugins
:要安装到 Jenkins 的插件 ID 列表jenkins_custom_plugins
:要安装到 Jenkins 的自定义插件列表
有关变量的完整列表,请参见 defaults/main.yml
。
示例剧本
- hosts: jenkins
vars:
jenkins_version: "2.73.1"
jenkins_hostname: "jenkins.example.com"
jenkins_port: 8080
jenkins_install_via: "docker"
jenkins_jobs:
- "my-first-job"
- "another-awesome-job"
jenkins_include_secrets: true
jenkins_include_custom_files: true
jenkins_custom_files:
- src: "jenkins.plugins.openstack.compute.UserDataConfig.xml"
dest: "jenkins.plugins.openstack.compute.UserDataConfig.xml"
jenkins_plugins:
- git
- blueocean
jenkins_custom_plugins:
- "openstack-cloud-plugin/openstack-cloud.jpi"
roles:
- emmetog.jenkins
管理配置文件
上面的示例将在 {{ playbook_dir }}/jenkins-configs/jobs/my-first-job/config.xml
和 {{ playbook_dir }}/jenkins-configs/jobs/another-awesome-job/config.xml
寻找作业配置文件。
注意:这些目录是可自定义的,请查看 jenkins_source_dir_configs
和 jenkins_source_dir_jobs
角色变量。
该角色还会查找 {{ playbook_dir }}/jenkins-configs/config.xml
。该 config.xml
文件将被复制到服务器,并用作作业配置模板。
上述示例还会上传 {{ playbook_dir }}/jenkins-configs/secrets
下的整个 secrets 目录,并复制在 {{ jenkins_custom_files }}
变量中定义的自定义文件。请注意,{{ jenkins_include_secrets }}
和 {{ jenkins_include_custom_files }}
变量应设置为 true
,以使这些功能正常工作。此外,角色可以通过在 {{ jenkins_custom_plugins }}
列表变量中提供 .jpi 或 .hpi 文件来安装自定义插件。
config.xml
和自定义文件被视为模板,因此可以在其中放置变量,包括来自 Ansible vault 的敏感数据。
当您想要更改配置文件或添加新项目(例如作业、插件等)时,正常的工作流程是:
- 在 Jenkins UI 中进行更改
- 将生成的 XML 文件复制回您的版本控制系统
- 对于新创建的文件,请确保将其添加到相应的列表中:
- 对于新作业,必须将其添加到
jenkins_jobs
- 对于自定义文件,必须将其添加到
jenkins_include_custom_files
- 对于自定义插件,必须将其添加到
jenkins_custom_plugins
示例 Jenkins 配置文件
在 {{ jenkins_source_dir_configs }}/config.xml
中,您可以放置全局 Jenkins 配置,例如:
<?xml version='1.1' encoding='UTF-8'?>
<hudson>
<disabledAdministrativeMonitors/>
<version>2.176.1</version>
<installStateName>RESTART</installStateName>
<numExecutors>1</numExecutors>
<mode>EXCLUSIVE</mode>
<useSecurity>true</useSecurity>
<authorizationStrategy class="hudson.security.AuthorizationStrategy$Unsecured"/>
<securityRealm class="hudson.security.HudsonPrivateSecurityRealm">
<disableSignup>false</disableSignup>
<enableCaptcha>false</enableCaptcha>
</securityRealm>
<disableRememberMe>false</disableRememberMe>
<projectNamingStrategy class="jenkins.model.ProjectNamingStrategy$DefaultProjectNamingStrategy"/>
<workspaceDir>${JENKINS_HOME}/workspace/${ITEM_FULLNAME}</workspaceDir>
<buildsDir>${ITEM_ROOTDIR}/builds</buildsDir>
<markupFormatter class="hudson.markup.EscapedMarkupFormatter"/>
<jdks/>
<viewsTabBar class="hudson.views.DefaultViewsTabBar"/>
<myViewsTabBar class="hudson.views.DefaultMyViewsTabBar"/>
<clouds/>
<quietPeriod>0</quietPeriod>
<scmCheckoutRetryCount>0</scmCheckoutRetryCount>
<views>
<hudson.model.AllView>
<owner class="hudson" reference="../../.."/>
<name>all</name>
<filterExecutors>false</filterExecutors>
<filterQueue>false</filterQueue>
<properties class="hudson.model.View$PropertyList"/>
</hudson.model.AllView>
</views>
<primaryView>all</primaryView>
<slaveAgentPort>0</slaveAgentPort>
<disabledAgentProtocols>
<string>JNLP-connect</string>
<string>JNLP2-connect</string>
</disabledAgentProtocols>
<label>master</label>
<crumbIssuer class="hudson.security.csrf.DefaultCrumbIssuer">
<excludeClientIPFromCrumb>false</excludeClientIPFromCrumb>
</crumbIssuer>
<nodeProperties/>
<globalNodeProperties/>
</hudson>
示例作业配置文件
以下是您可以放在 {{ playbook_dir }}/jenkins-configs/jobs/my-first-job/config.xml
中的示例:
<?xml version='1.0' encoding='UTF-8'?>
<project>
<actions/>
<description>我的第一个作业,它说“你好,世界”</description>
<keepDependencies>false</keepDependencies>
<properties/>
<scm class="hudson.scm.NullSCM"/>
<canRoam>true</canRoam>
<disabled>false</disabled>
<blockBuildWhenDownstreamBuilding>false</blockBuildWhenDownstreamBuilding>
<blockBuildWhenUpstreamBuilding>false</blockBuildWhenUpstreamBuilding>
<triggers/>
<concurrentBuild>false</concurrentBuild>
<builders>
<hudson.tasks.Shell>
<command>echo "Hello World!"</command>
</hudson.tasks.Shell>
</builders>
<publishers/>
<buildWrappers/>
</project>
认证和安全
该角色支持以下 Jenkins 认证机制:
- 基于 API 令牌的认证(推荐,要求至少使用 Jenkins 2.96)
- 使用严格的 Crumb 发行者插件的 Crumb 认证(如果*不*使用 API 令牌并且 Jenkins 版本 >= 2.176.2,则需要)
- 无安全性(不推荐)
基于 API 令牌的认证
推荐使用基于 API 令牌的认证,但需要额外的配置工作。API 令牌的优点在于可以在 Jenkins 中轻松撤销,并且其使用情况也会被跟踪。API 令牌也不需要获取 Crumb 令牌,自从 Jenkins 版本 2.172.2 以来这变得更加困难(请参见此安全公告)。
要创建 API 令牌,您需要执行以下步骤:
- 所有 API 令牌必须属于特定用户。因此,可以为部署创建一个特殊用户,或者以管理员或其他帐户身份登录。
- 在用户配置页面,点击“添加新令牌”按钮。
- 保存令牌值,最好放在 Ansible vault 中。
- 在剧本中定义以下变量:
jenkins_auth: "api"
jenkins_api_token: "(在 Ansible vault 中定义)"
jenkins_api_username: "(在 Ansible vault 中定义)"
- 备份文件
$JENKINS_HOME/users/the_username/config.xml
,其中the_username
对应拥有您刚创建的 API 令牌的用户。 - 将此文件添加到控制主机,并确保在
jenkins_custom_files
列表中部署到 Jenkins,如下所示:
jenkins_custom_files:
- src: "users/the_username/config.xml"
dest: "users/the_username/config.xml"
请注意,您可能需要根据相对于剧本在控制机上保存文件的位置更改 src
值。
基于 Crumb 的认证
基于 Crumb 的认证可用于防止跨站请求伪造攻击,推荐在 API 令牌不切实际时使用。 注意:基于 Crumb 的认证仅适用于“任何人都可以做任何事情”的访问控制设置。如果您的 Jenkins 配置需要更严格的安全设置,则应使用 API 令牌(如上文所述)。
基于 Crumb 的认证的配置可能有点棘手,因为 Jenkins 最近的安全修复。要配置 CSRF,您需要执行以下步骤:
- 如果您使用的是 Jenkins >= 2.176.2,您需要安装严格的 Crumb 发行者插件。可以通过将
strict-crumb-issuer
ID 添加到jenkins_plugins
列表来通过此角色完成。 - 在 Jenkins 中,点击“管理 Jenkins” -> “配置全局安全”
- 在“CSRF 保护”部分,启用“防止跨站请求伪造攻击”,然后选择“严格的 Crumb 发行者”(如果使用 Jenkins >= 2.176.2),否则选择“默认 Crumb 发行者”。请注意,要查看此选项,您需要安装严格的 Crumb 发行者插件。之后,您还需要将主 Jenkins
config.xml
文件备份到控制主机。
同样,以上操作需要至少使用 Ansible 2.9.0pre5 或 2.10(在写作时,这是两个开发中的版本。有关更多详细信息,请参阅此 Ansible 问题)。
HTTPS
如果您想在 Jenkins 上启用 HTTPS,可以按如下方式进行:
- 定义
jenkins_port_https
为 Jenkins 应该监听的端口 - 为 JKS 密钥库或 CA 签名证书定义变量:
- 对于 JKS 密钥库,您需要定义:
jenkins_https_keystore
:控制主机上密钥库文件的路径,该文件将由此角色复制到 Jenkins 服务器。jenkins_https_keystore_password
:所述 JKS 密钥库的密码。建议使用 Ansible vault。 重要:此字符串将被明文写入 Jenkins 服务器上的配置文件中。在服务器的进程列表中也将可见。建议将您的证书迁移到签名证书文件(如下所示)。
- 对于 CA 签名证书文件,您需要定义:
jenkins_https_certificate
:证书文件的路径,该文件将由此角色复制到 Jenkins 服务器。建议对该文件使用 Ansible vault。jenkins_https_private_key
:所述 CA 签名证书的私钥。建议对该文件使用 Ansible vault。
- 对于 JKS 密钥库,您需要定义:
- 如果您使用的是自签名证书,可以选择将
jenkins_https_validate_certs
定义为false
。
如果您使用 Docker 部署 Jenkins,建议使用反向代理,如jwilder/nginx-proxy或traefik,而不是配置 Jenkins 本身。这提供了更多灵活性,并允许责任分离。有关如何部署代理和配置 HTTPS 的更多细节,请参阅这些项目的文档。
如果在 Jenkins 实例前面使用反向代理并使用 Docker 部署,则您可能希望将 jenkins_docker_expose_port
变量设置为 false,以便该端口不会在主机上暴露,仅对反向代理可用。
许可证
MIT
作者信息
由 Emmet O'Grady 制作。
我是 NimbleCI 的创始人,它为 GitHub 中的功能分支工作流项目构建 Docker 容器。
我在我的个人博客上写作,并在NimbleCI 博客上撰写有关 Docker 相关的内容。