在日常运维中,重复、批量操作服务器既繁琐又容易出错。Ansible作为轻量自动化工具,无需在目标主机装代理客户端、无需复杂配置、基于SSH即可实现批量管理。本文以Ubuntu为例,对ansible进行简单介绍。

Ansible是什么

Ansible是一款基于Python开发的开源自动化运维工具,核心用途是批量配置管理、应用部署、任务编排,简单说就是“一次操作,多台机器同步执行”,彻底解决传统运维逐台登录、重复敲命令的痛点。

核心优势

  • 无代理架构(Agentless):最省心的特点!无需在被管理的目标主机上安装任何客户端软件,仅通过SSH协议(Linux)或WinRM协议(Windows)通信,部署成本极低,不用额外维护客户端版本。

  • 幂等性:无论执行1次还是多次,最终系统状态始终一致,避免重复操作导致的错误(比如“安装Nginx”任务,已安装则不执行,未安装则自动安装)。

  • 简单易学:核心配置文件(Playbook)采用YAML语法,可读性极强,不用掌握复杂编程语言,运维新手1-2天就能上手编写自动化脚本。

  • 功能强大:内置1000+模块,覆盖软件安装、文件管理、服务启停、云资源管理等几乎所有运维场景,还支持自定义模块和角色,适配企业级需求。

核心组件

  • 控制节点(Control Node):安装Ansible的机器,用于执行命令、编写Playbook,管理所有目标主机,可选用笔记本、服务器等任何满足软件要求的设备。

  • 被管理节点(Managed Nodes):需要被自动化管理的目标主机(服务器、网络设备等),无需安装Ansible,仅需开启SSH(Linux)或WinRM(Windows)即可。

  • Inventory(主机清单):定义被管理主机的列表文件,可将主机分组(如web服务器组、数据库服务器组),并指定主机IP、登录用户等信息,是Ansible识别目标主机的基础。

  • Modules(模块):Ansible执行具体任务的工具,每个模块对应一个具体操作(如安装软件、复制文件),无需自己编写复杂脚本,调用模块即可完成操作。

  • Playbook(剧本):YAML格式的配置文件,用于编排多个任务,定义“在哪些主机上执行哪些操作”,可复用、可版本管理,是企业级自动化的核心载体。

环境搭建

本次教程以Ubuntu 22.04 LTS为例,控制节点和被管理节点均为Linux系统,Windows系统可参考官方文档配置WinRM协议。

控制节点安装Ansible

Ansible支持多种安装方式,推荐使用apt或pip安装,新手优先选apt,步骤更简单,适配Ubuntu系统默认包管理机制。

方式1:apt安装(Ubuntu/Debian系列,推荐)

  1. 更新apt源(确保能获取到最新的Ansible包):sudo apt update -y

  2. 安装Ansible(Ubuntu官方源已包含Ansible,无需额外添加第三方源):sudo apt install -y ansible python3-apt

  3. 验证安装成功:ansible --version出现Ansible版本信息,即为安装成功。

方式2:pip安装(通用,适合所有Linux系统)

  1. 安装Python和pip(Ubuntu默认已安装Python3,仅需补充pip):sudo apt install -y python3 python3-pip

  2. 升级pip并安装Ansible:pip3 install --upgrade pip pip3 install ansible

配置SSH免密登录

