安基网 首页 编程 Python 查看内容

使用Python自动执行SSH和SCP任务

2019-11-17 11:28| 投稿: xiaotiger |来自: 互联网


免责声明:本站系公益性非盈利IT技术普及网,本文由投稿者转载自互联网的公开文章,文末均已注明出处,其内容和图片版权归原网站或作者所有,文中所述不代表本站观点,若有无意侵权或转载不当之处请从网站右下角联系我们处理,谢谢合作!

摘要: 我最近帮助了一个朋友在100多个设备上刷新软件。对于每个设备,他都知道MAC地址,并具有通过ssh登录的相应密码。他将此信息存储在Excel工作表中。他手动闪烁的过程是根据设备的MAC地址找出设备的IP地址。使用IP地址和密码SSH进入设备。通过SCP上载软件安装程序。执行一些Shell命令以安装软件。在一台设 ...

我最近帮助了一个朋友在100多个设备上刷新软件。对于每个设备,他都知道MAC地址,并具有通过ssh登录的相应密码。他将此信息存储在Excel工作表中。他手动闪烁的过程是

  1. 根据设备的MAC地址找出设备的IP地址。
  2. 使用IP地址和密码SSH进入设备。
  3. 通过SCP上载软件安装程序。
  4. 执行一些Shell命令以安装软件。

在一台设备上手动执行此操作就可以了,对于两台设备,您开始考虑wtf,三台设备之后,您就会想到WTF!在软件中,减少WTF始终是一个目标,因此我想也许我可以通过使用漂亮的Python脚本自动化他的过程来为他提供帮助。在本文中,我想向您展示最终的结果。

查找给定了MAC地址的IP地址

我们需要解决的第一件事是找出我们本地网络内部设备的IP地址。为此,您的PC和设备都必须连接到同一网络。给定一个IP地址,您可以使用python模块scapy(请注意,我在本文的先前版本中使用了其他软件包。但是,这仅在我已经连接到或对另一个设备执行ping操作时才有效)哪个MAC地址使用IP。在代码中,这看起来像

from scapy.layers.l2 import arping
def get_mac_and_ip(suffix: int) -> Tuple[str, str]:
ip = f"192.168.1.{suffix}"
ans, _ = arping(ip, timeout=.2, verbose=False)
for s, r in ans.res:
st="%19s,Ether.src% %ARP.psrc%"
return tuple(r.sprintf(st).strip().split())

return ("DONT", "CARE")
mac_to_ip = dict(get_mac_and_ip(suffix) for suffix in range(1, 256))

因此,我们只测试每个IP地址并存储回送MAC地址的IP地址。使用scapy时,您需要以root用户身份执行脚本。太酷了,现在我们知道所有MAC地址到IP地址的连接。下一个问题剩下三个。

建立SSH连接

下一个问题是,我们如何使用Python建立SSH连接。有一个名为paramiko的简洁库,使您可以非常简单地完成此操作。从根本上讲,您需要要连接的IP地址,用户名和密码。代码看起来像

import paramiko
# To allow connection without having to accept the host connection
# We need to use this policy. I've just pulled it here due to
# mediums way of displaying code ...
policy = paramiko.client.AutoAddPolicy
# Iterate over all our found mac, ip connections and SSH into
# the clients
for mac, ip in mac_to_ip.items():
# Assume that to be given
pwd = mac_to_pwd[mac]
with paramiko.SSHClient() as client:
client.set_missing_host_key_policy(policy)
try:
client.connect(ip, username='root', password=pwd)
except paramiko.ssh_exception.NoValidConnectionsError:
print("Connection failed")

现在,我们可以使用连接的客户端执行Shell命令,您将很快看到它。

通过SCP上传数据

在执行命令之前,我们需要将安装程序上载到我们的设备。为此,我们利用库SCP,该库与paramiko完美配合。在下面的示例中,假设我们已经使用paramiko SSHClient建立了连接。

from scp import SCPClient 
import sys
def progress4(f, size, sent, p):
prog = sent / size * 100.
sys.stdout.write(f"({p[0]}:{p[1]}) {f}'s progress: {prog}r")
local_path = "/home/me/installer.tar.gz"
remote_path = "/home/root/inst/"
with SCPClient(client.get_transport(), progress4=progress4) as scp:
scp.put(local_path, remote_path=remote_path)

该progress4功能打印出的上传进度。对我来说,这有助于估算我仍然需要等待多长时间而又不会变得急躁,这可能会导致另一个WTF :)。现在我们快到了,只剩一步了。

通过SSH执行Shell命令

现在,由于我们具有正在运行的ssh连接并上传了安装程序,因此我们只需解压缩它并运行它。这可以通过我们可以使用SSH客户端发送的shell命令轻松完成。在代码中,这看起来像

def exec_blocking(cmd, client):
print(f"Executing {cmd}")
_, stdout_, stderr_ = client.exec_command(cmd)
status = stdout_.channel.recv_exit_status()
print(f"STATUS {status}")
for line in stdout_.readlines():
print(line)
if status != 0:
errors = "n".join(list(stderr_.readlines))
raise Exception(f"{cmd} failed with {errors}")
# Unpack the installer
exec_blocking("tar xzvf /home/root/inst/installer.xzvf", client)
# Run the installer
exec_blocking("./installer/install.sh", client)

该命令将通过exec_command发送到设备。这是一个立即返回的非阻塞函数。要等到命令完成执行,您需要调用recv_exit_status()。这样,您可以确保命令执行成功与否。

结论

将所有代码段组合到一个脚本中,使我们可以使用单个命令在列表中所有设备上刷新/执行命令。这为我们节省了很多时间和WTF :)

希望您学到了一些新知识。感谢您的关注,并随时与我联系以提出问题,意见或建议。

翻译自:https://medium.com/@simon.hawe/save-time-by-automating-ssh-and-scp-tasks-with-python-e149de606c7b

0人点赞

Python



小编推荐:欲学习电脑技术、系统维护、网络管理、编程开发和安全攻防等高端IT技术,请 点击这里 注册账号,公开课频道价值万元IT培训教程免费学,让您少走弯路、事半功倍,好工作升职加薪!

本文出自:https://www.toutiao.com/a6759738446148796942/

免责声明:本站系公益性非盈利IT技术普及网,本文由投稿者转载自互联网的公开文章,文末均已注明出处,其内容和图片版权归原网站或作者所有,文中所述不代表本站观点,若有无意侵权或转载不当之处请从网站右下角联系我们处理,谢谢合作!


鲜花

握手

雷人

路过

鸡蛋

相关阅读

最新评论

 最新
返回顶部