python使用paramiko实现ssh定时执行命令


#!/usr/bin/env python3
# -*- coding:utf-8 -*-
# @Author: Rosaany

from paramiko.ssh_exception import NoValidConnectionsError, AuthenticationException
from argparse import RawTextHelpFormatter
import paramiko  # 第三方库, pip安装, pip install paramiko -i https://pypi.douban.com/sample
import time
import sys
import argparse
import socket


def ssh_client(host: str,
               user: str,
               pwd: str,
               cmds: list,
               verbose: int,
               waitSeconds: int):
    """ssh客户端"""

    # 私钥文件的存放路径
    # private = paramiko.RSAKey.from_private_key_file(r'C:\Users\xxxx\Documents\xxx')
    # 创建一个实例化
    ssh = paramiko.SSHClient()
    # 加载系统SSH密钥
    ssh.load_system_host_keys()
    # 自动添加策略,保存服务器的主机名和密钥信息,如果不添加,那么不在本地knows_hosts文件中记录的主机将无法连接,默认拒接
    ssh.set_missing_host_key_policy(paramiko.AutoAddPolicy())
    # 连接设备
    try:
        ssh.connect(
            hostname=host,
            username=user,
            timeout=5,
            compress=True,
            password=pwd
            # pkey=private,  #可以采用密钥连接
        )

        print("正在连接主机ip: {}.....".format(host))
    except NoValidConnectionsError:
        print('连接出现了问题')
    except AuthenticationException:
        print('用户名或密码错误')
    except socket.timeout:
        print('请检查你的远程主机通讯连接是否正常')
    except Exception as err:
        print('其他错误问题: {}'.format(err))
    finally:
        # 激活交互式shell
        # https://stackoverflow.com/questions/6203653/how-do-you-execute-multiple-commands-in-a-single-session-in-paramiko-python
        channel = ssh.invoke_shell()
        time.sleep(1)

        stop = True
        while (stop):
            try:
                for cmd in cmds:
                    channel.send(cmd.encode())
                    # 模拟回车'Enter'这个动作
                    channel.send(b'\n')
                    # 每个命令间隔时间
                    time.sleep(1)
                    r = channel.recv(40960).decode()
                    if verbose:
                        print(r)
                # 执行完一轮命令,等待时间
                time.sleep(waitSeconds)
            except KeyboardInterrupt:  # 捕获ctrl + c时终止程序
                stop = False

            if not waitSeconds:
                stop = False

        channel.close()
        ssh.close()


def tool():
    """
    命令行参数
    """
    ssh_client_help = "一个简单的SSH脚本定时执行命令脚本,如想终止脚本,请按下快捷键ctrl+c \n" \
                      "简单的示例:$python sshclient_exec_command.py -cmds 'top, ls, ifconfig'"

    if len(sys.argv) == 1:
        sys.argv.append('--help')

    parser = argparse.ArgumentParser(description=ssh_client_help, formatter_class=RawTextHelpFormatter)

    parser.add_argument('-u', type=str, default='root', help='ssh访问主机的用户名,默认用户名是root')
    parser.add_argument('-p', type=str, default='123456', help='ssh访问主机的密码,默认密码是123456')
    parser.add_argument('-host', type=str, default='192.168.1.1', help='ssh访问主机ip,默认访问主机是192.168.1.1')
    parser.add_argument('-cmds', type=str, \
        default="'ls -ll', 'ifconfig'", help='执行输入的命令,多个以英文逗号分隔,默认输入命令是"ls -ll,ifconfig"')
    parser.add_argument('-t', type=str, default=0, help='输入一个定时等待时间,单位是秒,默认定时时间为0秒')
    parser.add_argument('-v', type=int, default=1, help='显示详细信息,默认输出详细信息')

    arguments = parser.parse_args()
    return arguments


def main():
    """主程序"""
    arguments = tool()
    host = arguments.host
    user = arguments.u
    pwd = arguments.p
    cmds = arguments.cmds
    verbose = arguments.v
    waitSeconds = arguments.t

    if not isinstance(verbose, int):
        verbose = int(verbose)

    if not isinstance(waitSeconds, int):
        waitSeconds = int(waitSeconds)

    if isinstance(cmds, str):
        cmds = cmds.split(',')

    print("执行命令:{cmd}".format(cmd=cmds))

    ssh_client(
        host=host,
        user=user,
        pwd=pwd,
        cmds=cmds,
        verbose=verbose,
        waitSeconds=waitSeconds)


if __name__ == '__main__':
    # linux实时查看ssh连接通道state变化,-n 1表示每一秒查询一遍,注意TCP四次挥手是否正常释放
    # watch -n 1 -d 'netstat -anlt | grep 192.168.1.1'
    main()

使用示例

$python .\sshclient_exec_commands.py
usage: sshclient_exec_commands.py [-h] [-u U] [-p P] [-host HOST] [-cmds CMDS] [-t T] [-v V]

一个简单的SSH脚本定时执行命令脚本,如想终止脚本,请按下快捷键ctrl+c
简单的示例:$python sshclient_exec_command.py -cmds 'top, ls, ifconfig'

optional arguments:
  -h, --help  show this help message and exit
  -u U        ssh访问主机的用户名,默认用户名是root
  -p P        ssh访问主机的密码,默认密码是123456
  -host HOST  ssh访问主机ip,默认访问主机是192.168.1.1
  -cmds CMDS  执行输入的命令,多个以英文逗号分隔,默认输入命令是"ls -ll,ifconfig"
  -t T        输入一个定时等待时间,单位是秒,默认定时时间为0秒
  -v V        显示详细信息,默认输出详细信息
  • 定时执行

加上-t参数,默认不执行定时,单位是秒

python .\sshclient_exec_commands.py -host 192.168.1.1 -u root -p 123456 -cmds "ls" -t 1

  • 执行多个命令

比如:-cmds "ls -l, ifconfig",多个命令,中间加入一个英文逗号

python .\sshclient_exec_commands.py -host 192.168.1.1 -u root -p 123456 -cmds "mount" -t 1

ssh