ansible-自动化运维工具

ansible是自动化运维平台,用于集中管理多台服务器 ,进行配置管理与应用部署。

管理前提:已在受控节点(指被ansible管理的服务器或其他网络设备)上配置了密钥登录,ansible可以无密码登录到受控节点

Ansible「2.9」 中文官方文档 — Ansible Documentation

安装与配置

安装

# RedHat/CentOS 需要先安装epel源
sudo yum install epel-release
sudo yum install ansible -y

配置

主机互信配置

# 生成SSH密钥
ssh-keygen -t rsa
# 复制密钥到远程主机
ssh-copy-id /root/.ssh/id_rsa.pub root@remote_ip
# ssh 的时候不会提示保存密钥(其实也就输个yes的事情,可配可不配)
ssh-keyscan remote_ip >> ~/.ssh/known_hosts

被管主机只需要支持ssh连接就可以。

  1. 大批量的主机互信可考虑使用expect脚本
  2. 注意如果openssh升级后,需删除~/.ssh/known_hosts下对应主机的密钥再重新连接

主机清单

官方叫Inventory,听着怪怪的,其实就是相当于hosts文件,配置受控节点清单,可以采用ini格式或yaml格式配置(官方推荐yaml)。

可以在ansible命令执行时添加-i xxx/hosts指定,也可以在ansible.cfg中配置,默认的话是使用/etc/ansible/hosts

ini格式:

# xxx/hosts

mail.example.com

[grou1]
a.example.com
b.example.com

[group2]
one.example.com
two.example.com
three.example.com
1.2.3.4
192.168.123.[110:119]

[grou2:vars]

[fathergroup:children]   # 表示该主机组下的是子主机组
group1
group2

yaml格式:

all:
  hosts:
    mail.example.com:
  children:
    webservers:
      hosts:
        foo.example.com:
        bar.example.com:
   	  vars:
    dbservers:
      hosts:
        one.example.com:
        two.example.com:
        three.example.com:
# 查看主机组(内置all、ungrouped两个主机组)
ansible xx_group --list-hosts  

ansible.cfg

执行时优先使用当前目录下的ansible.cfg,没有则使用默认的/etc/ansible/ansible.cfg

下面是ansible.cfg中包含的几类配置项,初始状态是啥也没配的。

[defaults]
inventory=./hosts    # 默认使用当前目录下的Inventory仓库, 没有的话使用默认的

[inventory]

[privilege_escalation]
# 提权,如果受控主机的用户非root,需要配置好sudo
become=true
become_method=sudo
become_user=root


[paramiko _connection]

[ssh_connect]

[persistent_connection]

[accelerate]

[selinux]

[colors]

[diff]

命令管理

ansible server_name/group_name 
    -m module_name          # 调用模块
    -a "module_parameters"  # 模块参数
    -f num                  # 并行数

module模块

# 查看已有模块
ansible-doc -l
# 查看模块参数及使用方法
ansible-doc module_name

shell 命令行

远端执行操作系统命令

# shell 模块
ansible xx_group -m shell -a ‘sys_cmd’

file 文件

创建、删除文件/目录,修改文件/目录属性,

# file 模块
ansile xx_group -m file -a 'arg1=V1 arg2=V2 ...'
args:
	path/name/dest=		# 指定文件/目录绝对路径
	state= 				# 指定行为
	touch=				# 创建文件
	directory=			# 创建目录
	file=				# 对已有文件进行修改
	absent=				# 删除
	link=				# 软链接 	src指定源文件
	hard=				# 硬链接
	ower=				# 指定所有者
	group=				# 指定所有组
	mode=				# 指定权限
	setype=				# 指定上下文

copy/fetch 拷贝

copy: 拷贝本地文件到受控主机上

fetch: 拷贝受控主机文件到本地

# copy模块
ansible xx_group -m copy -a "src=/local/path/file dest=remote/path"
args:
	content=	# 写入内容到目标文件中
	src=		# 源文件
	dest=		# 目标地址
	owner=		# 指定所有者
	group=  	# 指定所属组
	mode=		# 指定权限
	
# fetch模块
ansible xx_group -m fetch -a "src=remote/path/file dest=local/path"

yum 软件包

yum_repository模块用于配置受控主机的yum源。

一个标准的yum源配置(.repo)如下

[aa]
name=   	# 该yum源的描述信息
baseurl=	# 源的具体地址
enabled=	# 是否启用,0或1
gpgcheck=	# 安装时是否进行数字签名验证,0或1
gpgkey=		# gpgkey为1时使用的公钥所在位置
# yum_repository模块
ansible xx_group -m yum_respository -a "args"
args:
	name=
	description=	# 
	baseurl=		# yum源的位置
	enabled=		# 启用源,true或false
	gpgcheck=		# 启用数字签名验证,true或false
	gpgkey=			# 指定公钥位置
	

# yum模块
ansible xx_group -m yum -a "args"
args:
	name=	# 指定软件包名称
	state=	# present/installed(默认)-安装软件包;absent/removed-卸载安装包;latest-更新
	

