将 HCP Packer 与 Red Hat Ansible Automation Platform 集成
作者: Glenn Chia、Pranit Raje 和 Simon Lynch
概述
此验证模式的目标是帮助您部署一个全面的不可变镜像构建管道,该管道结合了 HashiCorp Packer 用于镜像创建的强大功能和 Ansible 用于配置管理的功能。这种集成方法使组织能够
- 构建一致的、不可变的机器镜像,跨多个云提供商和本地环境
- 利用强大的 Ansible 自动化进行复杂的配置管理和应用程序部署
- 实施安全的身份验证工作流,使用 HashiCorp Vault 进行 SSH 密钥管理和密钥处理
- 自动化镜像构建流程,通过 GitHub Actions 进行持续集成和部署
- 维护合规性和治理,通过集中策略执行和审计跟踪
- 减少配置漂移,通过部署预配置的、经过测试的镜像,而不是在运行时配置基础设施
此验证模式通过无缝结合的集成架构解决了这些目标
- HashiCorp Packer 用于跨平台镜像构建和模板管理
- Red Hat Ansible 用于配置管理和 playbook 执行(支持开源和企业部署)
- HashiCorp Vault 用于集中密钥管理和动态 SSH 身份验证
- GitHub Actions 用于自动化 CI/CD 工作流和管道编排
- 多云部署模式,可适应 AWS、Azure、GCP 和本地环境
目标受众
本指南参考了以下角色
- 平台团队:管理您组织的平台。这是一个涵盖所有方面的角色,可能包括管理云服务提供商、CI/CD 管道、HashiCorp Vault 管理员、HCP Packer 的职责。
- 对于本指南,平台团队还负责管理和配置 Vault 和 Red Hat Ansible Automation Platform 以及 HCP Terraform 作为平台。
- 负责黄金镜像管道、镜像管理管道,通常使用 HashiCorp Packer。
- 请注意,在某些组织中,可能有不同的团队处理这些系统中的每一个。这需要在团队之间进行协调,才能使模式在组织中扩展运行。
- 应用程序团队:Ansible Automation Platform 中配置管理的消费者,并快速配置符合组织镜像标准的镜像。
- 安全团队:负责在 Ansible playbook 中定义所需的软件和配置的团队。这些配置符合组织的安全标准,实施强制安全工具安装,并在所有镜像构建中强制执行安全策略。在某些情况下,安全团队也是开发和维护这些 Ansible playbook 的团队。
使用 Ansible Automation Platform 的优势
在与 Packer 集成时,Ansible Automation Platform (AAP) 方法与单独使用基本的 Ansible provisioner 相比具有明显的优势。虽然标准的 Ansible provisioner 对于简单的配置效果很好,但 AAP 提供了企业级的功能,对于具有复杂环境和治理要求的组织至关重要。
AAP 提供集中式凭证管理,该管理超越了基本的 SSH 身份验证,能够与身份提供程序和特权访问管理系统集成到您的整个自动化环境中。此外,AAP 提供了全面的审计跟踪、审批工作流程和基于角色的访问控制,从而增强了组织的合规性。特别是对于不可变基础设施,AAP 通过集中式内容存储库、认证的 collections 和经过验证的角色,确保所有镜像的一致安全基线和配置,从而保证组织标准。
即使 AAP 在部署后可能不会与这些实例交互(遵循不可变性原则),但在镜像构建过程中使用 AAP 可以确保您将一致的安全姿态、合规性要求和组织标准实施到每个镜像中,然后再进行部署。
这种集中的治理方法提供了显著的好处,可以证明额外的集成复杂性是合理的,特别是对于需要维护镜像构建管道中一致控制和可见性的企业而言。对于已经使用 Ansible Automation Platform 的组织,此集成允许您使用现有的自动化资产,而不是在独立的 Packer 模板中复制它们。这些资产可以包括经过广泛测试的 playbook、角色和工作流程,这些都体现了组织的标准和安全实践。
先决条件
要遵循本指南,您需要以下先决条件
- 平台团队
- 具有创建 auth mounts、配置 auth roles 和创建策略权限的 Vault Enterprise 或 HCP Vault Dedicated 集群的特权访问权限。
- 配置和管理凭证和作业模板的 Ansible Automation Platform (AAP) 的特权访问权限。
- 对黄金镜像管道流程的特权访问权限,能够配置和管理镜像中的公钥身份验证和 sshd 配置。
- 创建 HCP 项目、服务主体、Packer bucket 和 channel 的 HCP Packer 的特权访问权限。
- 能够使用选定的 VCS 创建 CI/CD 管道并管理 CI/CD 密钥。
- Packer 构建主机到 AAP 的最小权限访问权限,具体如下:
- 如果使用自注册方法:API 权限仅限于特定 inventory 中的主机注册以及启动预定义作业模板的能力。
- 如果使用工作流程调用方法:API 权限仅限于使用参数启动特定工作流程以及监控作业执行状态的能力。
- 应用程序团队
- 权限使用 Red Hat Ansible Automation Platform 中预创建的凭证来使用 Ansible 作业/工作流程模板。
- 访问 HCP Packer 资源,例如 Registry、Channels 和 Buckets,以便使用 Terraform 访问构建的镜像。
限制
Packer 的 Ansible provisioner 缺乏与 Ansible Automation Platform (AAP) 的直接集成。当前的集成要求运行 Packer 的主机执行以下命令:
- 将新构建的机器注册到 AAP inventory 中
- 触发针对该 inventory 的工作流程或作业模板
- 监控作业执行完成情况
这种间接方法引入了额外的复杂性,因为它需要与 AAP 进行 API 交互,而不是利用原生集成。构建过程必须包括身份验证处理、inventory 管理和作业执行监控逻辑,从而产生对 AAP 可用性和构建过程期间网络访问的依赖性。
背景和最佳实践
在 GitHub Actions 管道中实施 HashiCorp Packer 和 Ansible 集成之前,了解确保部署的基础设施安全、可扩展性、不可变性和可维护性的基本原则和最佳实践至关重要。
多租户和 RBAC 策略
在开始将 HashiCorp Vault 签名的 SSH 凭证集成到 Packer 的 Ansible 中之前,定义清晰的多租户和基于角色的访问控制 (RBAC) 策略至关重要。需要在 Ansible 部署中的租户与 HashiCorp Vault 中的租户之间建立清晰的映射。这可确保运营安全、可扩展性并与组织结构保持一致。
多租户的关键考虑因素
- 组织对齐:将 Ansible 租户映射到业务部门、团队或环境边界
- Vault 命名空间策略:使用 Vault 命名空间或基于路径的分离来隔离租户的密钥和策略。定义 Ansible Automation Platform 组织、团队、角色和 Vault 命名空间之间的战略映射,并将 RBAC 和可扩展性作为关键考虑因素。我们建议为每个业务线 (LoB) 或环境创建一个专用的 Vault 命名空间,该命名空间将与 Ansible Automation Platform (AAP) 中专门用于该业务线 (LoB) 或环境的组织、团队逻辑映射。
- 凭证隔离:适当限定 SSH 凭证的范围,以防止跨租户访问
- 审计边界:设计日志记录以实现租户可见性,同时不暴露跨组织数据
HCP Packer 组织和治理
注册表结构
- 为获得最佳功能和血缘跟踪,请为每个组织使用单个 HCP Packer 注册表
- 在 HCP 组织内为平台团队使用创建一个专用的 HCP Packer 项目
存储桶管理
- 为每个应用程序或团队创建单独的存储桶,以隔离镜像元数据
- 使用一致的命名约定:
<bu>-<appname>-images(业务部门 + 应用程序名称) - 平台团队维护存储桶的创建和权限分配
通道生命周期
- 实施至少三个通道:开发、测试和生产
- 确保所有存储桶命名约定一致,以提高操作清晰度
- 平台团队管理通道创建和生命周期策略
安全加固实践
CIS 基准合规性
- 通过专用的 Ansible 角色实施 CIS 配置
- 自动化合规性验证并记录合理的偏差
安全基线实施
- 部署强制安全工具(防病毒软件、端点检测、监控代理)
- 配置集中式日志记录并强制密码/权限策略
漏洞管理
- 将自动化扫描和补丁管理集成到构建管道中
- 建立补救服务级别协议并维护软件清单以确保合规性
验证的架构
验证的设计实现了一个不可变的镜像构建管道,其中 Packer 协调机器镜像的创建,同时将配置管理任务委派给 Red Hat Ansible Automation Platform。这种关注点分离使组织能够为预期目的利用专用工具
- Packer 处理镜像生命周期管理,包括基本镜像选择、构建编排和工件发布。
- Ansible 管理配置复杂性,执行具有企业功能的复杂剧本,例如凭证管理、作业模板和工作流自动化。
- Vault 提供动态身份验证,为 Packer 到镜像的通信生成临时 SSH 凭证。
- GitHub Actions 编排整个管道,触发构建、管理依赖项和发布工件。
此架构确保正确配置、一致构建的镜像,以便在您的基础设施环境中安全部署。
使用 HCP Packer 的镜像管理