Ansible通过SSH通信,配置免密登录后,无需每次输入目标主机密码,提升自动化效率。Ubuntu系统默认开启SSH服务,若未开启可先执行sudo apt install -y openssh-server安装并启动。

  1. 控制节点生成SSH密钥(一路回车,无需设置密码):ssh-keygen -t rsa

  2. 将公钥复制到所有被管理节点(替换命令中的ubuntu和IP为目标主机的用户名和IP,Ubuntu默认用户名多为ubuntu):

    1
    2
    ssh-copy-id ubuntu@192.168.1.101  # 被管理节点1
    ssh-copy-id ubuntu@192.168.1.102 # 被管理节点2

    首次执行需输入目标主机密码,后续即可免密登录。
    如果不想交互式的输入用户名密码,可以使用下面的方法(sshpass自动将密码填充,StrictHostKeyChecking=no不进行本地.ssh/known_hosts指纹检查):

    1
    2
    3
    4
    5
    6
    7
    8
    9
    sudo apt update && sudo apt install sshpass -y
    # 显示输入密码
    sshpass -p 'passwd' ssh-copy-id -o StrictHostKeyChecking=no ubuntu@192.168.1.101 # 被管理节点1
    sshpass -p 'passwd' ssh-copy-id -o StrictHostKeyChecking=no ubuntu@192.168.1.102 # 被管理节点2

    # 把密码存入文件中
    # echo 'passwd' > passwdfile
    sshpass -f passwdfile ssh-copy-id -o StrictHostKeyChecking=no ubuntu@192.168.1.101 # 被管理节点1
    sshpass -f passwdfile ssh-copy-id -o StrictHostKeyChecking=no ubuntu@192.168.1.102 # 被管理节点2
  3. 验证免密登录:ssh ubuntu@192.168.1.101无需输入密码即可登录,说明配置成功。

配置主机清单(Inventory)

主机清单用于告诉Ansible“要管理哪些主机”,默认路径为/etc/ansible/hosts,我们可以直接编辑该文件,也可以自定义清单文件。Ubuntu系统中,编辑该文件需管理员权限。

  1. 编辑默认主机清单:sudo vim /etc/ansible/hosts

  2. 添加主机信息(按分组划分,方便批量操作),示例(适配Ubuntu默认用户名):

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
# 全局配置。默认采用python3,不进行本地.ssh/known_hosts指纹检查
[all:vars]
ansible_python_interpreter=/usr/bin/python3 # 或者在 /etc/ansible/ansible.cfg 中的[defaults]下定义 python_interpreter=/usr/bin/python3
ansible_ssh_common_args='-o StrictHostKeyChecking=no'

# 分组名:webservers(可自定义),下方是该组的主机
[webservers]
192.168.1.101 # 被管理节点1
192.168.1.102 # 被管理节点2
192.168.1.103 # 被管理节点3

# 可指定登录用户和端口(如果非默认22端口,Ubuntu默认SSH端口为22)
[webservers:vars]
ansible_ssh_user=ubuntu
ansible_ssh_port=22


# 分组名:dbservers(数据库服务器组),使用 /etc/ansible/ansible.cfg 中定义的默认用户登录
[dbservers]
192.168.1.201
192.168.1.202

# 分组名:webs(可自定义)。每个单独指定用户名
[webs]
192.168.1.101 ansible_ssh_user=ubuntu1 ansible_python_interpreter=/usr/bin/python3 # 被管理节点1
192.168.1.102 ansible_ssh_user=ubuntu2 # 被管理节点2
192.168.1.103 ansible_ssh_user=ubuntu3 # 被管理节点3


# 定义父组
[all_webs:children]
webservers
dbservers

查看主机清单:

1
ansible-inventory --graph

输出结果大概如下:

1
2
3
4
5
6
7
8
9
@all:
|--@local:
| |--localhost
|--@servers:
| |--10.2.28.35
|--@ungrouped:
|--@web:
| |--10.2.28.135
| |--10.2.28.35
  1. 验证主机清单:ansible all -m ping如果所有主机返回“pong”,说明Ansible能正常连接目标主机;若失败,检查SSH免密配置、主机IP是否正确,或目标主机SSH服务是否开启。
  2. 命名规范:小写、下划线,如web_servers

变量

变量是ansible自动化中存储动态值的核心机制,用于实现配置灵活性、环境适配和代码复用。我们可以直接将变量添加到主机清单中的hosts或组中。

常见的变量:

连接控制变量

