官网示例(python3)

 

说明:

在学习2.0 api的过程中遇到了一个坑,最新版的ansible(2.4)和2.3版本api引用时发生了变化,本文主要使用2.3 api进行操作,2.4只做分析

 

ansible api (ansible2.4)

#!/usr/bin/env python
#-*-coding:utf-8 -*-

import json
from collections import namedtuple
from ansible.parsing.dataloader import DataLoader
from ansible.vars.manager import VariableManager      #这里用的ansbile 2.4
from ansible.inventory.manager import InventoryManager     #这里用的ansible 2.4
from ansible.playbook.play import Play
from ansible.executor.task_queue_manager import TaskQueueManager
from ansible.plugins.callback import CallbackBase


#自定义运行callback,即运行完api后调用v2_runner_on_ok函数,打印host和result
class ResultCallback(CallbackBase):
    def v2_runner_on_ok(self, result, **kwargs):
      
     
#result所包含属性(_check_key..可用dir方法查看所包含的所有属性)
     host = result._host print(json.dumps({host.name: result._result}, indent=4)) #创建一个Options类型,列表里为属性,这里用来设置ansible执行时的参数,如ask_pass,sudo_user等等(namedtuple创建一个和tuple类似的对象,而且对象拥有可以访问的属性) Options = namedtuple('Options', ['connection', 'module_path', 'forks', 'become', 'become_method', 'become_user', 'check', 'diff']) # initialize needed objects loader = DataLoader() #可以通过options.(属性) 的方法去获取属性的值,如获取connection的值可以直接写成options.connection options = Options(connection='local', module_path='/path/to/mymodules', forks=100, become=None, become_method=None, become_user=None, check=False,diff=False) passwords = dict(vault_pass='secret') # Instantiate our ResultCallback for handling results as they come in results_callback = ResultCallback() # 加载inventory变量,这里的sources的值可以是hosts文件,也可以是ip列表,如['xxx.xxx.xx.x','xx.xx.xx.xx'] inventory = InventoryManager(loader=loader, sources=['/etc/ansible/hosts']) #管理变量的类,包括主机、组、扩展等变量 variable_manager = VariableManager(loader=loader, inventory=inventory) # 创建一个任务 play_source = dict( name = "Ansible Play", hosts = 'test',        #这里写在上面inventory里设置的sources所指定的文件里的组名 gather_facts = 'no', tasks = [ dict(action=dict(module='shell', args='ls'), register='shell_out'), dict(action=dict(module='debug', args=dict(msg='{{shell_out.stdout}}'))) ] ) play = Play().load(play_source, variable_manager=variable_manager, loader=loader)   # actually run it tqm = None try: tqm = TaskQueueManager(        #详细参数看源码 inventory=inventory,             variable_manager=variable_manager,      loader=loader,                #ansible.parsing.dataloader模块创建,用于数据解析 options=options,               #存放各类配置信息,ansible执行时的各种参数 passwords=passwords,             #登录密码 stdout_callback=results_callback,   #回调函数,调用最上面定义的callback函数 ) result = tqm.run(play) finally: if tqm is not None: tqm.cleanup()

 

ansible2.3 api

#!/usr/bin/env python
# -*-coding:utf-8 -*-

import json
from collections import namedtuple
from ansible.parsing.dataloader import DataLoader
from ansible.vars import VariableManager
from ansible.inventory import Inventory
from ansible.playbook.play import Play
from ansible.executor.task_queue_manager import TaskQueueManager
from ansible.plugins.callback import CallbackBase


# 自定义运行callback,即运行完api后调用v2_runner_on_ok函数,打印host和result
class ResultCallback(CallbackBase):
    def v2_runner_on_ok(self, result, **kwargs):      #执行完会生成一个result结果,通过result.__ditct__可打印所有的方法,其中_result和_host方法为主要内容

        host = result._host
        print(json.dumps({host.name: result._result}, indent=4))

# 创建一个Options类型,列表里为属性,这里用来设置ansible执行时的参数,如ask_pass,sudo_user等等(namedtuple创建一个和tuple类似的对象,而且对象拥有可以访问的属性)
Options = namedtuple('Options',
                     ['connection', 'module_path', 'forks', 'become', 'become_method', 'become_user', 'check', 'diff'])