该图说明了 HashiCorp Packer 和 HashiCorp Terraform 在自动化镜像构建和配置中的集成
- 代码管理:将 Packer 代码存储在专用的版本控制系统 (VCS) 存储库中(Packer 存储库)。Packer 代码引用 HCP Packer 注册表以进行元数据存储和跟踪。通过拉取请求 (PR) 流程实施所有更改,以进行代码审查和批准。
- CI/CD 管道执行:CI/CD 管道在合并到主分支时自动触发。管道在指定的云服务提供商上执行 Packer 构建过程。系统会自动将镜像元数据存储在 HCP Packer 注册表中,作为指定 Packer 通道中的新版本。
- 云部署:根据组织的合规性标准进行成功测试和验证后,将黄金镜像提升到 HCP Packer 生产通道。在 Terraform 模板中引用生产就绪的镜像,并在基础设施上部署它们。
使用 Ansible 进行镜像管理

该图表说明了 HashiCorp Packer、Ansible Provisioner 和 HashiCorp Terraform 之间的集成,用于一致、安全和自动地交付不可变基础设施,同时从源代码到生产部署保持完全的可追溯性。
- 源代码控制触发器:开发人员提交对 Packer 模板或 Ansible playbook 的更改,从而触发基于分支(开发、暂存、主)或语义版本标签的 GitHub Actions 工作流
- 安全凭证管理:GitHub Actions 运行程序配置云提供商和 HCP 服务主体身份验证的凭证和环境变量,用于构建过程。
- 镜像构建和配置:Packer 启动临时云实例,执行 Ansible playbook 进行配置管理和安全加固,然后创建不可变机器镜像
- 元数据和注册表管理:与构建的工件关联的元数据会自动推送到 HCP Packer 注册表,其中包含完整的 CI/CD 上下文、来源跟踪和合规性信息。
- 通道提升:系统根据源代码分支或标签(开发 → 开发通道,主 → 发布通道,标签 → 版本化通道)更新 HCP Packer 通道。
- 基础设施部署:下游系统引用 HCP Packer 通道,以在多云环境中部署经过验证的合规镜像,并提供完整的审计跟踪。
在 HashiCorp Packer 运行 Ansible playbook 之前,我们需要确保 Ansible 在 GitHub Actions 运行程序或我们用于 Packer 流水线的 CI/CD 执行环境中正在运行。然后,使用 HashiCorp Packer 和 Ansible provisioner,我们可以调用 Ansible playbook 以对镜像执行任何自定义操作,如下所示:
provisioner "ansible" {
playbook_file = "ansible/playbook.yml"
}
post-processor "manifest" {
output = "packer_manifest.json"
strip_path = true
custom_data = {
version_fingerprint = packer.versionFingerprint
}
}
而示例 playbook 可能如下所示:
---
- name: 'Provision Image'
hosts: default
become: true
tasks:
- name: install Apache
package:
name: 'httpd'
state: present
然后,playbook 运行所有任务以创建黄金镜像,并将关联的元数据发布到 HCP Packer 注册表。
使用 Ansible Automation Platform 进行镜像管理

