首页 > 代码库 > Ansible+Flask+jQueryFileUpload 远程文件管理

Ansible+Flask+jQueryFileUpload 远程文件管理

一.利用Ansible API 2.0对远程主机指定目录内文件的上传,删除,以及解压缩等操作.

核心代码:

AnsibleApi2.py

#!/usr/bin/env python
# -*- coding: utf-8 -*-
#
# this is the Simple Interface package of Ansible2 API
# 
# Author: TCollaboration
#

import os
from tempfile import NamedTemporaryFile
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.playbook_executor import PlaybookExecutor
from ansible.executor.task_queue_manager import TaskQueueManager
from ansible.plugins.callback import CallbackBase


class ResultsCollector(CallbackBase):

    def __init__(self, *args, **kwargs):
        super(ResultsCollector, self).__init__(*args, **kwargs)
        self.host_ok = {}
        self.host_unreachable = {}
        self.host_failed = {}

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

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

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


class AnsibleTask(object):

    def __init__(self, targetHost, passwd=None):

        Options = namedtuple(‘Options‘,
                             [‘listtags‘,
                              ‘listtasks‘,
                              ‘listhosts‘,
                              ‘syntax‘,
                              ‘connection‘,
                              ‘module_path‘,
                              ‘forks‘,
                              ‘remote_user‘,
                              ‘private_key_file‘,
                              ‘ssh_common_args‘,
                              ‘ssh_extra_args‘,
                              ‘sftp_extra_args‘,
                              ‘scp_extra_args‘,
                              ‘become‘,
                              ‘become_method‘,
                              ‘become_user‘,
                              ‘verbosity‘,
                              ‘check‘])

        # initialize needed objects
        self.variable_manager = VariableManager()

        self.options = Options(
            listtags=False,
            listtasks=False,
            listhosts=False,
            syntax=False,
            connection=‘smart‘,
            module_path=‘/usr/lib/python2.7/site-packages/ansible/modules‘,
            forks=100,
            remote_user=‘root‘,
            private_key_file=None,
            ssh_common_args=None,
            ssh_extra_args=None,
            sftp_extra_args=None,
            scp_extra_args=None,
            become=False,
            become_method=None,
            become_user=‘root‘,
            verbosity=None,
            check=False)
        if not passwd:
            self.passwords = dict(vault_pass=‘secret‘)
        else:
            self.passwords = {
                ‘conn_pass‘: ‘{0}‘.format(passwd),
                ‘become_pass‘: ‘{0}‘.format(passwd)
            }
        self.loader = DataLoader()

        # create inventory and pass to var manager
        self.hostsFile = NamedTemporaryFile(delete=False)
        self.hostsFile.write(targetHost)
        self.hostsFile.close()
        self.inventory = Inventory(
            loader=self.loader,
            variable_manager=self.variable_manager,
            host_list=self.hostsFile.name)
        self.variable_manager.set_inventory(self.inventory)
        self.callback = None

    def ansiblePlay(self, module_name, module_args):
        # create play with tasks
        play_source = dict(
            name="Ansible Play",
            hosts=‘all‘,
            gather_facts=‘no‘,
            tasks=[
                dict(action=dict(module=module_name, args=module_args))
            ]
        )
        play = Play().load(
            play_source,
            variable_manager=self.variable_manager,
            loader=self.loader)

        # run it
        tqm = None
        self.callback = ResultsCollector()
        try:
            tqm = TaskQueueManager(
                inventory=self.inventory,
                variable_manager=self.variable_manager,
                loader=self.loader,
                options=self.options,
                passwords=self.passwords,
                stdout_callback=‘default‘,
            )
            tqm._stdout_callback = self.callback
            result = tqm.run(play)
        finally:
            # print result
            if tqm is not None:
                tqm.cleanup()
                os.remove(self.hostsFile.name)
                self.inventory.clear_pattern_cache()

            return result

    def run_playbook(self, playbook_path):
        self.callback = ResultsCollector()
        pbex = PlaybookExecutor(
            playbooks=[playbook_path],
            inventory=self.inventory,
            variable_manager=self.variable_manager,
            loader=self.loader,
            options=self.options,
            passwords=self.passwords)

        pbex._tqm._stdout_callback = self.callback

        return pbex.run()  # 返回的结果是数字,不同的结果对应不同的数字

    def get_result(self):
        self.results_raw = {‘success‘: {}, ‘failed‘: {}, ‘unreachable‘: {}}
        for host, result in self.callback.host_ok.items():
            self.results_raw[‘success‘][host] = result._result

        for host, result in self.callback.host_failed.items():
            self.results_raw[‘failed‘][host] = result._result[‘msg‘]

        for host, result in self.callback.host_unreachable.items():
            self.results_raw[‘unreachable‘][host] = result._result[‘msg‘]

        return self.results_raw


def ansible_command(targetHost, passwd, module_name, module_args):
    """
     ansible 模块接口
     :param targetHost 主机ip
     :param passwd 主机访问密码
     :param module_name 模块名称
     :param module_args 模块参数
    """
    ansiTask = AnsibleTask(targetHost, passwd)
    ret = ansiTask.ansiblePlay(module_name, module_args)
    return ret, ansiTask.get_result()