yum可以用其他模块替代,如apt,用于其他版本的Linux系统。

service 服务

对服务的管理,systemctl

ansible xx_group -m service -a "args"
args:
	name=		# 指定服务
	enabled=	# 设置服务开机自启,yes或no,默认为空
	state=		# 启动/关闭服务,started/stopped/restarted

group/user 组、用户

group对组进行管理,user对用户进行管理

# group模块
ansible xx_group -m group -a "args"
args:
	name=		# 指定组名
	state=		# present-创建组,absent-删除组
	
# user模块
ansible xx_group -m user -a "args"
args:
	name=		# 指定用户名
	comment=	# 指定注释信息
	group=		# 指定用户组
	groups=		# 指定用户附属组
	password=	# 指定密码   
	password={{‘pwd001’ | password_hash('sha512')}}  # 使用SHA512哈希算法进行加密
	state=		# present-创建用户,absent-删除用户
	shell=      # 指定shell程序

firewalld 防火墙

防火墙管理

# firewalld模块
ansible xx_group -m firewalld -a "args"
args:
	service=		# 指定开放服务
	port=			# 指定开放端口,80/tcp
	permanent=yes	# 设置永久生效,无默认值
	immediate=yes	# 设置当前生效,默认不生效
	state=			# enabled-创建规则,disabled-删除规则
	rich_rule=		# 富规则

parted/filesystem/mount/lvg/lvol

  • parted:对分区进行管理

  • filesystem:文件系统格式化

  • mount:挂载分区

  • lvg:卷组管理

  • lvol:逻辑卷管理

# parted 模块
ansible xx_group -m parted -a "args"
args:
	device=			# 指定哪块磁盘
	number=			# 指定第几个分区
	part_start=		# 指定磁盘划分的起始位置,不写默认为0%
	part_end=		# 指定磁盘划分的结束位置
	state=			# 指定操作,present-创建,absent-删除
	
# filesystem 模块
ansible xx_group -m filesystem -a "args"
args:
	dev=		# 指定设备	
	fstype=		# 指定文件系统类型
	force=		# 是否强制格式化,默认0

# mount 模块
ansible xx_group -m mount -a "args"
args:
	src=		# 指定挂载的设备
	path=		# 指定挂载点
	fstype=		# 指定挂载的文件系统,必填
	opts=		# 指定挂载选项,不指定默认为default
	state=		# mounted-挂载并写入etc/fstab,present-写入/etc/fstab,unmounted-仅卸载,absent-卸载并从/etc/fstab移除


# lvg模块
ansible xx_group -m lvg -a "args"
args:
	pvs=		# 指定物理卷,此命令会自动创建pv,多个pv使用','隔开
	vg=			# 指定卷组名称
	pesize=		# 指定PE大小,默认为4
	state=		# present(默认)-创建卷组,absent-删除卷组

# lvol模块
ansible xx_group -m lvg -a "args"
args:
	vg=			# 指定在哪个卷组划分逻辑卷
	lv=			# 指定逻辑卷名称
	size=		# 指定逻辑卷大小
	state=		# present-创建逻辑卷,absent-删除逻辑卷

replace/lineinfile替换

  • replace:字符级替换
  • linefile:行级替换
# replace
ansible xx_group -m replace -a "args"
args:
	path=		# 指定待编辑的文件
	regexp=		# 指定待编辑的内容,正则表达式
	replace=	# 替换后的字符
	
# linefile
ansible xx_group -m replace -a "args"
args:
	path=		# 指定待编辑的文件
	regexp=		# 指定待编辑的内容,正则表达式
	line=		# 替换后的行

# 追加到目标文件末尾
ansible xx_group -m lineinfile -a "dest=/path/to/remote/file line='newline'"
# 删除(切记正则表达式要写合适)
ansible xx_group -m lineinfile -a "dest=/path/to/remote/file regexp='正则' state=absent"
# 替换
ansible xx_group -m lineinfile -a "dest=/path/to/remote/file regexp='正则' line='newline' state=persent"
# 插入(某一行前)
ansible xx_group -m lineinfile -a "dest=/path/to/remote/file insertbefore='正则' line='newline'"
# 插入(某一行后)
ansible xx_group -m lineinfile -a "dest=/path/to/remote/file insertafter='正则' line='newline'"

setup

用于获取被管理主机的配置信息

ansible xx_group -m setup -a 'args'
argvs:
	filter= 	# 筛选输出的信息,可写可不写

脚本管理playbook

ansible的playbook采用yaml格式。参数可采用K=V格式或yaml字典格式(一行一参数)。

主要包含两个元素:

  • 主机清单user/host
  • 任务列表task

此外,还有变量、文件、善后任务等其他可选内容

