ansible小结(十)ansible api
ansible api 与ansible-playbook api 本应该是后面放在 ansible条件与循环、ansible变量篇之后讲的,不过使用过后实在按捺不住提前写的冲动,这个插个队先讲讲API 部分。
一、ansible api
ansible api 的使用非常强大,也非常简单,只不过把模块需要使用的参数写到了脚本中,这里先来看下官方给的示例,不过同于官方的是,我这里增我将结果进行了json美化输出。
[root@361way api]# cat test_api.py #!/usr/bin/env python # coding=utf-8 import ansible.runner import json runner = ansible.runner.Runner( module_name='ping', module_args='', pattern='all', forks=10 ) datastructure = runner.run() data = json.dumps(datastructure,indent=4) print data
其输出结果如下:
注:如果主机是不通或失败的,结果将会输出到dark部分里,一个含有失败主机的结果类似如下:
{ "dark" : { "web1.example.com" : "failure message" }, "contacted" : { "web2.example.com" : 1 } }
再为看下第二个示例:
#!/usr/bin/python import ansible.runner import sys # construct the ansible runner and execute on all hosts results = ansible.runner.Runner( pattern='*', forks=10, module_name='command', module_args='/usr/bin/uptime', ).run() if results is None: print "No hosts found" sys.exit(1) print "UP ***********" for (hostname, result) in results['contacted'].items(): if not 'failed' in result: print "%s >>> %s" % (hostname, result['stdout']) print "FAILED *******" for (hostname, result) in results['contacted'].items(): if 'failed' in result: print "%s >>> %s" % (hostname, result['msg']) print "DOWN *********" for (hostname, result) in results['dark'].items(): print "%s >>> %s" % (hostname, result)
上面的示例中对主机的输出结果进行了判断,并且结果的输出进行了定制化,上面执行的结果你可以和ansible all -m command -a 'uptime' 的结果进行下比对,看下有什么不同。
上面的示例基本上都是参照官方页面进行执行的,更多用法可以通过pydoc ansible或者通过python里的help(ansible)查看。另外在多主机执行时,可以使用async(异部)方式运行。
二、ansible_playbook api
ansible_playbook api 部分在官方文档上并没有提,不过通过查看ansible模块的帮助信息可以看到其是支持的。在ansible google论坛里(需翻墙),有老外也给出里代码,其实它和执行ansible的api方式一样,只是多了个几个参数:
import ansible.playbook from ansible import callbacks from ansible import utils stats = callbacks.AggregateStats() playbook_cb = callbacks.PlaybookCallbacks(verbose=utils.VERBOSITY) runner_cb = callbacks.PlaybookRunnerCallbacks(stats, verbose=utils.VERBOSITY) pb = ansible.playbook.PlayBook( playbook="nseries.yml", stats=stats, callbacks=playbook_cb, runner_callbacks=runner_cb, check=True ) for (play_ds, play_basedir) in zip(pb.playbook, pb.play_basedirs): import ipdb ipdb.set_trace() # Can play around here to see what's going on. pb.run()
大致看了下代码,在用api的方式执行playbook的时候,playbook,stats,callbacks,runner_callbacks这几个参数是必须的。不使用的时候会报错。
arguments = [] if playbook is None: arguments.append('playbook') if callbacks is None: arguments.append('callbacks') if runner_callbacks is None: arguments.append('runner_callbacks') if stats is None: arguments.append('stats') if arguments: raise Exception('PlayBook missing required arguments: %s' % ', '.join(arguments))
playbook用来指定playbook的yaml文件
stats用来收集playbook执行期间的状态信息,最后会进行汇总
callbacks用来输出playbook执行的结果
runner_callbacks用来输出playbook执行期间的结果。但是它返回的结果太简单,我想让它详细点,如果用自定义callback的方法插入到mongo里面的话也行,或者是直接输出,但是我想所有task都执行完后,把每个task的详细信息输出到终端上,最后发现结果输出都是靠callbacks.py里的AggregateStats这个类,在每执行完一个task后,都会调用AggregateStats进行计算,汇总。
[root@361way api]# cat playbook_api.py #!/usr/bin/env python # coding=utf-8 import ansible.playbook from ansible import callbacks from ansible import utils import json stats = callbacks.AggregateStats() playbook_cb = callbacks.PlaybookCallbacks(verbose=utils.VERBOSITY) runner_cb = callbacks.PlaybookRunnerCallbacks(stats,verbose=utils.VERBOSITY) res=ansible.playbook.PlayBook( playbook='/etc/ansible/playbooks/user.yml', stats=stats, callbacks=playbook_cb, runner_callbacks=runner_cb ).run() data = json.dumps(res,indent=4) print data # 执行结果如下: [root@361way api]# python playbook_api.py PLAY [create user] ************************************************************ TASK: [create test "{{ user }}"] ********************************************** changed: [10.212.52.16] changed: [10.212.52.14] { "10.212.52.16": { "unreachable": 0, "skipped": 0, "ok": 1, "changed": 1, "failures": 0 }, "10.212.52.14": { "unreachable": 0, "skipped": 0, "ok": 1, "changed": 1, "failures": 0 } } [root@361way api]#
三、总结
从上面的例子来看,感觉作用似乎有点鸡肋。多条ansible shell 指令的执行可以写成playbook 来执行,ansbile-playbook 也可以通过include 调用子playbook ,似乎API 部分用处并不大 。咋一听深感有理,不过细究一下,
1、当需要先对前一次作任务执行的结果进行处理,并将相应的结果对应的作为输入再在一次任务传入时,这里使用api 更方便;
2、需要对结果输出进行整形时,也比较api 方便;
3、playbook 之间进行调用或都playbook比较复杂时,想要理清任务之间的关系势必累显麻烦,而通过api,从上一层任务到下一层任务之间的调用关系明子。而且playbook之间可以是平行的关系。方便小的功能模块的复用。
4、方便二次开发及和其他程序之间的耦合调用----目前感觉这条是最实用的。
You can donate through PayPal.My paypal id: itybku@139.comPaypal page: https://www.paypal.me/361way
安装完ansible
from ansible import callbacks缺少callbacks模块,请问是什么问题
你的ansible是怎么装的?通过yum源装的还是手动装的?from……import引入模块时,只会从python指定的的位置找包。
帅哥 请教下 我们是前端展示用php调用ansible-playbook,如您所说使用api的话ansible-playbook 如何传参呢?
api中只有这段,playbook='/etc/ansible/playbooks/user.yml',我们可能需要类似这样的传参:
/etc/ansible/roles/adduser_normal.yaml -e "host=192.168.1.215 username=test1 expired_day=20160624 passwd=123.com" -s',
请问如何传进来呢?
这个倒没试过,回头试试看。
@ ansible
请问 你现在有找到解决办法吗?使用api的情况下playbook怎么传值呢