Python中通过SSH隧道连接PostgreSQL失败求助
问题排查与解决方向
1. SSH密钥密码未正确处理
你的私钥大概率设置了密码保护,pgAdmin会自动弹出输入框让你输入密钥密码,或者通过系统密钥链读取已保存的密码,但你的代码里没做对应处理,导致SSH连接失败,后续PostgreSQL因为隧道未建立而超时。
解决方式:
- 直接在
SSHTunnelForwarder初始化时传入密钥密码:
from sshtunnel import SSHTunnelForwarder with SSHTunnelForwarder( ("ssh服务器地址", 22), ssh_username="ssh用户名", ssh_private_key="/本地私钥路径", ssh_private_key_password="你的密钥密码", remote_bind_address=("172.26.201.14", 5432), local_bind_address=("localhost", 5433) ) as tunnel: # 数据库连接代码写在这里 pass
- 或者通过paramiko加载带密码的密钥后传入:
from sshtunnel import SSHTunnelForwarder import paramiko private_key = paramiko.RSAKey.from_private_key_file("/本地私钥路径", password="你的密钥密码") with SSHTunnelForwarder( ("ssh服务器地址", 22), ssh_username="ssh用户名", ssh_pkey=private_key, remote_bind_address=("172.26.201.14", 5432), local_bind_address=("localhost", 5433) ) as tunnel: # 数据库连接代码写在这里 pass
2. PostgreSQL连接目标错误
pgAdmin是通过SSH隧道把远程5432端口映射到本地端口,再连接本地端口;如果你的psycopg2代码直接连接172.26.201.14:5432,而隧道没建立成功,必然超时。
解决方式:确保psycopg2连接的是localhost加上你设置的本地转发端口(比如上面的5433),而非远程IP的5432端口。
3. SSH代理未启用
pgAdmin可能默认使用系统SSH代理(比如密钥链已保存密钥密码),但SSHTunnelForwarder默认未开启这个选项,导致无法读取已解锁的密钥。
解决方式:在SSHTunnelForwarder参数中添加allow_agent=True:
with SSHTunnelForwarder( ("ssh服务器地址", 22), ssh_username="ssh用户名", ssh_private_key="/本地私钥路径", allow_agent=True, remote_bind_address=("172.26.201.14", 5432), local_bind_address=("localhost", 5433) ) as tunnel: # 数据库连接代码写在这里 pass
4. 数据库连接时机错误
如果你的psycopg2连接代码写在了with SSHTunnelForwarder(...) as tunnel:的上下文块外面,此时隧道已经关闭,自然会连接超时。
解决方式:把数据库连接及操作代码放在隧道的上下文缩进块内:
import psycopg2 with SSHTunnelForwarder(...) as tunnel: conn = psycopg2.connect( dbname="你的数据库名", user="数据库用户名", password="数据库密码", host="localhost", port=tunnel.local_bind_port # 或你设置的固定本地端口 ) # 执行数据库操作 cursor = conn.cursor() cursor.execute("SELECT 1;") print(cursor.fetchone()) # 关闭连接 cursor.close() conn.close()
内容的提问来源于stack exchange,提问作者Aleksandr Lozko
相关产品推荐
相关产品推荐