- name: play1描述
  hosts: server1
  remote-user: user_name
  gather_facts: yes/no    # 执行此play时是否需要通过setup获取主机组的信息(fact变量)
  vars:
    变量1: 值1
    变量2: 值2
  tasks:
  - name: 任务一
    模块1: argx1=vx1 argx2=vx2
  - name: 任务二
    模块x: argx1=vx1 argx2=vx2
  handlers:
  - name: 
    ...
    
- name: paly2描述
  hosts: server2
  tasks:
  ...
ansible-playbook playbook.yml 
	-i <hosts_file>  # 配置host,默认为/etc/ansible/hosts
	-C # 仅测试,不执行

受控主机host/user

在哪一台受控主机上以什么角色执行

key 说明
hosts 主机IP或IP组
user 使用哪个账户执行
become 切换成其他用户执行
become_method 切换方式 [sudo, su, pbrun, pfexec, doas]
become_user 切换的用户名 [root或其他用户]

当脚本里包含了become时,ansible-playbook执行时需要带上--ask-become-pass,会在执行后提示输入sudo密码

任务task

  1. task是在受控主机上执行的任务,自上而下执行。
  2. 每个task都是对模块的一次调用
  3. 建议每个task配置好name属性,相当于注释,在执行时会输出,用于提示执行情况

变量vars

变量作用域越小,优先级越高

变量定义

...
  vars_files:  # 定义变量文件
  - vars.yaml
  vars:			# 定义变量
    变量1: 值1
    变量2: 值2

使用{{ 变量名 }}进行引用,{{}}中两边的空格无影响

字典变量

...
  vars:
    字典1:
      var1: value1
      var2: value2

使用{{ 字典名.变量名 }}进行引用

列表变量

类似于json的yaml表示

...
  vars:
    列表名:
    - 变量1: 值1
      变量2: 值2
    - 变量1: 值3
      变量2: 值4

使用{{ 列表名[下标] }}{{ 列表名[下标].变量名 }}进行引用,下标从0开始

数字变量

{{ a + b }}		# 加
{{ a - b }}		# 减
{{ a * b }}		# 乘
{{ a / b }}		# 除
{{ a ** b }}	# 次方

注册变量

将task执行后的shell输出注册为一个变量

...
  tasks:
  - name: 执行shell命令
    shell: 'hostname'
    register: aa
  - name: 打印注册变量
    debug: msg={{aa}}

aa相当于一个字典,包含cmd(执行的命令)、rc(执行的返回值)、stdout(执行的输出结果),如通过{{aa.stdout}}只输出执行结果

fact变量

fact指被管理主机的信息,可通过setup模块获取到,包含大量键值,如:

  • ansible_default_ipv4:Ipv4信息
  • ansible_default_ipv4.address:IP地址
  • ansible_fqdn:主机名
  • ansible_bios_version:BIOS版本

内置变量

  • {{groups}}列出清单文件中定义的所有主机组及主机
  • {{groups['主机组名']}}{{groups.主机组名}}列出指定主机组
  • {{hostvars['主机名'].变量}}显示指定主机的fact变量
  • {{inventory_hostname}}显示受控主机在清单文件中的名称

变量过滤器

对变量进行操作,如类型转化、截取、加密等

{{变量名 | 函数}}

  • 字符串类型
    • 转换:数字转字符{{'3'}}{{3|string}}
    • 大小写 转换:{{aaa | upper}}{{aaa | lower}}
  • 数字类型
    • 转换:转整型{{'3'|int}};转浮点数{{'3'|float}}
    • 绝对值:{{-3 | abs}}
  • 列表
    • 长度:length
    • 最大值:max
    • 最小值:min
    • 求和:sum
    • 排序:sort
    • 打乱顺序显示:shuffle
  • 变量默认值:{{aa | default('bb')}}未定义时显示默认值,不含已定义但空值
  • 加密{{passwd | hash('加密算法')}}{{passwd | password_hash('加密算法')}}
    • 加密算法有md5sha1sha512

role

可以理解为playbook的脚手架,ansible-galaxy则是脚手架程序

通过分享和重用一个包含多个文件的文件夹(类似于include),实现一个完整的play

# 创建role
ansible-galaxy init role_name

# 执行role
ansible-playbook role_name.yaml

结构

role遵循特定的文件目录结果

├─ role_name.yml
└─ roles
    └─ role_name
    	├─ tasks 			# 执行的任务
        │  └─ main.yml
        ├─ files			# 需要拷贝的文件
        ├─ template			# 需要拷贝的jinja2模板
        ├─ handlers			# Handler操作
        │  └─ main.yml
        ├─ vars				# 定义变量
        │  └─ main.yml
        ├─ defaults			# 默认变量
        │  └─ main.yml
        ├─ meta				# 注释信息
        │  └─ main.yml
        ...

role_name.yml

role的主入口

- hosts
  roles:
  - role: xxx

tasks/main.yml

-name: ...
...
-name: ...

其余部分就不再一一举例,每个文件夹下的main.yml内容实际上就是把playbook中对应部分的内容。

posted @ 2024-12-24 09:48  Zang998  阅读(107)  评论(0)    收藏  举报