Ansible基础配置和企业级项目实用案例
Ansible基础模块和功能
自动化运维工具
运维发展历程:手动 --> 标准化 --> 工具化 --> 自动化 --> 智能化
自动化系统安装工具:bare metal:pxe、cobbler
批量Configuration配置工具:puppet (ruby)、saltstack (python)、chef、cfengine等
批量Command and Control工具:fabric、func
自动化批量运维流程:在调度器上下线一批主机(标记为维护模式)--> 关闭服务 --> 部署新版本 --> 启动服务 --> 在调度器上启用这一批主机;
ansible:可实现批量Configuration、Command and Control部署和管理的自动化运维工具
运维工个的分类:(根据客户端和调度器端是否都要配置该工具)
- agent:puppet, func, ...
- agentless(ssh,):ansible, fabric
Ansible基本配置和架构
Ansible特性:
- 模块化:调用特定的模块,完成特定任务;
- 基于Python语言实现,由Paramiko, PyYAML和Jinja2三个关键模块;
- 部署简单:agentless;
- 支持自定义模块;
- 支持playbook:剧本执行多个任务时,非必需可以让节点一次性运行多个任务。;
-
连接插件connection plugins:负责和被监控端实现通信;
-
host inventory:指定操作的主机,是一个配置文件里面定义监控的主机;
-
各种模块核心模块、command模块、自定义模块;借助于插件完成记录日志邮件等功能;
- 幂等性;
ansible安装:epel源, ansible包
配置文件:/etc/ansible/ansible.cfg
主机清单:/etc/ansible/hosts
主程序:
- ansible
- ansible-playbook
- ansible-doc
ansible的简单使用格式:
ansible HOST-PATTERN -m MOD_NAME -a MOD_ARGS -f FORKS -C -u USERNAME -c CONNECTION
其中HOST-PATTERN主机匹配可用all(全部),IP地址匹配或hosts组匹配等
FORKS 指每次批量执行主机数量,默认5
ansible的常用模块
获取主机列表:ansible all --list-host(s)
主机状态检查:ansible 主机匹配 -m ping (状态正常为绿色,否则为红色)
获取模块列表:ansible-doc -l
获取某模块使用选项和用法:ansible-doc -s module
command模块:在远程主机运行命令;
例:chdir 执行命令前切换某个目录
creates
removes与creates相反,存在则执行,删除,不存在则不执行
shell模块:在远程主机在shell进程下运行命令,支持shell特性,如管道等,command不支持管道等操作;例如下:
excutable=PATH 可指定运行命令时的shell类型
shell模块很多与command相似。
group模块 管理组账号
例:system默认为no,state有present与absent(缺席)两种状态。黄色表示发生改变
user模块:管理用户账号,可用选项很多,常用选项如下:
- *name=
- system=
- uid=
- shell=
- group=
- groups=
- comment=
- home=
- generate_ssh_key
- generate_ssh_key
copy模块: Copies files to remote locations.
用法:
(1) src= dest=
(2) content= dest= (直接生成文件内容)
owner, group, mode
file模块: Sets attributes of files只能创建文件,不能像copy那样生成文件内容
用法:
(1) 创建链接文件:*path= src= state=link
(2) 修改属性:path= owner= mode= group=
(3) 创建目录:path= state=directory
state状态值:file、directory、link、hard、touch、touch、absent
fetch模块:Fetches a file from remote nodes
get_url模块:Downloads files from HTTP, HTTPS, or FTP to node
cron 模块:Manage cron.d and crontab entries.
- minute=
- day=
- month=
- weekday=
- hour=
- *job=
- *name=
- state= present or absent
hostname模块:Manage hostname
name=
pip模块:Manages Python library dependencies.
yum模块:Manages packages with the `yum' package manager
- name=:程序包名称,可以带版本号;
- state= present, latest,installed(安装)、absent,removed(卸载)
其他包管理工具apt(debian)、zypper(suse)、dnf(fedora)、prm、apk等
service模块:管理服务
- *name=
- state=started、stopped、restarted
- enabled=
- runlevel=
git模块:Deploy(部署) software (or files) from git checkouts
- repo=
- dest=
- version=
setup模块:获取各主机facts的各个变量、网络配置、硬件信息等 ansible HOST -m setup ,如:
Ansible自动化运维进阶
Playbook命令文件和使用方法
Playbook:YAML(可读性高,用来表达数据序列的格式)格式,任务(task)
可以用YAML脚本批量执行计划好的命令,从而实现运维自动化,避免重复运维配置等工作
基本数据结构:标量、数组、关联数组
Playbook的核心元素:
- Hosts:主机
- Tasks:任务列表
- Variables
- Templates:包含了模板语法的文本文件;
- Handlers:由特定条件触发的任务;
Roles(非核心)
playbook的基础组件:
- Hosts:运行指定任务的目标主机;
remoute_user: 在远程主机上执行任务的用户;
sudo_user:
- tasks:任务列表
模块,模块参数;
格式:(1) action: module arguments
(2) module: arguments
注意:shell和command模块后面直接跟命令,而非key=value类的参数列表;
(1) 某任务的状态在运行后为changed时,可通过“notify”通知给相应的handlers;
(2) 任务可以通过tags打标签,而后可在ansible-playbook后使用-t进行调用,且多个任务可使用同一个标签,一个任务也可用多个标签;
playbook的使用方法:
(1) 测试
- ansible-playbook --check 或 -C file.yml 只检测可能会发生的改变,但不真正执行操作;
- ansible-playbook --list-hosts file.yaml 查看任务主机
- ansible-playbook --list-tasks file.yaml 查看所有任务
- ansible-playbook --syntax-check file.yml 检查配置文件语法是否有错
(2) 运行 ansible-playbook file.yaml
简单示例:
handlers:任务,在特定条件下触发;接收到其它任务的通知时被触发;
notify: HANDLER TASK NAME
- hosts: webservers remote_user: root tasks: - name: install nginx yum: name=nginx state=latest - name: start nginx service : name=nginx enabled=true state=started - hosts: webservers remote_user: root tasks: - name: install redis yum : name=redis state=latest - name: connfig redis copy: src=/date/redis.conf dest=/etc/redis.conf owner=redis group=root tags: confredis notify: restartredis - name: start redis service : name=redis state=started tags: startredis handlers: - name: restartredis service : name=redis state=restartes
variables:
(1) facts:可直接调用;
注意:可使用setup模块直接获取目标主机的facters;
(2) 用户自定义变量:
- (a) ansible-playbook命令的命令行中的 -e VARS(如,“packname=tree”), --extra-vars=VARS
- (b) 在playbook中定义变量的方法:
vars:
- var1: value1
- var2: value2
变量引用:{{ variable }}
(3) 通过roles传递变量;
(4) Host Inventory
(a) 用户自定义变量
(i) 向不同的主机传递不同的变量;IP/HOSTNAME varaiable=value var2=value2
(ii) 向组中的主机传递相同的变量;[groupname:vars] variable=value,直接在/etc/ansible/hosts的主机下定义组变量
(b) invertory参数:用于定义ansible远程连接目标主机时使用的参数,而非传递给playbook的变量,在ansible的hosts组的主机后定义;
- ansible_ssh_host =
- ansible_ssh_port =
- ansible_ssh_user =
- ansible_ssh_pass =
- ansbile_sudo_pass =
template模块:基于模板方式生成一个文件复制到远程主机
- *src=
- *dest=
- owner=
- group=
- mode=
模板:templates为文本文件,嵌套有脚本(使用模板编程语言Jinja2编写)
示例: (用ansible-playbook调用此文件,ansible不能直接用templates调用)
- hosts: websrvs remote_user: root tasks: - name: install nginx yum: name=nginx state=present - name: install conf file template: src=files/nginx.conf.jj2 dest=/etc/nginx/nginx.conf notify: restart nginx tags: instconf - name: start nginx service service: name=nginx state=started handlers: - name: restart nginx service: name=nginx state=restarted
模板配置文件 :nginx.conf.jj2
worker_processes {{ ansible_processor_vcpus }}; listen {{ http_port }};
条件测试:复杂环境的批量判断操作
when语句:在task中使用,jinja2的语法格式
tasks: - name: install conf file to centos7 template: src=files/nginx.conf.c7.jj2 dest=/etc/nginx/nginx.conf when: ansible_distribution_major_version == "7" - name: install conf file to centos6 template: src=files/nginx.conf.c6.jj2 dest=/etc/nginx/nginx.conf when: ansible_distribution_major_version == "6"
循环:迭代,需要重复执行的任务;
对迭代项的引用,固定变量名为”item“,而后,要在task中使用with_items给定要迭代的元素列表;例:
- name: install some packages yum: name={{ item }} state=latest with_items: - nginx - memcached - php-fpm
- name: add some groups group: name={{ item }} state=present with_items: - group11 - group12 - group13
- name: add some users
user: name={{ item.name }} group={{ item.group }} state=present
with_items:
- { name: 'user11', group: 'group11' }
- { name: 'user12', group: 'group12' }
- { name: 'user13', group: 'group13' }
就是利用item和with_items相当与一个数组,一次完成多个重复的、属性相同指令,加版本号的方法也类似,如下:
- hosts: webserves remote_user: root vars: - jdk_version: 1.8.0 tasks: - name : install { { item } } package yum : name= {{ item }} state =installed with_items: - nginx - java-{ { jdk_version }}-openjdk - tomcat - tomcat-webapps - tomcat-docs_webapp - tomcat-admin-webapps - name : config tomcat copy : src ={{ item.file }} dest={{ item.conf }} with_items: - { file: '/data/tomcat-users.xml', conf: '/etc/tomcat-user.xml' } - { file: '/data/server.xml', conf: '/etc/server.xml' }
角色(roles):分类组织调用各个应用各个模块
角色集合:/etc/ansible/roles/下可有多个按应用分类的角色,如:
- mysql/
- httpd/
- nginx/
- memcached/
每个角色,以特定的层级目录结构进行组织:如 mysql/下
- files/ :存放由copy或script模块等调用的文件;
- templates/:template模块查找所需要模板文件的目录;
- tasks/:至少应该包含一个名为main.yml的文件;其它的文件需要在此文件中通过include进行包含;
- handlers/:至少应该包含一个名为main.yml的文件;其它的文件需要在此文件中通过include进行包含;
- vars/:至少应该包含一个名为main.yml的文件;其它的文件需要在此文件中通过include进行包含;
- meta/:至少应该包含一个名为main.yml的文件,定义当前角色的特殊设定及其依赖关系;其它的文件需要在此文件中通过include进行包含;
- default/:设定默认变量时使用此目录中的main.yml文件;
在playbook调用角色方法1:
- hosts: webservers
remote_user: root
roles:
- mysql
- memcached
- nginx
在playbook调用角色方法2:传递变量给角色
- hosts:
remote_user:
roles:
- { role: nginx, username: nginx等变量 }
键role用于指定角色名称;后续的k/v用于传递变量给角色;
还可以基于条件测试实现角色调用;
roles:
- { role: nginx, when: "ansible_distribution_major_version == '7' " }
关于更多ansible的介绍和查看ansible官网:http://www.ansible.com.cn