变量名 作用 示例值
ansible_host 覆盖实际连接的主机名/IP 192.168.1.10
ansible_port 制定非标准SSH端口 2222
ansible_user 登录用户名 ubuntu
ansible_ssh_private_key_file 制定SSH私钥路径 ~/.ssh/deploy.key
ansible_password SSH秘钥(不推荐) P@ssw0rd
ansible_become 是否提权,使用sudo true
ansible_become_user 提权目标用户 root

基础设施变量

变量名 作用 示例值
http_port 应用服务端口 8080
db_host 数据库服务器地址 db01.example.com
max_connections 服务最大连接数 1000
data_dir 数据存储路径 /opt/data
cluster_nodes 集群节点列表 ["node1", "node2"]

Ansible核心用法

Ansible的使用主要分为两种场景:临时命令(Ad-Hoc)剧本(Playbook)。临时命令适合快速执行单个任务,剧本适合编排多个任务,实现复杂自动化。

临时命令(Ad-Hoc):快速执行单个任务

语法:ansible 主机/分组名 -m 模块名 -a '模块参数'

常用参数说明:
-i:指定自定义主机清单路径(默认使用/etc/ansible/hosts)
-m:指定要使用的模块(默认使用command模块)
-a:模块的具体参数
--become:提升权限(如sudo)
-u:指定SSH登录用户(Ubuntu默认用户为ubuntu)

常用临时命令示例(直接复制执行,适配Ubuntu)

  1. 查看所有webservers主机的磁盘使用情况:ansible webservers -m shell -a 'df -h'

  2. 批量在dbservers主机上安装MySQL(Ubuntu中MySQL包名为mysql-server):ansible dbservers -m apt -a 'name=mysql-server state=present' --become说明:state=present表示“确保安装”,–become表示使用sudo权限,Ubuntu中普通用户执行管理员操作需sudo。

  3. 批量启动webservers主机的Nginx服务:ansible webservers -m systemd -a 'name=nginx state=started enabled=yes' --become说明:enabled=yes表示设置开机自启,Ubuntu 16.04及以上默认使用systemd管理服务。

  4. 批量复制本地文件到目标主机:ansible all -m copy -a 'src=/root/test.txt dest=/tmp/test.txt mode=0644' --become说明:mode=0644是文件权限,src是本地路径,dest是目标主机路径,–become用于获取写入权限。

  5. 查看模块帮助(新手必备):

    1
    2
    ansible-doc -s apt  # 查看apt模块的简短用法
    ansible-doc copy # 查看copy模块的详细文档和示例

常用模块速查表

Ansible内置模块众多,以下是新手最常用的模块,按功能分类,方便快速查询,重点标注Ubuntu适配模块:

模块类别 模块名 核心功能 简单示例(适配Ubuntu)
软件包管理 apt Ubuntu/Debian系列安装软件 apt name=nginx state=present
软件包管理 yum CentOS/RHEL系列安装软件(Ubuntu不适用) yum name=nginx state=present(Ubuntu用apt)
服务管理 systemd 管理systemd服务(启停、开机自启) name=nginx state=started
文件操作 copy 本地文件复制到目标主机 src=/local/file dest=/remote/file
文件操作 file 创建目录、修改文件权限 path=/tmp/dir state=directory
命令执行 shell 执行shell命令(支持管道、重定向) shell ‘ps aux | grep nginx’
用户管理 user 创建、删除用户,修改用户组 name=appuser state=present

Playbook(剧本):编排复杂任务

当需要执行多个任务(如“安装Nginx → 复制配置文件 → 启动服务 → 开机自启”)时,临时命令无法满足需求,此时需要编写Playbook,将多个任务编排起来,一键执行。

Playbook采用YAML语法,核心规则:
缩进统一(推荐2个空格,不要用Tab)键值对用冒号分隔(如name: 安装Nginx)列表项用“- ”开头(如tasks下的任务列表)