# initialize needed objects
loader = DataLoader()

# 可以通过options.(属性) 的方法去获取属性的值,如获取connection的值可以直接写成options.connection
options = Options(connection='local', module_path='/path/to/mymodules', forks=100, become=None, become_method=None,
                  become_user=None, check=False, diff=False)
passwords = dict(vault_pass='secret')

# Instantiate our ResultCallback for handling results as they come in
results_callback = ResultCallback()

# 管理变量的类,包括主机、组、扩展等变量
variable_manager = VariableManager()

# 加载inventory变量,这里的sources的值可以是hosts文件,也可以是ip列表,如['xxx.xxx.xx.x','xx.xx.xx.xx']
inventory = Inventory(loader=loader, variable_manager=variable_manager,host_list='/etc/ansible/hosts')


# 创建一个任务
play_source = dict(
    name="Ansible Play",
    hosts='test',
gather_facts = 'no',
               tasks = [
    dict(action=dict(module='shell', args='ls'), register='shell_out'),
    dict(action=dict(module='debug', args=dict(msg='{{shell_out.stdout}}')))
]
)
play = Play().load(play_source, variable_manager=variable_manager, loader=loader)

# actually run it
tqm = None
try:
    tqm = TaskQueueManager(
    inventory = inventory,
    variable_manager = variable_manager,
    loader = loader,
    options = options,
    passwords = passwords,
    stdout_callback = results_callback,
    )
    result = tqm.run(play)
finally:
    if tqm is not None:
        tqm.cleanup()

 

ansible-playbook api调用方式(ansible 2.3.1)

#!/usr/bin/env python

import json
from collections import namedtuple
from ansible.parsing.dataloader import DataLoader
from ansible.vars import VariableManager
from ansible.inventory import Inventory
from ansible.executor.playbook_executor import PlaybookExecutor      #引入executor模块

#用来加载解析yml文件或者json内容 loader
= DataLoader() variable_manager = VariableManager()
# 根据inventory加载对应变量,此处host_list参数可以有两种格式:
# 1: hosts文件(需要),
# 2: 可以是IP列表,此处使用IP列表
inventory = Inventory(loader=loader, variable_manager=variable_manager,host_list='/etc/ansible/hosts')  #这里可通过分析源码得到参数
variable_manager.set_inventory(inventory)
passwords
=None
#初始化
Options = namedtuple('Options',
                     ['connection',
                      'remote_user',
                      'ask_sudo_pass',
                      'verbosity',
                      'ack_pass',
                      'module_path',
                      'forks',
                      'become',
                      'become_method',
                      'become_user',
                      'check',
                      'listhosts',
                      'listtasks',
                      'listtags',
                      'syntax',
                      'sudo_user',
                      'sudo'])
#初始化需要的对象 options
= Options(connection='smart', remote_user='root', ack_pass=None, sudo_user='root', forks=100, sudo='yes', ask_sudo_pass=False, verbosity=5, module_path=None, become=True, become_method='sudo', become_user='root', check=None, listhosts=None, listtasks=None, listtags=None, syntax=None) # 多个yaml文件则以列表形式 playbook = PlaybookExecutor(playbooks=['/etc/ansible/test.yml'],inventory=inventory, variable_manager=variable_manager, loader=loader,options=options,passwords=passwords) result = playbook.run() print (result)                #ansible-playbook模块没有与callback模块共用

 

 test.yml

[root@bogon ~]# cat test.yml 
---
- hosts: 10.10.10.11
  gather_facts: false
  sudo: True
  remote_user: root
  tasks:
    - shell: ifconfig
      register: output
    - debug: var=output.stdout
[root@bogon ~]# 

 

执行结果:

[root@bogon ~]# python aa.py 

PLAY [10.10.10.11] ****************************************************************************************************************************************************************************