def ansible_playbook(targetHost, passwd, playbook_yaml):
    """
     ansible playbook接口
     :param targetHost 主机ip
     :param passwd 主机访问密码
     :param playbook_yaml yaml任务文件
    """
    ansiTask = AnsibleTask(targetHost, passwd)
    ret = ansiTask.run_playbook(playbook_yaml)
    return ret, ansiTask.get_result()


二.利用jQueryFileUpload框架完成文件列表,文件上传,文件删除等操作的Http请求,以及UI展示

主要涉及到:

<script src="http://www.mamicode.com/static/plugins/jQueryFileUpload/vendor/jquery.ui.widget.js"></script>
<!-- The Templates plugin is included to render the upload/download listings -->
<script src="http://www.mamicode.com/static/plugins/jQueryFileUpload/tmpl.min.js"></script>
<!-- blueimp Gallery script -->
<script src="http://www.mamicode.com/static/plugins/jQueryFileUpload/jquery.blueimp-gallery.min.js"></script>
<!-- The Iframe Transport is required for browsers without support for XHR file uploads -->
<script src="http://www.mamicode.com/static/plugins/jQueryFileUpload/jquery.iframe-transport.js"></script>
<!-- The basic File Upload plugin -->
<script src="http://www.mamicode.com/static/plugins/jQueryFileUpload/jquery.fileupload.js"></script>
<!-- The File Upload processing plugin -->
<script src="http://www.mamicode.com/static/plugins/jQueryFileUpload/jquery.fileupload-process.js"></script>
<!-- The File Upload validation plugin -->
<script src="http://www.mamicode.com/static/plugins/jQueryFileUpload/jquery.fileupload-validate.js"></script>
<!-- The File Upload user interface plugin -->
<script src="http://www.mamicode.com/static/plugins/jQueryFileUpload/jquery.fileupload-ui.js"></script>
<!-- The main application script -->
<script src="http://www.mamicode.com/static/plugins/jQueryFileUpload/bootstrap.min.js"></script>

当然在form表单提交的时候,你可能会带外数据,那么你可能会用到jQueryFileUpload框架中的绑定事件,

如下:

// Callback for the submit event of each file upload:
// submit: function (e, data) {}, // .bind(‘fileuploadsubmit‘, func);

// Callback for the start of each file upload request:
// send: function (e, data) {}, // .bind(‘fileuploadsend‘, func);

// Callback for successful uploads:
// done: function (e, data) {}, // .bind(‘fileuploaddone‘, func);

// Callback for failed (abort or error) uploads:
// fail: function (e, data) {}, // .bind(‘fileuploadfail‘, func);

// Callback for completed (success, abort or error) requests:
// always: function (e, data) {}, // .bind(‘fileuploadalways‘, func);

// Callback for upload progress events:
// progress: function (e, data) {}, // .bind(‘fileuploadprogress‘, func);

// Callback for global upload progress events:
// progressall: function (e, data) {}, // .bind(‘fileuploadprogressall‘, func);

// Callback for uploads start, equivalent to the global ajaxStart event:
// start: function (e) {}, // .bind(‘fileuploadstart‘, func);

// Callback for uploads stop, equivalent to the global ajaxStop event:
// stop: function (e) {}, // .bind(‘fileuploadstop‘, func);

// Callback for change events of the fileInput(s):
// change: function (e, data) {}, // .bind(‘fileuploadchange‘, func);

// Callback for paste events to the pasteZone(s):
// paste: function (e, data) {}, // .bind(‘fileuploadpaste‘, func);

// Callback for drop events of the dropZone(s):
// drop: function (e, data) {}, // .bind(‘fileuploaddrop‘, func);

// Callback for dragover events of the dropZone(s):
// dragover: function (e) {}, // .bind(‘fileuploaddragover‘, func);

// Callback for the start of each chunk upload request:
// chunksend: function (e, data) {}, // .bind(‘fileuploadchunksend‘, func);

// Callback for successful chunk uploads:
// chunkdone: function (e, data) {}, // .bind(‘fileuploadchunkdone‘, func);

// Callback for failed (abort or error) chunk uploads:
// chunkfail: function (e, data) {}, // .bind(‘fileuploadchunkfail‘, func);

// Callback for completed (success, abort or error) chunk upload requests:
// chunkalways: function (e, data) {}, // .bind(‘fileuploadchunkalways‘, func);


三.利用Flask搭建Web服务器,Flask依赖两个外部库:Jinja2模板引擎和Werkzeug WSGI工具集。

页面展示:

技术分享

技术分享

技术分享

技术分享


打印业务数据:

技术分享

技术分享


当然这只是目前研究开发的项目中很小的一个功能模块,拿出来分享,谢谢.

本文出自 “TCollaboration” 博客,转载请与作者联系!

Ansible+Flask+jQueryFileUpload 远程文件管理