python脚本 实现批量远程执行命令,传输文件功能

python脚本 实现批量远程执行命令,传输文件功能

前言

由于一些不可抗力因素,公司生产上的机器封了ssh的端口,无可奈何只能自己写了一个python 程序来实现批量远程控制和传输文件脚本。

服务端(被远程操控端)

  • server.py 放在被控制的主机上 需要修改的地方为ip_pat中的正值表达式,默认是筛选本机的192开头的地址,可根据实际情况调整,端口默认为11115,日志默认打印在当前目录的server.log中

  • 执行方法

python server.py #前端运行
nohup python server.py & #后端运行
import socket
import time
import json
import struct
import subprocess
import os
import re
import datetime


def write_log(data, cmd=''):
    with open('server.log', 'a') as f2:
        now = datetime.datetime.now().strftime('%Y-%m-%d %H:%M:%S')
        if cmd:
            f2.write(now + '\n' + json.dumps(data) + '\n' + cmd + '\n')
        else:
            f2.write(now + '\n' + json.dumps(data) + '\n')


def getip(patten):
    ip_text = subprocess.check_output(["ip", "a"])
    ip_search = re.search(patten, ip_text)
    return ip_search.groups()[0]


def return_cl(data):
    clientSocket.send((ip.center(30, '-') + "\n" + data))
    time.sleep(0.2)
    clientSocket.send('$end$')


def execute_cmd(cmd):
    write_log(head_dict, cmd)
    return_data = ''
    res = subprocess.Popen(
        cmd, shell=True, stdout=subprocess.PIPE, stderr=subprocess.PIPE, close_fds=True)
    nomal_text = res.stdout.read().rstrip()
    error_text = res.stderr.read().rstrip()
    if nomal_text:
        return_data += nomal_text
    if error_text:
        return_data += error_text
    return_cl(return_data)


def wirte_file(data, filename):
    write_log(head_dict)
    dir_path = os.path.dirname(filename)
    if not os.path.exists(dir_path):
        return_data = 'dir %s not exists' % dir_path
        return_cl(return_data)
        return False
    if os.path.isdir(filename):
        return_data = '%s is dir' % filename
        return_cl(return_data)
        return False
    try:
        with open(filename, 'wb') as f2:
            f2.write(data)
            return_cl('file %s transport successfully' % filename)
    except IOError:
        return_cl('Permission denied: wirte ' + filename)


if __name__ == '__main__':

    ip_pat = r"inet (192.[0-9\.]*?)/24 brd"
    ip = getip(ip_pat)

    server = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
    server.bind((ip, 11115))

    print('server started')
    server.listen(1)
    fulldata = ''

    while True:
        clientSocket, clientAddress = server.accept()
        fulldata = ''
        head_len_byte = clientSocket.recv(1024)
        try:
            head_len = struct.unpack('i', head_len_byte)[0]
        except struct.error:
            write_log('bad request')
            clientSocket.close()
            continue
        head_dict = json.loads(clientSocket.recv(head_len))

        while True:
            data = clientSocket.recv(1024)
            if data == b'$end$':
                break
            else:
                fulldata += data

        if head_dict['type'] == 'cmd':
            execute_cmd(fulldata.decode('utf-8'))
        if head_dict['type'] == 'file':
            wirte_file(fulldata, head_dict['dest'])

客户端(操控端)

  • client.py 连接默认端口为11115,只需修改iplist即可
  • 执行方法
python client.py cmd '命令'  #操控远程主机执行命令,并返回结果
python client.py file 本地文件地址 远端文件地址
import socket
import sys
import os
import struct
from time import sleep
import json

promote = '''Useage :
python  (cmd 'context' | file 'context' 'dest_filename')
'''


def check_file(file_path):
    if not os.path.isfile(file_path):
        exit(file_path + ' not exists')
    return True


def check_params():
    params = [i.rstrip() for i in sys.argv[1:]]

    if len(params) == 2 and params[0] == 'cmd' or (
            len(params) == 3 and params[0] == 'file' and check_file(params[1])):
        send_data(params)
        exit()

    exit(promote)


def send_data(args):
    tran_dict = {
        'type': args[0]
    }
    if args[0] == 'cmd':
        data = args[1].encode('utf-8')

    if args[0] == 'file':
        tran_dict['dest'] = args[2]
        with open(args[1], 'rb') as f:
            data = f.read()

    head_info = json.dumps(tran_dict)
    head_info_len = struct.pack('i', len(head_info))

    socket.setdefaulttimeout(4)

    for ip in iplist.rstrip().split():
        try:
            sk = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
            sk.connect((ip, 11115))
            sk.send(head_info_len)
            sleep(0.2)
            sk.send(head_info.encode('utf-8'))
            sk.sendall(data)
            sleep(0.2)
            sk.send(b'$end$')

            res_data = ''
            while True:
                temdata = sk.recv(1024)
                if temdata == b'$end$':
                    break
                else:
                    res_data += temdata.decode('utf-8')
            print res_data
        except socket.timeout:
            print '%s connection time out'.center(30, '-') % ip
            continue
        except:
            print '%s is DOWN'.center(30, '-') % ip
            continue
        sk.close()


if __name__ == '__main__':
    iplist = '''192.168.58.128
    192.168.58.129
    '''
    check_params()
    exit()
  • 0
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
Python是一种强大的编程语言,常被用于编写运维脚本。而Linux运维脚本指的是用于在Linux操作系统上执行运维任务的脚本。下面是关于Python Linux运维脚本的一些重要信息。 首先,Python具有丰富的库和模块,可以轻松地与操作系统交互。通过使用Python的os模块,我们可以执行与文件和目录相关的任务,如创建、删除、移动和重命名文件和目录。 其次,Python可以通过subprocess模块调用Linux命令。这对于在Linux系统上执行各种系统管理任务非常有用,如安装软件包、配置网络、管理用户和组等。通过subprocess模块,我们可以在Python脚本中调用shell命令,并获取命令的输出结果。 另外,Python还可以通过paramiko模块执行远程操作。Paramiko是一个用于SSH连接和文件传输Python库,我们可以使用它来连接到远程服务器并执行命令。这对于Linux系统管理员来说非常有用,可以远程执行命令传输文件以及进行远程服务器的管理和监控。 此外,Python还可以通过fabric库进行自动化部署和管理。Fabric是一个基于Python开发的用于自动化部署和系统管理的库,它简化了一系列常用的系统管理任务,如批量执行命令、上传和下载文件、执行远程脚本等。使用Fabric,我们可以编写简洁、可维护的自动化脚本,提高工作效率。 总而言之,Python是一种功能强大的编程语言,适合编写Linux运维脚本。它提供了丰富的库和模块,使得在Linux系统上执行各种任务变得容易。无论是执行本地命令、远程操作还是自动化部署,Python都是一个理想的选择。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值