实战示例1:批量部署Nginx

  1. 创建Playbook文件(命名为nginx_deploy.yml):
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
    55
    56
    57
    58
    59
    60
    61
    62
    63
    64
    65
    66
    67
    68
    69
    70
    71
    72
    73
      - name: 批量部署Nginx服务  # Play名称,自定义
    hosts: webservers # 目标主机分组(对应Inventory中的分组)
    remote_user: ubuntu # 登录目标主机的用户(Ubuntu默认用户)
    become: yes # 提升权限(sudo,Ubuntu必需)
    tasks: # 任务列表,按顺序执行
    - name: 更新apt源 # 任务0:Ubuntu安装软件前先更新源(关键步骤)
    apt:
    update_cache: yes
    cache_valid_time: 3600 # 缓存1小时,避免重复更新
    - name: 安装Nginx # 任务1:安装Nginx(Ubuntu用apt模块)
    apt:
    name: nginx
    state: present # present=确保安装,absent=卸载,latest=安装最新版

    - name: 复制Nginx配置文件 # 任务2:复制本地配置文件到目标主机
    copy:
    src: /root/nginx.conf # 本地配置文件路径
    dest: /etc/nginx/nginx.conf # 目标主机路径(Ubuntu Nginx默认配置路径)
    mode: 0644 # 文件权限
    notify: # 通知处理器(配置文件变更后重启服务)
    - restart nginx

    - name: 启动Nginx服务并设置开机自启 # 任务3:启动服务
    systemd:
    name: nginx
    state: started
    enabled: yes

    handlers: # 处理器(仅在被notify触发时执行,用于重启服务、重载配置等)
    - name: restart nginx
    systemd:
    name: nginx
    state: restarted`

    1. 准备本地Nginx配置文件(/root/nginx.conf),可使用Ubuntu默认配置(可从目标主机/etc/nginx/nginx.conf复制),也可自定义。

    2. 执行Playbook:`ansible-playbook nginx_deploy.yml`

    3. 执行结果说明:

    4. 绿色:任务已执行,目标主机状态无变化(如Nginx已安装)

    5. 黄色:任务已执行,目标主机状态发生变化(如更新apt源、安装了Nginx、复制了配置文件)

    6. 红色:任务执行失败,需检查错误信息(如依赖缺失、路径错误)

    #### 实战示例2:服务器初始化

    新服务器上线时,需批量完成初始化配置(优化apt源、配置时间同步、关闭防火墙等),编写Playbook可实现标准化初始化(Ubuntu无SELinux,无需关闭):

    ```yaml
    - name: 生产环境服务器标准化初始化
    hosts: all
    remote_user: ubuntu
    become: yes
    tasks:
    - name: 优化apt源为阿里云源(Ubuntu 22.04
    copy:
    src: /root/sources.list
    dest: /etc/apt/sources.list
    mode: 0644
    - name: 更新apt源缓存
    apt:
    update_cache: yes
    - name: 安装时间同步工具
    apt:
    name: ntpdate
    state: present
    - name: 同步系统时间(阿里云时间服务器)
    shell: ntpdate ntp.aliyun.com
    - name: 关闭防火墙(生产环境可根据需求调整规则,Ubuntu默认防火墙为ufw)
    ufw:
    state: disabled

实战示例2:更新google-chrome

对服务器(此处以localhost为例)上的google-chrome进行升级:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
- name: 升级 Ubuntu 22.04 上的 Google Chrome 浏览器
hosts: localhost
gather_facts: true
become: true

tasks:
# 更新缓存
- name: 更新 apt 缓存
apt:
update_cache: yes

# 升级 Chrome
- name: 升级 Google Chrome 到最新版
apt:
name: google-chrome-stable
state: latest

# 验证版本
- name: 检查 Chrome 版本
command: google-chrome --version
register: chrome_ver
changed_when: false

- name: 显示版本
debug:
msg: "升级成功!当前版本:{{ chrome_ver.stdout }}"

Playbook常用执行命令

1
2
3
4
5
6
7
8
9
10
11
12
13
14
# 标准执行Playbook
ansible-playbook nginx_deploy.yml

# 模拟执行(Dry Run),不实际修改系统,用于验证剧本逻辑
ansible-playbook nginx_deploy.yml --check

# 仅执行指定标签的任务(需在Playbook中给任务添加tags)
ansible-playbook server_init.yml --tags "ntp,ufw"

# 限制仅在某台主机执行(灰度验证常用)
ansible-playbook nginx_deploy.yml --limit 192.168.1.101

# 输出详细日志(调试用)
ansible-playbook nginx_deploy.yml -vvv

生产环境必备:敏感信息加密(Ansible Vault)

Playbook中若包含敏感信息(如数据库密码、云服务AK/SK),明文存储会有安全风险,Ansible Vault可实现敏感数据加密,满足等保合规要求。(Ubuntu与CentOS用法一致)

常用Vault命令

  1. 创建加密文件(用于存储敏感变量):ansible-vault create secret.yml执行后会提示设置密码,输入密码后进入编辑模式,添加敏感变量(如数据库密码):

    1
    2
    3
    db_password: '12345678'
    aliyun_ak: 'XXXXXXXXXXXX'
    aliyun_sk: 'YYYYYYYYYYYY'
  2. 编辑加密文件:ansible-vault edit secret.yml需输入创建时的密码,方可编辑。

  3. 执行包含加密文件的Playbook:

    1
    2
    3
    4
    5
    # 手动输入密码
    ansible-playbook nginx_deploy.yml --ask-vault-pass

    # 指定密码文件(无需手动输入,适合自动化执行)
    ansible-playbook nginx_deploy.yml --vault-password-file /root/vault_pass.txt

五、新手常见问题排查(适配Ubuntu)

  1. 问题1:执行ansible ping失败排查方向:① SSH免密配置是否正确(重新执行ssh-copy-id);② 目标主机ufw防火墙是否开放22端口(可执行sudo ufw allow 22开放);③ 主机IP是否在Inventory中正确配置,登录用户是否为Ubuntu默认用户(ubuntu)。

  2. 问题2:Playbook执行提示“Permission denied”解决方法:在Playbook中添加become: yes,提升权限,或执行命令时添加--become,Ubuntu普通用户无管理员权限,必需sudo。

  3. 问题3:模块执行失败(如apt安装失败)排查方向:① 目标主机apt源是否正常(可先执行sudo apt update);② 软件包名是否正确(如Ubuntu安装MySQL为mysql-server,而非mariadb-server);③ 是否添加become: yes权限。

  4. 问题4:Playbook执行后,配置未生效排查方向:① 任务顺序是否正确(如Ubuntu安装软件前需先更新apt源);② 是否需要重启服务(可通过notify触发处理器);③ 配置文件路径是否正确(如Ubuntu Nginx配置路径为/etc/nginx/nginx.conf)。

六、进阶学习方向

掌握基础用法后,可进一步学习以下内容,提升Ansible使用能力:

  1. Roles(角色):将复杂Playbook拆分为可复用的角色(如nginx角色、mysql角色),适合大型项目管理,可通过ansible-galaxy下载社区现成角色。

  2. 变量与模板(Template):使用Jinja2模板,动态生成配置文件(如根据不同主机配置不同的Nginx端口)。

  3. 条件判断与循环:在Playbook中添加when条件(如“仅在Ubuntu系统上执行apt安装”)、loop循环(如批量创建多个用户)。

  4. 云资源管理:对接阿里云、AWS等云平台,实现云主机、安全组等资源的自动化创建与管理。

  5. Ansible Tower:可视化管理Ansible,实现Playbook调度、权限控制、日志审计,适合企业级大规模部署。

七、总结

Ansible的核心价值的是“自动化、标准化、可复用”,无需复杂的编程基础,新手通过本文的基础操作和实战案例(适配Ubuntu系统),就能快速上手,解决日常运维中的重复工作。

建议大家先从临时命令入手,熟悉常用模块(重点掌握apt模块),再逐步编写简单的Playbook,结合Ubuntu服务器的实际管理场景(如批量部署、服务器初始化)反复练习,很快就能熟练掌握。