Paramiko“未知服务器”

2024-12-06 08:40:00
admin
原创
163
摘要:问题描述:我正在尝试开始使用 Paramiko 库,但是当我尝试连接以下简单程序时,该库会引发异常:import paramiko ssh = paramiko.SSHClient() ssh.connect('127.0.0.1', username='boatzart', password='mypass...

问题描述:

我正在尝试开始使用 Paramiko 库,但是当我尝试连接以下简单程序时,该库会引发异常:

import paramiko
ssh = paramiko.SSHClient()
ssh.connect('127.0.0.1', username='boatzart', password='mypassword')

我收到的错误是:

Traceback (most recent call last):
File "test.py", line 6, in <module>
ssh.connect('127.0.0.1')
File "build/bdist.macosx-10.7-intel/egg/paramiko/client.py", line 316, in connect
File "build/bdist.macosx-10.7-intel/egg/paramiko/client.py", line 85, in missing_host_key
paramiko.SSHException: Unknown server 127.0.0.1

无论我尝试哪个服务器,都会发生这种情况。


解决方案 1:

我遇到了同样的问题,以下是适合我的解决方案:

import paramiko

client = paramiko.SSHClient()
client.set_missing_host_key_policy(paramiko.AutoAddPolicy())
client.connect('127.0.0.1', username=username, password=password)
stdin, stdout, stderr = client.exec_command('ls -l')

这是设置连接到系统或本地 HostKeys 对象中没有主机密钥的服务器时使用的策略。默认策略是拒绝所有未知服务器(使用 RejectPolicy)。您可以替换 AutoAddPolicy 或编写自己的策略类。

更多详细信息请参阅paramiko api doc。希望对您有所帮助。

之后,您可以将其保存到另一个密钥文件中以供下次使用,如下所示。

ssh.get_host_keys().save('/some/file/path')

您始终可以按如下方式从文件加载。

ssh.load_host_keys('/some/file/path')

解决方案 2:

正确的方法是:

  • 在调用之前,先HostKeys.add在返回的实例上调用,并将可信密钥传递给它。SSHClient.get_host_keys`connect`

from base64 import decodebytes
# ...

keydata = b"""AAAAB3NzaC1yc2EAAAADAQAB..."""
key = paramiko.RSAKey(data=decodebytes(keydata))
client.get_host_keys().add('example.com', 'ssh-rsa', key) 

根据实际的密钥类型,您可能需要使用ECDSAKeyEd25519Key代替RSAKey

要了解如何获取代码中使用的密钥,请参阅我的回答:

使用 pysftp 验证主机密钥。

如果您只知道指纹,请参阅:

Python - pysftp / paramiko - 使用指纹验证主机密钥

  • 或者使用 加载已缓存的主机密钥(例如通过 OpenSSH 命令行sshclient.load_system_host_keys()

  • 或者您至少可以从第一次尝试时缓存主机密钥,以确保它将来不会改变。

为此,请SSHClient.load_host_keys在 之前使用connect。它使 Paramiko 自动将新的主机密钥添加到文件中(与 结合使用时AutoAddPolicy)。

解决方案 3:

引发异常的原因是缺少主机密钥,而神秘的“未知服务器”就是线索 - 因为异常是从missing_host_key

尝试一下这个:

import paramiko

paramiko.util.log_to_file('ssh.log') # sets up logging

client = paramiko.SSHClient()
client.load_system_host_keys()
client.connect('127.0.0.1', username=username, password=password)
stdin, stdout, stderr = client.exec_command('ls -l')

解决方案 4:

我遇到了这个问题,想在这里发布一个解决方法。问题确实是 ssh 服务器发送了 ecdsa 密钥,而 paramiko 尚不支持该密钥。在我的 debian Wheezy 系统上,我通过注释掉 /etc/ssh/sshd_config 中的一行来禁用 ecdsa:

主机密钥 /etc/ssh/ssh_host_ecdsa_key

重新启动 sshd,然后恢复使用 RSA。我的 known_hosts 文件中有一些 ecdsa 密钥,所以我删除它以进行重置,然后手动登录以重新创建密钥。从那里开始,paramiko 就可以按预期完美运行,并进行 RSA 主机密钥检查。

解决方案 5:

我遇到了这个错误:我可以从 shell 连接,但是 paramiko 说“未知服务器 workdevel114”。

known_hosts 中有两个类似的条目:

user@host> grep workdevel114 ~/.ssh/known_hosts
workdevel114 ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAAAgQC8qGbuI1BaBodi7sKWLfV8Eh+De80Th7HFLD4WiJWo57THl0Q+QcopUaU3pF....
user@host> grep I1BaBodi7sKWLfV8Eh+De80Th7HFLD4WiJWo57THl0Q+QcopUaU3pF ~/.ssh/known_hosts
workdevel114 ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAAAgQC8qGbuI1BaBodi7sK...
|1|f/auQ9nY5dFbVtOdY3ocjtVO9dM=|esvazUDTT3VIcLk9DxmPI6FZt1s= ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAAAgQC8qGbuI1BaBodi7sKWLfV8Eh+De80Th7HFLD4...

秒数条目 (|1|....) 似乎让 paramiko 感到困惑。我猜这与这张票有关: https: //github.com/paramiko/paramiko/issues/67

我通过添加以下行解决了这个问题:

client.set_missing_host_key_policy(paramiko.AutoAddPolicy())

但在这种情况下,这会禁用 ssh 协议的主机检查:Paramiko 认为主机密钥未知,但实际上它是已知的。已知密钥被忽略。我不在乎,因为在我的环境中,中间人攻击的可能性很小。

paraiko-版本:1.7.7.1-1ubuntu1

解决方案 6:

我尝试使用上下文管理器将 Martin Prikryl 的部分回应合并到单个类中。

或者您至少可以缓存第一次尝试的主机密钥,以确保将来不会更改。为此,请SSHClient在连接之前使用 .load_host_keys。它使 Paramiko 自动将新主机密钥添加到文件中(与 结合使用时AutoAddPolicy)。


import paramiko
from paramiko import client, sftp_client


class SFTP:
    sftp: sftp_client.SFTPClient
    ssh: client.SSHClient
    host: str
    user: str
    password: str

    def __init__(self, host: str, user: str, password: str):
        self.host = host
        self.user = user
        self.password = password

    def __enter__(self) -> sftp_client.SFTPClient:
        ssh = paramiko.SSHClient()
        ssh.set_missing_host_key_policy(paramiko.AutoAddPolicy())
        ssh.load_system_host_keys()
        ssh.connect(self.host, username=self.user, password=self.password)
        self.ssh = ssh

        sftp = ssh.open_sftp()
        self.sftp = sftp
        return sftp

    def __exit__(self, exc, _, __) -> bool:
        if exc is None:
            self.sftp.close()
            self.ssh.close()
            return True

        raise exc

例子:


with SFTP('host', 'user', 'password') as sftp:
    ...
相关推荐
  政府信创国产化的10大政策解读一、信创国产化的背景与意义信创国产化,即信息技术应用创新国产化,是当前中国信息技术领域的一个重要发展方向。其核心在于通过自主研发和创新,实现信息技术应用的自主可控,减少对外部技术的依赖,并规避潜在的技术制裁和风险。随着全球信息技术竞争的加剧,以及某些国家对中国在科技领域的打压,信创国产化显...
工程项目管理   2500  
  为什么项目管理通常仍然耗时且低效?您是否还在反复更新电子表格、淹没在便利贴中并参加每周更新会议?这确实是耗费时间和精力。借助软件工具的帮助,您可以一目了然地全面了解您的项目。如今,国内外有足够多优秀的项目管理软件可以帮助您掌控每个项目。什么是项目管理软件?项目管理软件是广泛行业用于项目规划、资源分配和调度的软件。它使项...
项目管理软件   1541  
  PLM(产品生命周期管理)项目对于企业优化产品研发流程、提升产品质量以及增强市场竞争力具有至关重要的意义。然而,在项目推进过程中,范围蔓延是一个常见且棘手的问题,它可能导致项目进度延迟、成本超支以及质量下降等一系列不良后果。因此,有效避免PLM项目范围蔓延成为项目成功的关键因素之一。以下将详细阐述三大管控策略,助力企业...
plm系统   16  
  PLM(产品生命周期管理)项目管理在企业产品研发与管理过程中扮演着至关重要的角色。随着市场竞争的加剧和产品复杂度的提升,PLM项目面临着诸多风险。准确量化风险优先级并采取有效措施应对,是确保项目成功的关键。五维评估矩阵作为一种有效的风险评估工具,能帮助项目管理者全面、系统地评估风险,为决策提供有力支持。五维评估矩阵概述...
免费plm软件   23  
  引言PLM(产品生命周期管理)开发流程对于企业产品的全生命周期管控至关重要。它涵盖了从产品概念设计到退役的各个阶段,直接影响着产品质量、开发周期以及企业的市场竞争力。在当今快速发展的科技环境下,客户对产品质量的要求日益提高,市场竞争也愈发激烈,这就使得优化PLM开发流程成为企业的必然选择。缺陷管理工具和六西格玛方法作为...
plm产品全生命周期管理   26  
热门文章
项目管理软件有哪些?
曾咪二维码

扫码咨询,免费领取项目管理大礼包!

云禅道AD
禅道项目管理软件

云端的项目管理软件

尊享禅道项目软件收费版功能

无需维护,随时随地协同办公

内置subversion和git源码管理

每天备份,随时转为私有部署

免费试用