TASK [command] ********************************************************************************************************************************************************************************
changed: [10.10.10.11]
{"_ansible_parsed": true, "stderr_lines": [], "cmd": "ifconfig", "end": "2018-02-01 14:49:00.920984", "_ansible_no_log": false, "stdout": "ens32: flags=4163<UP,BROADCAST,RUNNING,MULTICAST>  mtu 1500\n        inet 10.10.10.11  netmask 255.255.255.0  broadcast 10.10.10.255\n        inet6 fe80::250:56ff:fe93:e5c6  prefixlen 64  scopeid 0x20<link>\n        ether 00:50:56:93:e5:c6  txqueuelen 1000  (Ethernet)\n        RX packets 10048045  bytes 1340025577 (1.2 GiB)\n        RX errors 0  dropped 0  overruns 0  frame 0\n        TX packets 9885546  bytes 975436242 (930.2 MiB)\n        TX errors 0  dropped 0 overruns 0  carrier 0  collisions 0\n\nlo: flags=73<UP,LOOPBACK,RUNNING>  mtu 65536\n        inet 127.0.0.1  netmask 255.0.0.0\n        inet6 ::1  prefixlen 128  scopeid 0x10<host>\n        loop  txqueuelen 1  (Local Loopback)\n        RX packets 5214029  bytes 417704433 (398.3 MiB)\n        RX errors 0  dropped 0  overruns 0  frame 0\n        TX packets 5214029  bytes 417704433 (398.3 MiB)\n        TX errors 0  dropped 0 overruns 0  carrier 0  collisions 0\n\nvirbr0: flags=4099<UP,BROADCAST,MULTICAST>  mtu 1500\n        inet 192.168.122.1  netmask 255.255.255.0  broadcast 192.168.122.255\n        ether 52:54:00:b7:6f:ef  txqueuelen 1000  (Ethernet)\n        RX packets 0  bytes 0 (0.0 B)\n        RX errors 0  dropped 0  overruns 0  frame 0\n        TX packets 0  bytes 0 (0.0 B)\n        TX errors 0  dropped 0 overruns 0  carrier 0  collisions 0", "changed": true, "rc": 0, "start": "2018-02-01 14:49:00.908486", "stderr": "", "delta": "0:00:00.012498", "invocation": {"module_args": {"warn": true, "executable": null, "_uses_shell": true, "_raw_params": "ifconfig", "removes": null, "creates": null, "chdir": null}}, "stdout_lines": ["ens32: flags=4163<UP,BROADCAST,RUNNING,MULTICAST>  mtu 1500", "        inet 10.10.10.11  netmask 255.255.255.0  broadcast 10.10.10.255", "        inet6 fe80::250:56ff:fe93:e5c6  prefixlen 64  scopeid 0x20<link>", "        ether 00:50:56:93:e5:c6  txqueuelen 1000  (Ethernet)", "        RX packets 10048045  bytes 1340025577 (1.2 GiB)", "        RX errors 0  dropped 0  overruns 0  frame 0", "        TX packets 9885546  bytes 975436242 (930.2 MiB)", "        TX errors 0  dropped 0 overruns 0  carrier 0  collisions 0", "", "lo: flags=73<UP,LOOPBACK,RUNNING>  mtu 65536", "        inet 127.0.0.1  netmask 255.0.0.0", "        inet6 ::1  prefixlen 128  scopeid 0x10<host>", "        loop  txqueuelen 1  (Local Loopback)", "        RX packets 5214029  bytes 417704433 (398.3 MiB)", "        RX errors 0  dropped 0  overruns 0  frame 0", "        TX packets 5214029  bytes 417704433 (398.3 MiB)", "        TX errors 0  dropped 0 overruns 0  carrier 0  collisions 0", "", "virbr0: flags=4099<UP,BROADCAST,MULTICAST>  mtu 1500", "        inet 192.168.122.1  netmask 255.255.255.0  broadcast 192.168.122.255", "        ether 52:54:00:b7:6f:ef  txqueuelen 1000  (Ethernet)", "        RX packets 0  bytes 0 (0.0 B)", "        RX errors 0  dropped 0  overruns 0  frame 0", "        TX packets 0  bytes 0 (0.0 B)", "        TX errors 0  dropped 0 overruns 0  carrier 0  collisions 0"]}

