由于项目需要部署数十台Windows服务器,在开始的时候,部署方式是分别登录到每一台服务器上,在各个服务器上单独执行部署脚本,但是在服务器逐渐增多之后,当需要更新版本时,就需要登录数十台服务器执行更新脚本,工作量相当重复。
Windows执行远程Dos脚本,传统方式一般是通过135端口,但是这个端口因为太不安全,基本上都被防火墙给屏蔽了。
所有后来就想着通过别的方式来执行Bat脚本,且方式简单,于是就有了下面的内容。
服务端和客户端均使用Python实现。
话不多说,上代码。

一、服务端

端口可以自己修改,默认只有白名单中的IP可以访问。

RemoteServer.py

#-*- coding: utf-8 -*-

import socket
import os
import threading

import urllib.parse
import ctypes
import datetime


local_ip = '0.0.0.0'        # 配置socket server绑定的本地IP
local_port = 4321           # 配置socket server绑定的本地端口

server = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
server.bind((local_ip, local_port))
server.listen(5)

# 只响应白名单中的计算机发来的任务
# admin_filter的key()
admin_filter = {}
admin_filter['172.19.1.30'] = {'exe'}
admin_filter['127.0.0.1'] = {'exe'}


print('White list:' + str(admin_filter))
print('Server bind on %s:%s' % (local_ip, str(local_port)))
print('-----------------Server starting success-----------------')


def exe_prog(msg):
    # 路径由空格,加上引号就好了 -_-!!!!!
    #os.system(u"\"C:\Program Files (x86)\TTPlayer\TTPlayer.exe\"".encode("gbk"))
    os.system(msg)
    # os.system("C:\ProgramData\Anaconda3\envs\py2\python.exe F:\\source_files\\quant\\remote_pc_control\\exe_calc.py")

while 1:
    conn, addr = server.accept()
    msg = urllib.parse.unquote(conn.recv(1024).decode('utf-8'))
    
    peer_name = conn.getpeername()
    sock_name = conn.getsockname()

    # peer_name是个tuple,peer_name[0]是ip,peer_name[1]是端口号
    now_dt = str(datetime.datetime.now())
    print(u'%s, visitor: %s:%s'%(now_dt, peer_name[0],peer_name[1])) # , sock_name
    # 所谓的白名单,管理员权限验证
    if peer_name[0] in admin_filter.keys():
        print(msg)
        if '"quit"' == msg: # 可能是 'quit' 可能是 '"quit"' …… 自己检验一下
            conn.close()
            exit(0)
        t = threading.Thread(target=exe_prog,args=(msg,))
        t.start()

    #conn.send('server: I received '+msg)

二、python客户端

RemoteClient.py

#-*- coding: utf-8 -*-

import socket
from urllib import parse

def send_cmd(instr):
    try:
        client = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
        client.connect(('172.19.1.xx', 4321))
        client.settimeout(5)
        client.sendall(parse.quote(instr).encode('utf-8'))
        
    except Exception as e:
        print(e)
    finally:
        client.close()

msg = u"d:\\test.bat"

send_cmd(msg)

三、服务端启动脚本

StartRemoteServer.bat

@echo off

chcp 65001
title 远程调用服务

python RemoteServer.py

@pause

四、调用方式

1、安装python3。
2、先修改服务端脚本,把客户端的IP添加的白名单中。
3、修改客户端脚本中的服务器IP。
4、修改客户端脚本中的msg。
5、启动服务端,然后在客户端DOS中执行下列命令即可。

python RemoteClient.py