ansible2.3 API封装

2.3的api和2.8有一些区别,一个是inventory方面的,2.3直接导入Inventory,而2.8是InventoryManager,这两个类的方法不太一样。
最近有用到2.3版本的,所以这里记一下,详细介绍还是看之前博客Python调用ansible 2.8 API

先安装依赖和包,如果是2.7的python版本,pip版本不能超过21

安装依赖和包
yum  install python-devel sshpass -y
yum install  python-pip -y
pip install --upgrade "pip < 21.0"
pip install ansible==2.3.1
#/usr/bin/python
# coding=UTF-8
import json
import sys
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
from ansible.plugins.callback import CallbackBase
from ansible.playbook.play import Play
from ansible.executor.task_queue_manager import TaskQueueManager
from ansible.inventory.host import Group                           #对 主机组 执行操作 ,可以给组添加变量等操作,扩展
from ansible.inventory.host import Host                            #对 主机 执行操作 ,可以给主机添加变量等操作,扩展

class ResultsCallback(CallbackBase):
    def __init__(self,*args,**kwargs):
        super(ResultsCallback,self).__init__(*args,**kwargs)
        self.task_ok = {}
        self.task_unreachable = {}
        self.task_failed = {}
        self.task_skipped = {}
        self.task_stats = {}
        # self.host_ok = {}
        # self.host_unreachable = {}
        # self.host_failed = {}

    def v2_runner_on_unreachable(self, result):
        self.task_unreachable[result._host.get_name()] = result

      

    def v2_runner_on_ok(self, result, *args, **kwargs):
        self.task_ok[result._host.get_name()] = result
        

    def v2_runner_on_failed(self, result, *args, **kwargs):
        self.task_failed[result._host.get_name()] = result
 

    def v2_runner_on_skipped(self, result, *args, **kwargs):
        self.task_skipped[result._host.get_name()] = result

    def v2_runner_on_stats(self, result, *args, **kwargs):
        self.task_stats[result._host.get_name()] = result



