入门 Ansible 镜像执行环境 EE
2025-02-10 20:00
1 什么是 Ansible
Ansible 可自动管理远程系统并控制其所需状态。 大多数 Ansible 环境都有三个主要组件:
- 控制节点 Control node: 安装了Ansible的系统,运行 ansible 或 ansible-inventory 等 Ansible 命令。
- 清单 Inventory:按逻辑组织的受管节点列表。可以在控制节点上创建清单,向 Ansible 描述主机部署情况。
- 受管节点 Managed node: 接受 Ansible 控制管理的远程系统或主机。
1.1 特性
Ansible 提供开源自动化,可降低复杂性并随处运行。使用 Ansible 几乎可以实现任何任务的自动化。
- 消除重复工作,简化工作流程
- 管理和维护系统配置
- 持续部署复杂软件
- 执行零停机时间滚动更新
Ansible 使用简单、人类可读的脚本(称为 playbook)来自动执行任务。在playbook中声明本地或远程系统所需的状态。Ansible 可确保系统保持该状态。
1.2 原则
作为自动化技术,Ansible 的设计遵循以下原则
- 无代理架构 Agent-less architecture:避免在 IT 基础设施中安装额外软件,从而降低维护开销。
- 简约 Simplicity:自动运行手册使用简单明了的 YAML 语法编写代码,读起来就像文档一样。Ansible 也是去中心化的,它使用 SSH 和现有的操作系统凭据来访问远程机器。
- 可扩展性和灵活性 Scalability and flexibility:模块化设计支持多种操作系统、云平台和网络设备,可轻松快速地扩展自动化系统。
- 惰性和可预测性 Idempotence and predictability:当系统处于你的操作步骤所描述的状态时,即使操作步骤运行多次(幂等操作),Ansible 也不会改变任何东西。
2 在容器中使用 Ansible: 执行环境(EE) Execution Environments
Ansible 执行环境旨在解决复杂性问题,并提供容器化带来的所有好处。EE 可以在三个主要方面降低复杂性:
- software dependencies 软件依赖性
- portability 便携性
- content separation 内容分离
2.1 设置EE
确保在系统上安装了以下软件包:
- docker(或者
podman不稳定 不推荐) - python3
- python3-pip
mise use -g python@3.11
此处尽量安装最新版本的python3,否则安装ansible-navigator时,ansible-builder默认版本为1.x.x,与yml文件的 version:3 冲突报错。
安装docker,参考2025-02-08-about-container#32-安装docker-deamon
安装 ansible-navigator :
pip3 install ansible-navigator
ansible-navigator --version
ansible-builder --version
安装 ansible-navigator 可让你在命令行上运行 EE。它包括用于构建 EE 的 ansible-builder 软件包。
2.2 构建EE
构建一个 EE,它代表一个 Ansible 控制节点,除了 Ansible 集合( community.postgresql )及其依赖关系( psycopg2-binary Python 连接器)之外,还包含 ansible-core 和 Python 等标准软件包。
构建EE文件夹:
mkdir my_first_ee && cd my_first_ee
创建一个 execution-environment.yml 文件,指定镜像中应包含的依赖项。
version: 3
images:
base_image:
name: quay.io/fedora/fedora:39
dependencies:
ansible_core:
package_pip: ansible-core
ansible_runner:
package_pip: ansible-runner
system:
- openssh-clients
- sshpass
galaxy:
collections:
- name: community.postgresql
psycopg2-binary Python 软件包已包含在集合的 requirements.txt 文件中。对于不包含 requirements.txt 文件的集合,需要明确指定 Python 依赖项。有关详情,参阅 Ansible Builder 文档。
构建名为 postgresql_ee 的 EE 容器镜像。(ansible-builder 默认使用的是 podman。。。),如果使用 docker,添加 –container-runtime docker 参数。
ansible-builder build -v --tag postgresql_ee --container-runtime docker
# 实际转换为 docker的命令(这里构建镜像需要几分钟,卡住不动实际在下载,缓解焦虑不妨直接执行洗面命令):
# docker build -f context/Dockerfile --progress=plain -t postgresql_ee context
2.3 运行EE
在命令行上对 localhost 或使用 ansible-navigator 的操作远程目标运行 EE。
除了 ansible-navigator 之外,还可以使用其他工具运行 EE。
创建 test_localhost.yml。
- name: Gather and print local facts
hosts: localhost
become: true
gather_facts: true
tasks:
- name: Print facts
ansible.builtin.debug:
var: ansible_facts
在 postgresql_ee EE 中运行 playbook。
ansible-navigator run test_localhost.yml --execution-environment-image postgresql_ee --mode stdout --pull-policy missing --container-options='--user=0'
可以看到收集到的事实是关于容器的,而不是开发机器的。这是因为 ansible playbook 是在容器内运行的。
2.4 远程目标运行EE
先使用 vagrant 创建 10台 ubuntu 虚拟机。安装 VirtualBox 和 Vagrant 参考:2024-11-21-regain-vagrant
生成SSH密钥对:
ssh-keygen -t rsa -b 4096 -f ~/.ssh/vagrant_key
mkdir vagrant-cluster && cd vagrant-cluster
,创建Vagrantfile:
Vagrant.configure("2") do |config|
# 这里的 bionic64镜像实际上是 Ubuntu 18.04 LTS 64
config.vm.box = "hashicorp/bionic64"
# 禁用自动插入新密钥,使用固定密钥
config.ssh.insert_key = false
# 循环创建10台虚拟机
(1..10).each do |i|
config.vm.define "node#{i}" do |node|
node.vm.hostname = "node#{i}"
ip = "172.28.128.#{9 + i}" # IP范围:192.168.0.10 ~ 192.168.0.19
node.vm.network "private_network", ip: ip
# VirtualBox自定义设置
node.vm.provider "virtualbox" do |vb|
vb.name = "node#{i}"
vb.memory = "2048"
vb.cpus = 1
end
# 将主机公钥添加到虚拟机(替换YOUR_PUB_KEY)
node.vm.provision "shell", inline: <<-SHELL
# 解决报错: dpkg-preconfigure: unable to re-open stdin: No such file or directory
export DEBIAN_FRONTEND=noninteractive
# 加入 ssh pub key
echo "ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAACAQDYgAOBXNnyhZdy25vl3B3jWgDw57j2BKq7kpDEXyWbGUlo9lcFnBf4ZBKGi1bU1T+59mWbMPQNykj0xcB3Tw+ZM/VYBf9OX1CQAM29F8QQZHBh2Y4VpEGIfXGIGJSkMBc1LVIQXYyfVbCNNRM9hZIRzbtq78D9Uu1fenuDk9IwtgJ1abjvl1tSHTcr3E2S3GXFDgCBZp00VRrtiVRz/bV0fb8HKdngQh1AsL7AKUv3cShN2ubXcsxk1R679fOVfuRo/AaomgA+vavVfFpqwr6ULCjX5n0dbqKiyGusRhbk8GthIIhN1ewbW/9/piASGNeZRViy87tJM/7dy4O+1Zjv5MsSwK0lWLu8Hf6Fl42GmlKIhGdWU1dBf8od0PI/7VcR4j9fiENmxh6E+4xc/Gt6YGWgJvtXoDsjj5FWELNBUiuDhRrHKuR9ziDck3lbHUR95GLIj89zWBkP9ZflsdEflxus0Gtjb6E8U1b6qu7mikI9LzMsuVe8d+viCdxYtd+kayXqdZrVkX9sqOcTyqYUHIrJT3LqiOQWj0rV2/vrQ5RKec9iJWF2j9yO1pcI0BcIlHaDMB9l0tG1hjg2n86lkM0HYcqlED3uhbXUBrm6iLds3nK26AHGFlVJYI3E9sJ4yANm8AcO6VP3F6DUj6vENHf/r1HHG2Ac3ZfoIpGJTw== memorycancel@TommyUbun" >> /home/vagrant/.ssh/authorized_keys
chmod 600 /home/vagrant/.ssh/authorized_keys
# 安装 python3.11.11
apt-get update -y && apt-get upgrade -y
add-apt-repository ppa:deadsnakes/ppa -y
apt-get update
apt-get install -y software-properties-common wget build-essential
wget https://www.python.org/ftp/python/3.11.1/Python-3.11.1.tar.xz
tar -xf Python-3.11.1.tar.xz
cd Python-3.11.1
./configure --enable-optimizations
make altinstall
rm /usr/bin/python3
cp /usr/local/bin/python3.11 /usr/bin/python3
SHELL
end
end
end
vagrant plugin update
vagrant up
ssh vagrant@192.168.56.10 # 连接第1台
ssh vagrant@192.168.56.19 # 连接第10台
mkdir inventory
在 inventory 目录下创建 hosts.yml 清单文件。
all:
hosts:
172.28.128.10
172.28.128.11
172.28.128.12
172.28.128.13
172.28.128.14
172.28.128.15
172.28.128.16
172.28.128.17
172.28.128.18
172.28.128.19
创建 test_remote.yml playbook:
- name: Gather and print facts
hosts: all
become: true
gather_facts: true
tasks:
- name: Print facts
ansible.builtin.debug:
var: ansible_facts
在 postgresql_ee EE 内运行playbook。
ansible-navigator run test_remote.yml -i inventory --execution-environment-image postgresql_ee:latest --mode stdout --pull-policy missing --enable-prompts -u vagrant -k -K
总结:使用ansible-builder 根据 execution-environment.yml 文件构建 Ansible 运行环境 EE(镜像)。 使用ansible-navigator 在Ansible 运行环境 EE(镜像) 内执行 playbook。