TASK [debug] **********************************************************************************************************************************************************************************
ok: [10.10.10.11] => {
    "output.stdout": "ens32: flags=4163<UP,BROADCAST,RUNNING,MULTICAST>  mtu 1500\n        inet 10.10.10.11  netmask 255.255.255.0  broadcast 10.10.10.255\n        inet6 fe80::250:56ff:fe93:e5c6  prefixlen 64  scopeid 0x20<link>\n        ether 00:50:56:93:e5:c6  txqueuelen 1000  (Ethernet)\n        RX packets 10048045  bytes 1340025577 (1.2 GiB)\n        RX errors 0  dropped 0  overruns 0  frame 0\n        TX packets 9885546  bytes 975436242 (930.2 MiB)\n        TX errors 0  dropped 0 overruns 0  carrier 0  collisions 0\n\nlo: flags=73<UP,LOOPBACK,RUNNING>  mtu 65536\n        inet 127.0.0.1  netmask 255.0.0.0\n        inet6 ::1  prefixlen 128  scopeid 0x10<host>\n        loop  txqueuelen 1  (Local Loopback)\n        RX packets 5214029  bytes 417704433 (398.3 MiB)\n        RX errors 0  dropped 0  overruns 0  frame 0\n        TX packets 5214029  bytes 417704433 (398.3 MiB)\n        TX errors 0  dropped 0 overruns 0  carrier 0  collisions 0\n\nvirbr0: flags=4099<UP,BROADCAST,MULTICAST>  mtu 1500\n        inet 192.168.122.1  netmask 255.255.255.0  broadcast 192.168.122.255\n        ether 52:54:00:b7:6f:ef  txqueuelen 1000  (Ethernet)\n        RX packets 0  bytes 0 (0.0 B)\n        RX errors 0  dropped 0  overruns 0  frame 0\n        TX packets 0  bytes 0 (0.0 B)\n        TX errors 0  dropped 0 overruns 0  carrier 0  collisions 0"
}
{"output.stdout": "ens32: flags=4163<UP,BROADCAST,RUNNING,MULTICAST>  mtu 1500\n        inet 10.10.10.11  netmask 255.255.255.0  broadcast 10.10.10.255\n        inet6 fe80::250:56ff:fe93:e5c6  prefixlen 64  scopeid 0x20<link>\n        ether 00:50:56:93:e5:c6  txqueuelen 1000  (Ethernet)\n        RX packets 10048045  bytes 1340025577 (1.2 GiB)\n        RX errors 0  dropped 0  overruns 0  frame 0\n        TX packets 9885546  bytes 975436242 (930.2 MiB)\n        TX errors 0  dropped 0 overruns 0  carrier 0  collisions 0\n\nlo: flags=73<UP,LOOPBACK,RUNNING>  mtu 65536\n        inet 127.0.0.1  netmask 255.0.0.0\n        inet6 ::1  prefixlen 128  scopeid 0x10<host>\n        loop  txqueuelen 1  (Local Loopback)\n        RX packets 5214029  bytes 417704433 (398.3 MiB)\n        RX errors 0  dropped 0  overruns 0  frame 0\n        TX packets 5214029  bytes 417704433 (398.3 MiB)\n        TX errors 0  dropped 0 overruns 0  carrier 0  collisions 0\n\nvirbr0: flags=4099<UP,BROADCAST,MULTICAST>  mtu 1500\n        inet 192.168.122.1  netmask 255.255.255.0  broadcast 192.168.122.255\n        ether 52:54:00:b7:6f:ef  txqueuelen 1000  (Ethernet)\n        RX packets 0  bytes 0 (0.0 B)\n        RX errors 0  dropped 0  overruns 0  frame 0\n        TX packets 0  bytes 0 (0.0 B)\n        TX errors 0  dropped 0 overruns 0  carrier 0  collisions 0", "_ansible_no_log": false, "_ansible_verbose_always": true}

PLAY RECAP ************************************************************************************************************************************************************************************
10.10.10.11                : ok=2    changed=1    unreachable=0    failed=0   
View Code

相关文章: