R / Richie全部文章 ↑

Linux · 5 分钟阅读

Ansible

Ansible 用 SSH 把"任务"推到远端执行,控制节点上不需要装任何 agent——这是它和 Salt、Chef、Puppet 的最大区别。

2026 年视角:社区版已经走到 10.x / Core 2.18+;Python 2 早就不支持了;PIP 装才是主流;EPEL 的 2.9 已经落伍,生产慎用。


1. 核心概念

概念 一句话
控制节点 跑 ansible 的机器
被管理节点 装 SSH + Python 即可
Inventory 主机清单(静态/动态)
Playbook YAML 写的剧本
Task 一次模块调用
Module 单个功能单元(copy / yum / service)
Role 标准化目录,复用 Playbook
Handler 变更通知触发的任务

2. 一段 Playbook 长什么样

- name: 部署 Web
  hosts: web
  become: true

  tasks:
    - name: 安装 Apache
      ansible.builtin.yum:
        name: httpd
        state: present

    - name: 推送配置
      ansible.builtin.template:
        src: httpd.conf.j2
        dest: /etc/httpd/conf/httpd.conf
      notify: reload httpd

  handlers:
    - name: reload httpd
      ansible.builtin.service:
        name: httpd
        state: reloaded

3. 工作流程

1. 加载 ansible.cfg + Inventory
2. 解析 Playbook
3. 收集 facts(setup 模块)
4. 按顺序执行 Task
5. 触发条件满足的 Handler
6. 汇总结果

4. 几条铁律

  • 幂等:同一个 playbook 跑两遍结果相同,别写 command: systemctl restart,用 service: state=restarted
  • 模块优先:能用模块就别用 shell / command
  • 变量集中:放 group_vars/ / host_vars/,别散落在 task 里
  • 小步提交:每个 Playbook 只做一件事

5. 安装

5.1 控制节点要求

组件 最低 推荐
Python 3.8+ 3.11+
SSH 客户端 任意 OpenSSH 8.0+
内存 1 GB 2 GB+

被管理节点只要 SSH + Python 2.6+/3.5+ 就能跑。

5.2 PIP(最稳)

python3 -m pip install --user ansible
# 或
uv pip install --system ansible-core

# 验证
ansible --version

5.3 系统包

CentOS / RHEL(EPEL 仓库仍是 2.9,生产慎用):

yum install -y epel-release
yum install -y ansible

Ubuntu 24.04+:

apt install -y ansible

5.4 容器化

无污染的开发环境:

docker run --rm -it \
  -v ~/.ssh:/root/.ssh:ro \
  -v $(pwd):/work \
  -w /work \
  quay.io/ansible/ansible-runner:latest

5.5 验证

ansible --version
ansible localhost -m ping

5.6 配置文件

mkdir -p /etc/ansible
cat > /etc/ansible/ansible.cfg <<'EOF'
[defaults]
inventory       = /etc/ansible/hosts
remote_user     = deploy
host_key_checking = False
roles_path      = ./roles
deprecation_warnings = False
EOF

2026 年别用 /etc/ansible/,放到项目目录里更便携。

5.7 常见坑

  • macOS 自带 Python 太老,brew 装一个 python@3.12
  • 升级系统 Python 后记得重装 ansible,否则控制台一片红
  • 国内环境加 ANSIBLE_PYTHON_INTERPRETER 强制走指定解释器

6. Inventory

Inventory 列出被管理的主机。默认路径 /etc/ansible/hosts,但实际项目里通常放在仓库内的 inventory/ 目录里。

6.1 静态清单

# inventory/prod/hosts
[lb]
192.168.50.66
192.168.50.110

[web]
192.168.50.111
192.168.50.112

[db]
192.168.50.113

范围语法:

[web]
www[01:50].example.com

[db]
db-[a:f].example.com

6.2 主机变量

jumper ansible_ssh_port=5555 ansible_ssh_host=192.168.50.66

[targets]
localhost           ansible_connection=local
other1.example.com  ansible_connection=ssh ansible_ssh_user=deploy

6.3 动态清单

云上主机(AWS、阿里云、腾讯云)几乎都是动态的,用社区提供的插件即可:

# inventory/aws_ec2.yml
plugin: aws_ec2
regions:
  - cn-north-1
keyed_groups:
  - key: tags.Environment
hostnames:
  - private-ip-address

7. 常用命令

# 测试连通
ansible all -m ping

# 一行输出
ansible all -m ping -o

# 远程执行
ansible web -m shell -a 'uptime'
ansible all -a "/bin/echo hello"

# 列出主机 / 收集 facts
ansible web --list-hosts
ansible web -m setup --tree facts/

8. SSH 配置

首次连接大量新主机时,known_hosts 检查会让流程变得很烦。建议在个人开发环境关掉:

# ansible.cfg
[defaults]
host_key_checking = False

或者用环境变量:

export ANSIBLE_HOST_KEY_CHECKING=False

生产环境慎用,要开 host_key_checking = True 防中间人。


9. 最佳实践

  • 静态 + 动态混用:开发测试用静态文件,生产用云厂商动态插件
  • 用 YAML 格式(xxx.yml)而非老旧的 INI
  • 把敏感信息丢进 ansible-vault,别放在 inventory 里
  • 关键密码走环境变量 + SOPS/Hashicorp Vault 集成

10. 参考