ansible特点:
只要在主控制端部署Ansible环境
默认使用SSH协议对设备管理
轻量级,无需在客户端安装agent
基于python开发
支持api及自定义模块
alter_hosts(){
cat >> /etc/hosts <<eof
192.168.44.50 ansible
192.168.44.51 web1
192.168.44.52 web2
eof
}
stop_firewalld(){
systemctl stop firewalld
sed -ri '/^SELINUX=/c SELINUX=disabled' /etc/sysconfig/selinux
setenforce 0
systemctl disable firewalld
systemctl status firewalld
}
ssh-keygen
ssh-copy-id web1
ssh-copy-id web2
安装ansible
yum -y install ansible
=====================Ad-Hoc===================================
ad hoc 临时的,在ansible中是指需要快速执行,并且不需要保存的命令。其实就是
执行简单的命令——一条命令。对于复杂的命令则为 playbook。
列出ansible支持的模块:
ansible-doc命令:
获取模块列表,及模块使用格式;
-l:获取列表
-s module_name:获取指定模块的使用信息
[root@ansible ~]# ansible-doc -l
[root@ansible ~]# ansible-doc yum
[root@ansible ~]# ansible-doc -s yum
a.在执行 /usr/bin/ansible 时,默认是以当前用户的身份去执行这个命令.如果想以指定
的用户执行 /usr/bin/ansible, 请添加 “-u username”选项,如下:
$ ansible webs -a "/usr/bin/foo" -u username
b.[root@localhost ~]# ansible webs -m shell -a 'echo $TERM'
web1 | SUCCESS | rc=0 >>
xterm
web2 | SUCCESS | rc=0 >>
xterm
c.复制文件
ansible webs -m copy -a "src=/etc/hosts dest=/tmp/hosts"
d.Ansible 提供对 yum 和 apt 的支持.这里是关于 yum 的示例
ansible webs -m yum -a "name=acme state=present"
e.使用 file 模块也可以创建目录,与执行 mkdir -p 效果类似 (webs要有alice用户)
ansible webs -m file -a "dest=/path/to/c mode=755 owner=mdehaan group=mdehaan state=directory"
f.使用 ‘user’ 模块可以方便的创建账户,删除账户,或是管理现有的账户
ansible webs -m user -a "name=foo password=<root>"
g.webs上重启某个服务(reloaded, restarted, started, stopped)
ansible webservers -m service -a "name=httpd state=stopped"
=========================facts=======================================
facts组件是Ansible用于采集被管理主机信息的一个功能,可以使用setup模块查看主机的有的facts信息。
[root@localhost ~]# ansible web1 -m setup -a 'filter=ansible_all_ipv4_addresses'
web1 | SUCCESS => {
"ansible_facts": {
"ansible_all_ipv4_addresses": [
"192.168.44.51",
"192.168.44.66"
]
},
"changed": false
}
查看主机内存信息
[root@ansible ansible]# ansible web1 -m setup -a 'filter=ansible_*_mb'
查看地接口为eth0-2的网卡信息
[root@ansible ansible]# ansible web1 -m setup -a 'filter=ansible_ens33'
========================playbook=====================================
playbook的基础组件:
name
定义playbook或者task的名称
hosts
playbook中的每一个paly的目的都是为了让某个或某些以某个指定用户的身份执行任务。
hosts用于指定要执行指定任务的主机,其可以是一个或多个由冒号分割主机组。与命令模式
下的ansible匹配规则一样
user
remote_user则用于指定远程主机上的执行任务的用户,也可以使用user
tasks
任务列表
play的主体部分是task list. task list中的各任务按次序逐个在hosts中指定的所有主
机上执行,即在所有主机上完成第一个任务后再开始第二个。
======================================Variables=================================
Variables:
类型:
内建变量
自定义变量
变量调用:
{{ var_name }}
内建变量
由facts组件提供,可以使用setup模块查询
[root@ansible ansible]# ansible web1 -m setup
自定义变量
1.用命令行传递参数
为了使Playbook更灵活、通用性更强,允许用户在执行的时候传入变量的值,这个时候就需要用到“额外变量”。
定义命令行变量
在release.yml文件里,hosts和user都定义为变量,需要从命令行传递变量值。
---
- hosts: '{{ hosts }}'
remote_user: '{{ user }}'
tasks:
- ...
使用命令行变量
在命令行里面传值的方法:
#ansible-playbook e33_var_in_command.yml --extra-vars "hosts=web user=root"
还可以用json格式传递参数:
ansible-playbook e33_var_in_command.yml --extra-vars "{'hosts':'vm-rhel7-1', 'user':'root'}"
还可以将参数放在文件里面:
ansible-playbook e33_var_in_command.yml --extra-vars "@vars.json"
2.在hosts Inventory中为每个主机定义专用变量值
向不同的主机传递不同的变量:
IP/HOSTNAME variable_name=value
向组内的所有主机传递相同的变量:
[groupname:vars]
variable_name=value
3.在playbook中定义
vars:
- var_name: value
- var_name: value
通过vars_files关键字引入变量文件:
- hosts: all
remote_user: root
vars:
favcolor: blue
vars_files:
- /vars/external_vars.yml
- /vars/nginx_vars.yml
示例文件:
# vim /vars/nginx_vars.yml
http_port: 80
server_name: localhost
cert_file: /etc/nginx/ssl/nginx.crt
key_file: /etc/nginx/ssh/nginx.key
conf_file: /etc/nginx/conf/default.conf
注意:变量文件不一定以.yml结尾,变量冒号后面必须有空格
4.Inventory使用参数:
用于定义ansible远程连接目标主机时使用的属性,而非传递给playbook的变量;
ansible_ssh_host
ansible_ssh_port
ansible_ssh_user
ansible_ssh_pass
ansible_sudo_pass
…
5.在角色调用时传递
roles:
- { role: ROLE_NAME, var: value, …}
6.set_fact自定义facts变量:
set_fact模块可以自定义facts,这些自定义的facts可以通过template或者变量的方式
在playbook中使用。如果你想要获取一个进程使用的内存的百分比,则必须通过set_fact来进行计算之后得出其值,并将其值在playbook中引用。
下面是一个配置mysql innodb buffer size的示例:
- name: Configure MySQL
hosts: mysqlservers
tasks:
- name: install MySql
yum: name=mysql-server state=installed
- name: Calculate InnoDB buffer pool size
set_fact: innodb_buffer_pool_size_mb="{{ ansible_memtotal_mb / 2 }}"
- name: Configure MySQL
template: src=templates/my.cnf dest=/etc/my.cnf owner=root group=root mode=0644
notify: restart mysql
- name: Start MySQL
service: name=mysqld state=started enabled=yes
handlers:
- name: restart mysql
service: name=mysqld state=restarted
my.cnf的配置示例:
# {{ ansible_managed }}
[mysqld]
datadir=/var/lib/mysql
socket=/var/lib/mysql/mysql.sock
# Disabling symbolic-links is recommended to prevent assorted
security risks
symbolic-links=0
# Configure the buffer pool
innodb_buffer_pool_size = {{ innodb_buffer_pool_size_mb|int }}M
[mysqld_safe]
log-error=/var/log/mysqld.log
pid-file=/var/run/mysqld/mysqld.pid
所有变量都可以在playbook或者jinja2模板中通过{{ varname }}中使用。另外,
当变量和jinja2的管道配合起来的时候能提供各种灵活的条件判断和变量处理。具体看下边两个例子。
如果第一个任务执行失败了才会执行第二个任务,可以这么写:
[root@ansible ansible]# cat wait.yml
---
- name: test
hosts: web1
tasks:
- shell: /usr/bin/ls
register: result
ignore_errors: True
- debug: msg="it failed"
when: result|failed
变量的优先级
• -e 命令行指定的最高
• inventory文件定义的变量次之,其实inventory文件也分全局,group级别的和hosts级别的变量定义
• fact变量次之
• 角色的default变量优先级最低
===========================ansible模版======================
最简示例:
[root@ansible ansible]# cat wait.yml
- name: user
hosts: web1
user: root
vars:
- user: "wing"
- say: "wingfile"
tasks:
- name: task {{ user }}
template: src=/root/testfile dest=/root/{{ say }}
[root@ansible ansible]# cat /root/testfile
hello
i love {{ user }}
[root@ansible ansible]# ansible-playbook wait.yml
===============================playbook===========
示例1:简单playbook
文档以---开头,没有也可以
[root@master ~]# cd /etc/ansible/
[root@master ansible]# vim test.yml //固定后缀为yml
---
- hosts: webs
user: root
- name: playbook_test
shell: touch /tmp/playbook.txt
tags: suibian
核心元素:
Playbooks
Variables #变量元素,可传递给Tasks/Templates使用;
Tasks #任务元素,由模块定义的操作的列表,即调用模块完成任务;
Templates #模板元素,使用了模板语法的文本文件,可根据变量动态生成配置文件;
Handlers #处理器元素,通常指在某事件满足时触发的操作;
Roles #角色元素
参数解释:
hosts参数指定了对哪些主机进行操作;
user参数指定了使用什么用户登录远程主机操作;
tasks指定了一个任务,其下面的name参数同样是对任务的描述,在执行过程中会打印出来。
tags:给指定的任务定义一个调用标识,形式如下
- name:cd NAME
module: arguments
tags: TAG_ID
cd /etc/ansible
vim test.yaml
---
- hosts: webs
vars:
http_port: 80
max_clients: 200
remote_user: root
tasks:
- name: ensure apache is at the latest version
yum: pkg=httpd state=latest
- name: write the apache config file
template: src=/srv/httpd.j2 dest=/etc/httpd.conf
notify:
- restart apache
- name: ensure apache is running
service: name=httpd state=started
handlers:
- name: restart apache
service: name=httpd state=restarted
语法检测:
[root@ansible ansible]# ansible-playbook --syntax-check test.yml
playbook: test.yml
测试运行
[root@master ansible]#ansible-playbook -C /path/to/playbook.yaml
可以使用如下参数:
--list-hosts
--list-tasks
--list-tags
运行Playbook:
[root@master ansible]# ansible-playbook test.yml
只运行指定标记的任务:-t tags
[root@ansible ansible]# ansible-playbook -t 标记名称 test.yml
跳过某一个被标记的任务:--skip-tags=SKIP_TAGS
[root@ansible ansible]# ansible-playbook --skip-tags=标记名称 test.yml
从某一个任务开始往下运行:--start-at-task 任务名称
[root@ansible ansible]# ansible-playbook --start-at-task "start httpd service" test.yml
批量上传公钥
常用选项:
Options: (= is mandatory)(= 后面的参数是强制要有的)
- exclusive [default: no]: 是否移除 authorized_keys 文件中其它非指定 key
= key: SSH public key(s) 可以是字符串或 url,如:https://github.com/username.keys
- key_options [Default: None]: 附加到 key 中的字符串,该字符串会加到 key 的开头
- path [Default: (homedir)+/.ssh/authorized_keys]: 指定 authorized_keys 文件存放的位置
- state (Choices: present, absent) [Default: present]: present 添加指定 key 到 authorized_keys
文件中;absent 从 authorized_keys 文件中移除指定 key
= user: 指定修改远端服务器上哪个用户的 authorized_keys
- manage_dir (Choices: yes, no) [Default: yes]: 指定模块是否应该管理 authorized key 文件所在的目录。
如果设置为 yes,模块会创建目录,以及设置一个已存在目录的拥有者和权限。如果通过 path 选项,重新指定
了一个 authorized key 文件所在目录,那么应该将该选项设置为 no
[root@localhost ~]# grep -v '#' /etc/ssh/ssh_config
StrictHostKeyChecking no
[root@localhost ~]# ansible webs --list-hosts
hosts (2):
10.0.0.21
10.0.0.22
法一
[root@localhost ~]# cat push.ssh.ymal
---
- hosts: webs
remote_user: root
tasks:
- name: Set authorized key in alternate location
authorized_key:
user: root
state: present
key: "{{ lookup('file', '/root/.ssh/id_rsa.pub') }}"
#path: /etc/ssh/authorized_keys/charlie \\指定远端存储的路径
# manage_dir: False
[root@localhost ~]# ansible-playbook push.ssh.ymal -k
法二
[root@localhost ~]# ansible webs -m authorized_key -a "user=root key='{{ lookup('file','/root/.ssh/id_rsa.pub') }}'" -k
网友评论