该图表说明了 HashiCorp Packer、Ansible Automation Platform (AAP) 和 HashiCorp Vault 之间的集成,用于安全、自动化的镜像构建和配置
- 使用 Packer 构建镜像:HashiCorp Packer 使用基本操作系统模板启动镜像构建过程。
- Vault CA 信任配置:使用 Packer 的 ansible provisioner,通过检索和安装 Vault 的公共 SSH CA 密钥并更新 SSH 守护程序配置,配置镜像以信任 HashiCorp Vault 的 SSH 证书颁发机构。
- AAP 注册和作业模板执行:在用 Vault CA 信任构建基本镜像后,Packer 会触发另一个 Ansible playbook。此 playbook 具有以下任务,并且主机需要相应地具有这些任务的权限。
- 将 IP 地址注册为 AAP 中的新主机
- 将主机添加到库存,或选择性地创建新的库存
- 启动针对库存的作业模板
- 由于系统在 Packer 运行后终止主机,因此从库存中注销主机。如果创建了库存,则可以选择删除库存。
协调 Packer 构建的 CI/CD 管道仅报告 AAP 作业是成功还是失败。访问 AAP 用户界面 https://<aap-dns-name>/execution/jobs/playbook/<job-id>/output 以获取详细的执行日志和特定的错误消息。我们建议以编程方式提取作业 ID 并在此工作流中构造此 URL,这简化了诊断镜像构建过程中问题的过程。
Ansible Automation Platform 具体注意事项
如果您将 Ansible Automation Platform 集成到 Packer 流水线中,请遵循以下指南。
使用 HashiCorp Vault 和 AAP 进行动态 SSH 凭证
Ansible Automation Platform 可以与 HashiCorp Vault 集成,以在自动化任务期间动态生成 SSH 凭证以进行安全机器访问。这消除了在 AAP 中存储静态凭证的需求,并通过自动轮换的短寿命凭证提供了增强的安全性。
使用经过认证的 Ansible Controller 集合,您可以自动化 AAP 与 Vault 的 SSH 密钥引擎的配合配置
- Vault 身份验证凭证:使用“HashiCorp Vault 签名 SSH”凭证类型配置 Vault 身份验证,该类型支持多种身份验证方法:Token、TLS、Kubernetes 和 AppRole
- 机器凭证配置:设置 AAP 中的标准机器凭证,Vault 会使用 SSH 密钥动态填充该凭证
- 凭证输入源:使用
ansible.controller.credential_input_source将 Vault 凭证链接到机器凭证,指定身份验证路径和 SSH 角色等参数
此集成通过确保 AAP 作业使用运行时生成的全新临时凭证,而不是存储在 AAP 凭证系统中的长期静态凭证,从而增强了安全性。
Packer 镜像构建流程,用于 AAP 和 Vault 集成
Packer 与 Ansible Automation Platform 和 HashiCorp Vault 集成的构建过程需要两个关键步骤
- 配置 Vault CA 信任:使用 Packer ansible provisioner 配置镜像,以信任 HashiCorp Vault 的证书颁发机构,方法是检索 Vault 的 SSH CA 公钥,将其放置在正确的位置,并配置 SSH 守护程序以信任该 CA 签发的证书。
- AAP 集成:在配置镜像以信任 Vault 的 CA 之后,可以将主机注册到 AAP 资源库并触发作业模板执行,或者调用 AAP 工作流来处理新构建实例的注册和配置。
这种两阶段方法与前面描述的 AAP 凭证配置协同工作。在构建了具有 Vault SSH CA 信任的临时 Packer 虚拟机后,AAP 可以使用其动态凭证生成功能来安全地访问主机虚拟机。AAP 中配置的 Vault SSH 凭证会在运行时从 Vault 请求短期签名的 SSH 证书,目标机器会预先配置为信任这些证书。这确保了系统仅使用从镜像创建到持续管理期间的动态、短期凭证。
有关详细的实施说明,请参阅我们的综合指南:HashiCorp Vault 与 Ansible Automation Platform 的集成。
使用 HashiCorp Packer 和 Ansible provisioner,我们可以调用一个 playbook,执行以下 AAP 操作
provisioner "ansible" {
playbook_file = "../ansible/aap.yml"
extra_arguments = [
"-e", "inventory_name=packer-aap",
"-e", "inventory_description='Packer with AAP inventory'",
"-e", "inventory_organization=Default",
"-e", "host_name=al2023-aap-vault-ssh-ca",
"-e", "host_description='Packer with AAP sample host'",
"-e", "instance_ip=${build.Host}",
"-e", "template_name=example-template",
]
# AAP Credentials
ansible_env_vars = [
"ANSIBLE_REMOTE_TMP=/tmp",
"CONTROLLER_HOST=${var.controller_host}",
"CONTROLLER_USERNAME=${var.controller_username}",
"CONTROLLER_PASSWORD=${var.controller_password}"
]
}
该 playbook 创建资源库,将主机添加到资源库,并启动一个作业模板以根据集中的 AAP playbook 配置主机。系统执行作业模板后,会从资源库中删除主机并删除资源库。此操作不会删除作业模板执行日志,系统会保留这些日志用于审计目的。
---
- name: Configure AAP
hosts: all
become: true
gather_facts: true
vars:
ansible_python_interpreter: /usr/bin/python3
tasks:
- name: Create inventory
ansible.controller.inventory:
name: "{{ inventory_name }}"
description: "{{ inventory_description }}"
organization: "{{ inventory_organization }}"
state: present
controller_host: "{{ lookup('env', 'CONTROLLER_HOST') }}"
controller_username: "{{ lookup('env', 'CONTROLLER_USERNAME') }}"
controller_password: "{{ lookup('env', 'CONTROLLER_PASSWORD') }}"
validate_certs: false
register: inventory_result
- name: Add host to inventory
ansible.controller.host:
name: "{{ host_name }}"
description: "{{ host_description }}"
inventory: "{{ inventory_result.id }}"
variables:
ansible_host: "{{ instance_ip }}"
state: present
controller_host: "{{ lookup('env', 'CONTROLLER_HOST') }}"
controller_username: "{{ lookup('env', 'CONTROLLER_USERNAME') }}"
controller_password: "{{ lookup('env', 'CONTROLLER_PASSWORD') }}"
validate_certs: false
register: host_result
- name: Launch job template with the new inventory
ansible.controller.job_launch:
job_template: "{{ template_name }}"
inventory: "{{ inventory_result.id }}"
# credentials:
# - "{{ credential_name }}"
controller_host: "{{ lookup('env', 'CONTROLLER_HOST') }}"
controller_username: "{{ lookup('env', 'CONTROLLER_USERNAME') }}"
controller_password: "{{ lookup('env', 'CONTROLLER_PASSWORD') }}"
validate_certs: false
wait: true
register: job_launch_result
- name: Display job launch information
debug:
var: job_launch_result
- name: Delete host from inventory
ansible.controller.host:
name: "{{ host_name }}"
inventory: "{{ inventory_result.id }}"
state: absent
controller_host: "{{ lookup('env', 'CONTROLLER_HOST') }}"
controller_username: "{{ lookup('env', 'CONTROLLER_USERNAME') }}"
controller_password: "{{ lookup('env', 'CONTROLLER_PASSWORD') }}"
validate_certs: false
register: host_delete_result
# Always attempt to delete, even if the job failed, to clean up resources
ignore_errors: true
- name: Display host deletion status
debug:
var: host_delete_result
- name: Delete inventory
ansible.controller.inventory:
name: "{{ inventory_result.id }}"
organization: "{{ inventory_organization }}"
state: absent
controller_host: "{{ lookup('env', 'CONTROLLER_HOST') }}"
controller_username: "{{ lookup('env', 'CONTROLLER_USERNAME') }}"
controller_password: "{{ lookup('env', 'CONTROLLER_PASSWORD') }}"
validate_certs: false
register: inventory_delete_result
ignore_errors: true
- name: Display inventory deletion status
debug:
var: inventory_delete_result
人员和流程考虑事项
此集成需要平台团队管理 Red Hat Ansible Automation Platform、HashiCorp Vault、HCP Packer 以及这些平台管理的下游主机。确保与平台团队、安全团队和应用程序团队进行跨团队协作,以满足集成目标。与应用程序团队明确预期,例如处理时间增加和运行阻塞。为平台团队和应用程序团队提供集中式文档和培训。更新 Terraform 模块和 CI/CD 管道,以与 Ansible Automation Platform 和 HCP Packer 集成。这种简化的方法可确保适当的治理,同时保持组织基础设施自动化管道中的运营效率。
结论
Red Hat Ansible Automation Platform 和 HashiCorp Packer 集成为现代、可扩展的基础设施管理奠定了基础。通过将基础设施视为不可变工件,组织可以实现更高的可靠性、安全性和运营效率。这种方法不仅解决了当前的基础设施挑战,还使团队能够充满信心地适应未来的技术要求。
此集成的成功强化了将专用工具结合起来创建综合解决方案的价值,这些解决方案超越了单个组件的功能,最终通过提高基础设施可靠性和运营效率,为企业带来卓越的业务成果。