1. 什么是Ansible,它有什么用?
Ansible它是个集配置管理和应用部署于一体的自动化运维工具。
应用情况:1)自动化批量部署应用;2)自动化管理配置文件;3)自动化云服务器;4)自动化持续交付。
它默认通过ssh协议管理机器。真正具有批量部署的是ansible所运行的模块,ansible只是提供一种框架。主要包括:
(1)、连接插件connection plugins:负责和被监控端实现通信;
(2)、host inventory:指定操作的主机,是一个配置文件里面定义监控的主机;
(3)、各种模块核心模块、command模块、自定义模块;
(4)、借助于插件完成记录日志邮件等功能;
(5)、playbook:剧本执行多个任务时,非必需可以让节点一次性运行多个任务。
它的优点
1. 轻量级,无需在客户端安装agent,更新时,只需在操作机上进行一次更新即可;
2. 批量任务执行可以写成脚本,而且不用分发到远程就可以执行;
3. 使用python编写,维护更简单,ruby语法过于复杂;
4. 支持sudo。
需求:
管理主机:本地电脑或者笔记本一台,安装ansible软件。
托管节点(被管理对象):一组远程服务器,已安装python2.4以上版本。如节点未开启sftp,则需要在ansible.cfg 配置文件中配置成 scp 的方式,以完成通讯。
进阶话题:chroot,lxc,jailcontainers这些本地管理选项。还有一个ansible-pull模式,反转主控关系,让托管节点,定期从中央git目录,拉取配置并实现北京连接通信。
2. 安装ansible,笔者为mac笔记本,故而仅介绍mac ox上安装方式。
brew install ansible
接着编辑(或创建)/etc/ansible/hosts (这是默认配置路径),并在其中加入一个或多个远程系统.
3. 重要的配置文件Inventory, ansible.cfg
ansible可以对同一个组的主机进行批量配置,组与主机的关系,就是通过Inventory文件的配置项确认的。
以下内容为某个简要的案例配置
[ECSServers]
主机名 ansible_ssh_host=主机ip ansible_ssh_port=(22为默认项 ) ansible_ssh_user=root
[组名:vars]
[组名A:children] # 参数都是组名,假设为组名B,children意味着组名A的变量都可以被组名B继承
动态Inventory配置
这里仅适用一个python文件的方式,展示动态Inventory配置方法,其他方法请查询网上资料。一般生产上是从cmdb,从数据库中获取动态的Inventory配置信息。然后实行配置。这里的python文件方式仅仅只是个展示。
#! /usr/bin/env python
# coding=utf-8
import json
hostip1 = ['192.168.1.15']
hostip2 = ['192.168.1.35']
group1 = 'test1'
group2 = 'test2'
hostdata = {group1:{"hosts":hostip1},group2:{"hosts":hostip2}}
print json.dumps(hostdata,indent=4)
关于ansible.cfg,查看stackflow资料。
如果是linux系统,一般可能位于以下位置:
ANSIBLE_CONFIG (an environment variable)
ansible.cfg (in the current directory)
.ansible.cfg (in the home directory)
/etc/ansible/ansible.cfg
重要的配置项有:
inventory = /etc/ansible/hosts #默认inventory文件路径
forks = 5 # 执行命令时,一次性启动的并行线程数,以便批量处理服务器的配置部署。
sudouser = root #默认情况,一般不用改,但是特殊的情况下,要改
remote_port
timeout # 连接持续多久算超时失败
log_path = xxx/xxx/xxx.log # 默认情况下,不记录日志,如果想开启日志记录,必须设置log_path的值
transport = smart # 用户通常可以这个设置为‘smart’,让playbook在需要的条件自己选择‘connection:’参数.
4. 新手任务:测试ping命令,尝试能否ping的通一组服务器.(ps:笔者只有一台可测试用)
ansible all -m ping -u root --ask-pass
all:所有主机; -m ping:测试ping命令; -u root:使用root用户; --ask-pass:要求输入密码。
扩展知识,如果不想要【--ask-pass】选项,希望免密码登录,则需要在本机设置ssh的秘钥。以下为简要步骤:
首先是原理解释图:
接着是操作步骤:参考资料
假设ansible管理主机A,要求免密登录到远程节点服务器B。
A主机上
ssh-keygen -t rsa -C 'ForECSServer'
scp id_sra.pub root@服务器ip:/root/.ssh # 笔者曾用MyMac.pub测试,莫名失败,标记该事项。
B服务器上
cd /root/.ssh
cat id_sra.pub >> authorized_keys
A主机上测试免密登录
ssh root@服务器ip # 注意,如果A主机上执行命令的用户不是root,那么必须要用root@ip的形式才能免密码登录
最后测试下ansible的免密登录,执行以下命令
ansible all -m ping -u root # ok,登录成功。
5. Ansible的ad-hoc命令
使用案例1,在服务器上执行重启命令
ansible [你的组名] -a "/sbin/reboot" -f 10
a:args的意思,参数,f:forks,指定线程数,该案例说明一次开启10个线程,重启10台节点服务器。想象下管理成百上千个服务器的情形。
使用案例2,在一台服务器上执行shell命令
ansible [你的组名] -m shell -a'echo $TERM'
-m参数指定ansible使用的模块,默认是command模块,这里指定shell,-a:参数,不提。
使用案例3,将本地文件copy到一组服务器上
ansible [你的组名] -m copy -a"src=/etc/hosts dest=/tmp/hosts"
-m:使用copy模块; -a:src和dest
使用案例4,yum和apt的支持
ansible [你的组名] -m yum -a"name=acme state=present"
使用案例5,使用git部署web-app,好方便的方法
ansible [你的组名] -m service -a"name=httpd state=started"
使用案例6,管理服务service
ansible webservers -m service -a"name=httpd state=started"
-a:args的意思,其中state可以为stated,restarted,stopped,确认已启动/重启/停止
使用案例7,将进程挂后台执行,以及查询
ansible all -m ping -B 3600 -P 0
-B 3600:表示异步后台执行,在3600秒后失败,-P :设定Poll Interval时间,默认值为15秒;
ansible all -m async_status "jid='上一条命令获得的ansible_job_id的值' "
使用案例8,file模块的使用,详见图片资料
使用案例9,cron计划任务模块的使用,详见图片资料
使用案例10,yum和get_url模块的使用,详见图片资料
参考资料截图如下:
6. Ansible 提供了7个命令,执行不同操作
ansible:核心指令,用于执行ad-hoc单条命令。类似linux的shell中执行一条指令
操作指令格式:ansible [服务器组名/服务器主机名] -m 模块 -a 参数 -f 线程数。具体查-h帮助文档
ansible-doc:用于查看模块信息。-l 列出模块,
ansible-galaxy:用于方便的下载第三方模块
ansible-lint:用于playbook语法检查的命令。
ansible-playbook:生产商最为常用的命令。
ansible-pull:pull模式,一个很重要的模式,必须学会使用。
ansible-vault:加密解密命令。重要的安全命令,导致使用复杂,但是更高的安全性。
7. Playbooks
Playbooks是 Ansible的配置,部署,编排语言.他们可以被描述为一个需要希望远程主机执行命令的方案,或者一组IT程序运行的命令集合.
一个简单的ansible例子:(ps:这是个yml文件,由你来命名,例如website.yml)
---
- hosts: webservers
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
这里主要讨论它各个模块的作用:
1)host:组名或者主机名,指定被操作的服务器
2)task:不用说了吧,任务
3)notify:位于task中,与handlers结合使用,主要用于服务重启或者服务器重启,其他场景用的很少。思考playbook的执行顺序以便理解。task中一系列任务完成后,可能任务A触发一个notify restart nginx;任务B也触发一个notfiy restart nginx。。。。最后handlers仅在触发notify的情况下,执行一次。
4)include和roles:重要的功能,主要是复用代码的思想。
5)vars:自定义变量,关于自定义变量,存在三种定义变量的方法,
方法一:在Inventory文件(默认为/etc/ansible/hosts)中设定变量,直接{{ 变量名 }}来使用
方法二:在playbook文档中,vars:模块设定,如上所述,同样通过{{ 变量名 }}来使用。
方法三:引用其他playbook文档,vars_files:模块设定,通过{{ 变量名 }}引用,如下所示。
vars_files: #
- var.yml
6)register模块,从5)小点引申而来,用来进行任务间通信,主要是任务间的信息传递,这个模块功能很重要,如下所示
该案例中,注册了一个info变量。该变量用于记录
8. Playbooks提升
1)Playbook的一个顶层结构组织方式,参考资料。注意两个入口文件,site.yml是剧本playbook的入口文件,main.yml是角色对应功能的入口文件。
production # inventory file for production servers 关于生产环境服务器的清单文件
stage # inventory file for stage environment 关于 stage 环境的清单文件
group_vars/
group1 # 这里我们给特定的组赋值
group2 # ""
host_vars/
hostname1 # 如果系统需要特定的变量, 把它们放置在这里.
hostname2 # ""
library/ #如果有自定义的模块,放在这里(可选)
filter_plugins/ # 如果有自定义的过滤插件,放在这里(可选)
site.yml # master playbook 主 playbook
webservers.yml # playbook for webserver tier Web 服务器的 playbook
dbservers.yml # playbook for dbserver tier 数据库服务器的 playbook
roles/
common/ # this hierarchy represents a "role" 这里的结构代表了一个 "role"
tasks/ #
main.yml # <-- tasks file can include smaller files if warranted
handlers/ #
main.yml # <-- handlers file
templates/ # <-- files for use with the template resource
ntp.conf.j2 # <------- templates end in .j2
files/ #
bar.txt # <-- files for use with the copy resource
foo.sh # <-- script files for use with the script resource
vars/ #
main.yml # <-- variables associated with this role
defaults/ #
main.yml # <-- default lower priority variables for this role
meta/ #
main.yml # <-- role dependencies
webtier/ # same kind of structure as "common" was above, done for the webtier role
monitoring/ # ""
fooapp/ # ""
2)变量
3)条件判断:when
4)循环
5)过滤器的使用,例如