class Runner(object):
    def __init__(self,
                 connection='ssh',  # 连接方式 local 本地方式,smart ssh方式
                 remote_user="None",  # 远程用户
                 host_list='/etc/ansible/hosts',
                 ack_pass=None,  # 提示输入密码
                 sudo=None,
                 sudo_user="root",
                 ask_sudo_pass=None,
                 module_path=None,  # 模块路径,可以指定一个自定义模块的路径
                 become=None,  # 是否提权
                 become_method="sudo",  # 提权方式 默认 sudo 可以是 su
                 become_user="root",  # 提权后,要成为的用户,并非登录用户
                 check=False,
                 diff = False,
                 listhosts = None,
                 listtasks = None,
                 listtags = None,
                 forks = 5,  # 同时执行的主机数量
                 tags = [],  # 执行的tags列表
                 skip_tags = [],  # skip跳过的tags列表
                 verbosity = 3,
                 syntax = None,
                 start_at_task = None,
                 inventory = None,
                 passwords=None,
                 *args,**kwargs):


        #三元表达式,假如没有传递 inventory文件, 就使用 "localhost,"
        #这里需要注意如果不使用host文件,即inventory未传入,直接动态传入host列表的情况,这里会将localhost加入主机中,所以执行all主机组也会执行本机,所以要么改为未传入就为“”,要么就设置其他的主机组名称,不使用all执行全部
        #inventory 就是平时用到的存放主机ip以及变量的资源库文件,-i 参数后面跟的文件
        self.inventory = inventory if inventory else "localhost,"

        # 实例化数据解析器,用于解析 存放主机列表的资源库文件 (比如: /etc/ansible/hosts) 中的数据和变量数据的
        self.loader = DataLoader()

        # 实例化 资产配置对象,InventoryManager管理资源库,可以指定一个loader数据解析器和一个inventory文件
        #self.inv_obj = InventoryManager(loader=self.loader, sources=self.inventory)

        # 设置密码,可以为空字典,但必须有此参数
        self.passwords = {"conn_pass":passwords}

        # 实例化回调插件对象
        self.results_callback = ResultsCallback()

        # 变量管理器,假如有变量,所有的变量应该交给他管理。 这里他会从 inventory 对象中获取到所有已定义好的变量。 这里也需要数据解析器。
        #self.variable_manager = VariableManager(self.loader, self.inv_obj)

        #self.loader = DataLoader()
        self.variable_manager = VariableManager()
        #self.results_callback = ResultsCallback()
        #default host_list='/etc/ansible/hosts'
        self.inventory = Inventory(loader=self.loader, variable_manager=self.variable_manager,host_list=host_list)
        self.variable_manager.set_inventory(self.inventory)
        #self.passwords = None

        Options = namedtuple('Options',
                             ['connection',
                              'remote_user',
                              'verbosity',
                              'ack_pass',
                              'module_path',
                              'forks',
                              'become',
                              'become_method',
                              'become_user',
                              'check',
                              'listhosts',
                              'listtasks',
                              'listtags',
                              'syntax',
                              "skip_tags",
                              'tags',
                              "start_at_task",
                              ])
        # 初始化需要的对象
        self.options = Options(connection=connection,
                          remote_user=remote_user,
                          ack_pass=ack_pass,
                          forks=forks,
                          verbosity=5,
                          module_path=module_path,
                          become=become,
                          become_method=become_method,
                          become_user=become_user,
                          check=check,
                          listhosts=listhosts,
                          listtasks=listtasks,
                          listtags=listtags,
                          syntax=syntax,
                          skip_tags=skip_tags,
                          tags=tags,
                               start_at_task=start_at_task,)
    def run_ad_hoc(self,hosts='all', gether_facts="no", module="ping", args=''):
        play_source = dict(
            name="Ad-hoc",
            hosts=hosts,
            gather_facts=gether_facts,
            tasks=[
                #dict(action=dict(module='shell', args='ls /home'), register='shell_out'),
                #dict(action=dict(module='debug', args=dict(msg='{{shell_out.stdout}}'))),
                {"action": {"module": module, "args": args}}
            ]
        )
        play = Play().load(play_source, variable_manager=self.variable_manager, loader=self.loader)

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

        ##定义字典用于接收或者处理结果
        result_raw = {'success': {}, 'failed': {}, 'unreachable': {}, 'skipped': {}, 'status': {}}

        # 循环打印这个结果,success,failed,unreachable需要每个都定义一个
        for host, result in self.results_callback.task_ok.items():
            result_raw['success'][host] = result._result
        for host, result in self.results_callback.task_failed.items():
            result_raw['failed'][host] = result._result

        for host, result in self.results_callback.task_unreachable.items():
            result_raw['unreachable'][host] = result._result

        return result_raw

    def run_playbook(self,playbook,extra_vars={}):
        #自定义变量是用一个字典保存的
        #使用变量管理器VariableManager().extra_vars.update(extra_vars_dict)的方法进行添加
        self.variable_manager.extra_vars.update(extra_vars)
        playbook = PlaybookExecutor(playbooks=playbook, inventory=self.inventory,
                                    variable_manager=self.variable_manager,
                                    loader=self.loader, options=self.options, passwords=self.passwords)

        playbook._tqm._stdout_callback = self.results_callback
        results = playbook.run()

        ##定义字典用于接收或者处理结果
        result_raw = {'success': {}, 'failed': {}, 'unreachable': {}, 'skipped': {}, 'status': {}}

        # 循环打印这个结果,success,failed,unreachable需要每个都定义一个
        for host, result in self.results_callback.task_ok.items():
            result_raw['success'][host] = result._result
        for host, result in self.results_callback.task_failed.items():
            result_raw['failed'][host] = result._result

        for host, result in self.results_callback.task_unreachable.items():
            result_raw['unreachable'][host] = result._result

        for host, result in self.results_callback.task_skipped.items():
            result_raw['skipped'][host] = result._result

        for host, result in self.results_callback.task_stats.items():
            result_raw['status'][host] = result._result

        return result_raw

    #动态添加主机,传入主机列表和组名
    def add_dynamic_hosts(self, hostip_list, groupname=None, groupvars=None):
        """
            add hosts to a group
        """
        #如果有传入组名,则添加组,并创建Group实例
        if groupname:

            my_group = Group(name=groupname)

        else:
            #or ungruped
            my_group=Group(name="all")

        #如果有传入组变量,则将组变量设置给上面创建的Group实例
        if groupvars:
            for key, value in groupvars.iteritems():
                my_group.set_variable(key, value)

        # add hosts to group
        #则遍历主机列表,添加主机并且设置组
        for hostip in hostip_list:
            my_host = Host(name=hostip, port="22")
            my_group.add_host(my_host)

        self.inventory.add_group(my_group)

if __name__ == '__main__':
    
    # 1、执行hoc 传入机器机器IP列表的方式
    # run1 = Runner(remote_user="root",passwords="123456",become=True,become_user="root")
    # run1.add_dynamic_hosts(hostip_list=["10.0.0.108"],groupname="remote")
    #print(run1.run_ad_hoc(hosts= "remote", module="shell", args="/sbin/ethtool ens33 | grep Speed | awk '{print $2}'"))
	
	# 2、执行hoc 使用某个host文件的方式
    #run2 = Runner(remote_user="root",passwords="123456",host_list="/root/PycharmProjects/ansibletest/ansiblehosts")
    #print(run2.run_ad_hoc(hosts= "all", module="shell", args='pwd'))

    #3、执行playbook 
    # run3 = Runner(remote_user="root",passwords="123456",)
    # run3.add_dynamic_hosts(hostip_list=["10.0.0.108"],groupname="remote")
    #print(run3.run_playbook(playbook=["/root/PycharmProjects/ansibletest/playbook.yaml"]))
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值