1.管理变量
将playbook中的某些值使用变量代替,从而简化playbook的编写
总结
1.变量能够让playbook复用
2.可以给清单中的主机和主机组定义变量
3.可以使用事实和外部文件定义变量,也可以在命令行中
4.register关键字何以用于捕获命令输出
5.ansiblevault
6.ansible事实是从受管主机自动检测到的变量
1.1 ansible变量简介
变量可能包含下面这些值: 要创建的用户、要安装的软件包、 要重启的服务、 要删除的文件、 要从互联网检索的文档 。
命名变量: 变量名称必须以字母开头,并且只能含有字母、数字和下划线
示例: web_server 、 remote_file 、 file1
定义变量的三个范围级别:
全局范围: 从命令行或ansible配置设置的变量
play范围: 在play和相关结构中设置的变量
主机范围: 由清单、事实收集或注册的任务,在主机组和个别主机上设置的变量
如果多个级别上定义了相同名称的变量,优先采用级别最高的变量,窄范围优先于广范围
1.2 在playbook中定义变量
1.在playbook开头的vars块中定义变量(常见方式)
2.在外部文件定义playbook变量
1.3 在playbook中使用变量
---
- name: testvar
hosts: all
vars:
user: leo
tasks:
- name: Create user {{ user }}
user:
name: "{{ user }}"
注意
注意:
1.将变量名称放在花括号内即可
2.当变量用作开始一个值的第一元素时,必须使用引号
1.4 变量的分类
直接应用于主机的清单变量分为两大类:
1.主机变量:应用于特定主机
2.组变量:应用于一个主机组或一组主机组中的所有主机
主机变量优先于组变量,但是playbook中定义的变量比这两者更高。(范围越小优先级越高)
1.定义主机变量和组变量:
方法一(比较旧,不建议采用):
定义主机的变量:
定义主机组的变量:
定义嵌套组user变量:
这种做法使得清单文件难以处理,在同一文件中混合提供主机和变量信息,语法也过时’,不建议使用。
方法二:使用目录填充主机和组变量
定义主机和主机组变量的首选做法是:(在与清单文件或目录相同的工作目录中)
1.创建group_vars(包含组变量) 和host_vars(包含主机变量)两个目录
2.创建group_vars/servers的YAML文件,设置变量为值: key:value
3.在host_vars目录中创建名称与主机匹配的文件来存放主机变量
所以一个项目目录中包含: ansible.cfg、group_vars、host_vars、inventory、playbook.yml
从命令行覆盖变量 清单变量可以被playbook中设置的变量覆盖 两者又可通过命令行参数覆盖
方法三:使用数组作为变量
2.使用已注册变量捕获命令输出
管理员可以使用register语句捕获命令输出
---
- name: Install a Package
hosts: servera.rhel8.com
tasks:
- name: Install
yum:
name: httpd
state: installed
register: installed_result ###将安装的结果注册变量
- debug:
var: installed_result ###输出返回值
1.5 管理变量的练习
创建playbook,来安装apache并开启,使可被访问,playbook查询web服务器并确认它 已经设置好并在运行
---
- name: Configure Apache
hosts: servera.rhel8.com
vars:
web_pkg: httpd #要安装的web服务器软件包
firewall_pkg: firewalld #要安装的防火墙软件包
web_service: httpd #要管理的web服务
firewall_service: firewalld #要管理的防火墙服务
python_pkg: python3-PyMySQL #uri模块所需软件包
rule: http #要在火墙中添加的服务
tasks:
- name: Install Packages
yum:
name:
- "{{ web_pkg }}"
- "{{ firewall_pkg }}"
- "{{ python3-PyMySQL }}"
state: latest
- name: The {{ web_pkg }} started and enabled
service:
name: "{{ web_pkg }}"
enabled: true
state: started
- name: The {{ firewall_pkg }} started and enabled
service:
name: "{{ firewall_pkg }}"
enabled: true
state: started
- name: Configure index.html
copy:
content: "hello 2020"
dest: /var/www/html/index.html
- name: Firewalld permits httpd
firewalld:
service: "{{ rule }}"
permanent: true
immediate: true
state: enabled
- name: Verity the Apache
hosts: localhost
tasks:
- name: Curl servera
uri:
url: http://servera.rhel8.com
return_content: yes
status_code: 200
...
2.魔法变量
2.1 常用的魔法变量
hostvars | 包含受管主机的变量,可以用于获取另一台受管主机的变量的值 |
---|---|
group_names | 列出当前受管主机所属的所有组 |
groups | 列出清单中的所有组和主机 |
inventory_hostname | 包含清单中配置的当前受管主机的主机名称 |
2.2 魔法变量的用途
1.使用debug模块报告特定主机的hostvars的值
ansible localhost -m debug-a 'var=hostvars["servera.rhel8.com"]'
3.管理事实
事实包括:主机名称、内核版本、网络借口、IP地址等
3.1 查看主机信息
方法一:使用setup模块显示所有事实信息
ansible servera.rhel8.com -m setup
方法二:ansible_facts 系统变量名显示所有事实信息
---
- name: Fact dump
hosts: servera.rhel8.com
tasks:
- name: Print all facts
debug:
var: ansible_facts #系统变量名
...
3.2 再将事实替换为动态的值
或者使用字典的方式查询值
---
- name: Fact dump
hosts: servera.rhel8.com
tasks:
- name: Print IP and Domain Name
debug:
msg:
This IPv4 address of {{ ansible_facts.fqdn }} is {{ ansible_facts.all_ipv4_addresses }}
...
3.3 关闭事实收集,开提升执行速度
---
- name: Configure User
hosts: servera.rhel8.com
gather_facts: no #关闭事实收集
tasks:
- name: Blue User
user:
name: blue
uid: 1001
state: present
...
3.4 创建自定义事实
可以使用INI格式或者JSON格式,自定义格式不能使用ymal格式,使用最为接近的json最好
1.INI格式
[packages]
web_package=httpd
db_package=mariadb-server
[users]
user1=westos
user2=redhat
2.JSON格式
{
"packages":{
"web_package":"httpd",
"db_package":"mariadb-server"
},
"users": {
"user1":"linux",
"user2":"redhat"
}
}
3.自定义事实
mkdir /etc/ansible/facts.d
建议创建目录存放事实文件
vim custom.fact
事实文件以.fact结尾
ansible localhost -m setup
查看本机事实
自定义事实的使用方式和默认事实相同,使用变量提高playbook的复用性。
3.5 自定义事实练习
3.5.1 创建事实文件并安装httpd
1.创建自定义事实
2.将控制节点上的事实文件并拷贝到受管主机指定位置
---
- name: Install facts
hosts: serverb.rhel8.com
vars:
remote_dir: /etc/ansible/facts.d
facts_file: user.fact
tasks:
- name: Create Directory
file:
state: directory
recurse: yes
path: "{{ remote_dir }}"
- name: Install new facts
copy:
src: "{{ facts_file }}"
dest: "{{ remote_dir }}"
...
ansible serverb.rhel8.com -m setup
查看受管主机事实
3.编写主playbook,安装新的事实
---
- name: Install and start Apache
hosts: serverb.rhel8.com
tasks:
- name: Install Apache
yum:
name: "{{ ansible_facts['ansible_local']['user']['blue']['packagesi'] }}"
state: latest
- name: Start Apache
service:
name: "{{ ansible_facts['ansible_local']['user']['blue']['service'] }}"
state: "{{ ansible_facts['ansible_local']['user']['blue']['state'] }}"
enabled: "{{ ansible_facts['ansible_local']['user']['blue']['enabled'] }}"
4.查看结果
ansible serverb.rhel8.com -m command -a 'systemctl status httpd'
3.5.2 使用基本身份认证的httpd
---
- name: webserver Vars
hosts: webservers
become: yes
vars:
firewall_pkg: firewalld ###火墙的包
firewall_srv: firewalld ###火墙服务
web_pkg: httpd ##Apache的包
web_srv: httpd ##Apache的服务
ssl_pkg: mod_ssl ##Apache加密需要的插件
httpdconf_src: files/httpd.conf ##指定的httpd配置文件源
httpdconf_dest: /etc/httpd/conf/httpd.conf ##httpd配置文件存放目的地
secrets_dir: /etc/httpd/secrets ##加密目录
secrets_src: files/htpasswd ##用户加密文件
secrets_dest: "{{ secrets_dir }}/htpasswd"
web_root: /var/www/html ##httpd默认发布页面目录
name: Install Packages
yum:
name:
- "{{ firewall_pkg }}"
- "{{ web_pkg }}"
- "{{ ssl_pkg }}"
state: latest
- name: Configure service
copy:
src: "{{ httpdconf_src }}"
dest: "{{ httpdconf_dest }}"
owner: root
group: root
mode: 0644
- name: Creat secrets directory
file:
path: "{{ secrets_dir }}"
state: directory
owner: apache
group: apache
mode: 0500
- name: Create htpasswd
copy:
src: "{{ secrets_src }}"
dest: "{{ secrets_dest }}"
owner: apache
group: apache
mode: 0400
- name: Create index.html
copy:
content: "{{ ansible_facts['fqdn'] }} ({{ ansible_facts['all_ipv4_addresses'] }})\n"
dest: "{{ web_root }}/index.html"
- name: Configure furewalld service
service:
name: "{{ firewall_srv }}"
state: started
enabled: true
- name: Firewalld permits https
firewalld:
service: https
state: enabled
immediate: true
permanent: true
- name: Configure Apache Servicr
service:
name: "{{ web_srv }}"
state: started
enabled: true
- name: Test Apache
hosts: localhost
become: no
gather_facts: no
vars:
- web_user: admin
vars_files:
- vars/secret.yml
tasks:
- name: Connect Apache with Auth
uri:
url: https://serverc.rhel8.com
validate_certs: no
force_basic_auth: yes
user: "{{ web_user }}"
passwd: "{{ web_pass }}"
return_content: yes
status_code: 200
register: auth_test
- debug:
var: auth_test.content
测试: