我正在尝试使用pysftp
使用Python脚本连接到SFTP站点。
由于我没有主机密钥文件,因此按照建议的here创建了一个主机密钥,并且我正在尝试加载该文件,但是pysftp
无法连接到sftp站点。
python代码非常简单:
cnopts = pysftp.CnOpts()
cnopts.hostkeys.load(pathToTheFile)
with pysftp.Connection(host, username=username, private_key=pathToPKey, cnopts=cnopts) as sftp:
#do things
我首先尝试在主机密钥文件中添加以下内容:
host.com ssh-ed25519 256 AZFsh0........Qy0=
但这会导致InvalidHostKey
错误和Incorrect padding
错误。我猜它不需要256键。因此,我删除了256。
当我尝试不使用256时:
host.com ssh-ed25519 256 AZFsh0........Qy0=
然后它识别出密钥,但是出现'utf-8' codec can't decode byte 0x90 in position 11: invalid start byte
错误。
因此,我尝试加载带有here中建议的以下代码的主机密钥,而不是加载主机密钥文件:
keydata = b"""AZFsh0........Qy0="""
key1 = paramiko.ed25519key.Ed25519Key(data=keydata)
key2 = paramiko.ed25519key.Ed25519Key(data=base64.b64decode(keydata))
key3 = paramiko.ed25519key.Ed25519Key(data=base64.b64decode(keydata).hex())
key4 = paramiko.ed25519key.Ed25519Key(data=decodebytes(keydata))
key5 = paramiko.ed25519key.Ed25519Key(data=decodebytes(keydata).hex())
cnopts.hostkeys.add("host.com", "ssh-ed25519", key1)
我尝试使用以上所有键,但是仍然出现类似Incorrect padding
,
我看到有人提到this may be a bug,但帖子来自2018年。 有人知道这是行不通的还是我错过了什么?
发布在Connection to an SFTP server using pysftp and Python 3 with just the server fingerprint中的解决方案有效,该解决方案在Martin Prikryl的响应链接中链接。
这就是我使用的(我清理了一些东西以删除未使用的功能)。
import hashlib as hl
#Removed trim_fingerprint() and clean_fingerprint() because it wasn't necessary in my case
class FingerprintKey:
def __init__(self, fingerprint):
self.fingerprint = fingerprint
def compare(self, other):
if callable(getattr(other, "get_fingerprint", None)):
return other.get_fingerprint() == self.fingerprint
elif other == self.get_fingerprint():
return True
elif hl.md5(other).hexdigest() == self.fingerprint:
return True
else:
return False
def __cmp__(self, other):
return self.compare(other)
def __contains__(self, other):
return self.compare(other)
def __eq__(self, other):
return self.compare(other)
def __ne__(self, other):
return not self.compare(other)
def get_fingerprint(self):
return self.fingerprint
def get_name(self):
return u'ssh-ed25519' # Including "256" errors out.
def asbytes(self):
return self
它以这种方式使用:
cnopts = pysftp.CnOpts()
cnopts.hostkeys.add('host.com', u'ssh-ed25519 256', FingerprintKey("e2d1............c957")) # Removed ":" from the MD5 value
我苦苦挣扎的主要事情是我不确定应该为cnopts.hostkeys.add
等插入什么值,所以我会详细说明这些细节,以防万一有人不熟悉此事。
就我而言,我使用WinSCP来获取主机密钥指纹。
keytype
的第二个参数(cnopts.hostkeys.add
)key
的第三个参数(cnopts.hostkeys.add
)。实际值是冒号(例如e2:d1:...... c9:57),但是正如Connection to an SFTP server using pysftp and Python 3 with just the server fingerprint的作者所提到的,我也必须手动删除冒号。 答案 0 :(得分:0)
“主机密钥文件” 的内容是完整的主机/公共密钥,不仅是指纹。
有关详细信息,请参见(再次):
Verify host key with pysftp
如果只想使用指纹来验证主机密钥,请参见:
Python - pysftp / paramiko - Verify host key using its fingerprint
(尽管这已经在第一个答案中链接了)。