Fabric的安装
Fabric支持pip,easy_install或源码方式安装,很方便解决包依赖问题,(根据用户环境,自行选择pip或ease_install)
pip install fabric
easy_install fabric
源码安装不介绍了。
校验安装结果,如果导入模块没有提示异常,则说明安装成功:
root@Python_S6:~# python
Python 2.7.5+ (default, Sep 19 2013, 13:48:49)
[GCC 4.8.1] on linux2
Type "help", "copyright", "credits" or "license" for more information.
>>> import fabric
>>>
官网提供了一个简单的入门示例:
root@Python_S6:/home/chart7/test/fabric# cat farbic.py #!/usr/bin/env python # -*- coding: utf-8 -*- from fabric.api import run def host_type(): #定义一个任务函数,通过run方法实现远程执行'uname -s'命令 run('uname -s')
运行结果如果下图所示
命令引用默认文件名为fabfile.py,如果使用非默认文件名称,则需通过'-f'来制定,如:fab -H 192.168.1.23,192.168.1.24 -f host_type.py host_type,如果管理机与目标主机未配置密钥认证信任,将提示会输入目标主机对应账户登录密码。
一、fab的常用参数
fab作为Fabric程序的命令入口,提供了丰富的参数调用,命令格式如下:
fab [options]
下面列举了常用的几个参数,更多参数可使用fab -help查看.
-l,显示定义好的任务函数名;
-f,指定fab入口文件,默认入口文件名为fabfile.py;
-g,指定网关设备,比如堡垒机环境,填写堡垒机IP即可;
-H,指定目标主机,多台主机用','号分隔;
-P,以异步并行方式运行多个主机任务,默认为串行运行;
-R,指定role(角色),以角色名区分不同业务组设备;
-t,设置设备连接超时时间;
-T,设置远程主机命令执行超时时间;
-w,当命令执行失败,发出警告,而非默认终止任务
二、fabfile的编写
fab命令是结合我们编写的fabfile.py(其他文件名必须添加-f filename引用)来搭配使用,部分命令行参数可以通过相应的方法来代替,使之更加灵活,列如"-H 192.168.1.23,192.168.1.24",我们可以通过定义env.hosts来实现,如"env.hosts=[192.168.1.23,192.168.1.24]".fabfile的主体由多个自定义的任务函数组成,不同任务函数实现不同的操作逻辑,下面详细介绍
三、全局属性设定
env对象的作用是定义fabfile的全局设定,支持多个属性,包括目标主机,用户,密码角色,各属性说明如下:
@roles('webservers') def webtask(): run('/etc/init.d/nginx start') @roles('dbservers'): def dbtask(): run('/etc/init.d/mysql start') @roles('webservers','dbservers') def publictask(): run('uptime') def deploy(): execute(webtask) execute(dbtask) execute(publictask)
在命令执行fab deploy就可以实现不同角色执行不同的任务函数。
常用API
Fabric提供了一组简单但功能强大的fabric.api命令集,简单地调用这样API就能完成大部分应用场景需求,Fabric支持常用的方法及说明如下:
示例1:查看本地与远程主机信息
本示例调用local()方法执行本地命令,添加"@runs_once"修饰保证该任务函数只执行一次。调用run()方法执行远程命令,
#!/usr/bin/env python # -*- coding: utf-8 -*- from fabric.api import * env.user = 'root' env.hosts = ['192.168.1.43','192.168.1.23','192.168.1.24'] env.port = '22' env.password = '123456' @runs_once #查看本地系统信息,当有多台主机时只运行一次 def local_task(): #本地任务函数 local('uname -a') def remote_task(): with cd('/data'): #with的作用是让后面的表达式语句继承当前状态,实现cd /var && ls -l的效果 run('ls -l')
通过fab命令分别调用local_task任务函数运行效果如下图所示
结果中显示了[192.168.1.23] Executing task 'local_task',但事实上并非在主机192.168.1.23上执行任务,而是返回Fabric主机本地的'uname -a'的执行效果
调用remtoe_task任务函数的执行结果如下图所示
示例2;动态获取远程目录列表
本示例使用"@task"修饰符标志入口函数go()对外部可以,配合"@runs_once"符等待接受用户输入,最后调用worktask()任务函数实现远程命令执行,
#!/usr/bin/env python # -*- coding: utf-8 -*- from fabric.api import * env.user = 'root' env.hosts = ['192.168.1.23','192.168.1.24'] env.password = '123456' @runs_once #在主机遍历过程中,只有一台出发此函数 def input_raw(): return prompt("please input direcotry name:",default="/home") def worktask(dirname): run("ls -l %s" %dirname) @task def go(): getdirname = input_raw() worktask(getdirname)
该示例实现了一个动态输入远程目录名称,在获取目录列表的功能,由于我们只要求输入一次,再显示所有主机上该目录的列表信息,调用了一个子函数input_raw(同时配置)@runs_once修饰符来达到此目的,执行结果如下图
文件上传与执行
#!/usr/bin/env python # -*- coding: utf-8 -*- from fabric.api import * from fabric.context_managers import * from fabric.contrib.console import confirm env.hosts=['192.168.1.23','192.168.1.24'] #假如所有主机密码都不一样,可以通过env.passwords字典变量一一指定 env.passwords = { 'root@192.168.1.23:22': '123456', 'root@192.168.1.24:22': '123456', } lpackpath="/home/a.tar.gz" rpackpath="/tmp/install" @task def put_task(): run("mkdir -p /tmp/install") with settings(warn_only=True): result = put(lpackpath, rpackpath) if result.failed and not confirm("put file failed, Continue[Y/N]?"): abort("Aborting file put task!") @task def run_task(): with cd("/tmp/install"): run("tar -zxvf a.tar.gz") @task def go(): put_task() run_task()