我试图通过SSH跳转主机(我已经在Oracle SQL Developer中成功创建了一个)与远程服务器建立Python连接,但是无法在Python中复制。可以成功连接到SSH主机,但由于超时或打开隧道错误而无法将端口转发到远程服务器。可以放心地认为我的代码是错误的,而不是服务器问题。还需要一种不使用“使用SSHTunnelForwarder()作为服务器:”方法的解决方案,因为我需要类似于OSD / cx_Oracle会话的连续会话,而不是批处理功能。
在这里(以及其他地方)使用paramiko,sshtunnel和cx_Oracle提供的类似示例对我没有用。许多其他示例不需要(或至少明确指定)远程服务器的单独登录凭据。我希望关键的不清楚之处是要使用哪个本地主机+端口,我的SQL Developer连接不需要明确使用(尽管我尝试使用OSD选择的端口,而不是同时使用)。
我认为最接近的比赛是paramiko-port-forwarding-around-a-nat-router的最佳答案
SSH主机
-主机= proxy_hostname
-端口= proxy_port = 22
-用户名= proxy_username
-密码= proxy_password
本地端口转发
-主机= remote_hostname
-端口= remote_port = 1521
-自动分配本地端口= True
连接
-用户名= remote_username
-密码= remote_password
-连接类型= SSH
-SID = remote_server_sid
即paramiko-port-forwarding-around-a-nat-router的类似代码
import paramiko
from paramiko import SSHClient
# Instantiate a client and connect to the proxy server
proxy_client = SSHClient()
proxy_client.connect(
proxy_hostname,
port=proxy_port,
username=proxy_username,
password=proxy_password)
# Get the client's transport and open a `direct-tcpip` channel passing
# the destination hostname:port and the local hostname:port
transport = proxy_client.get_transport()
dest_addr = (remote_hostname,remote_port)
local_addr = ('localhost',55587)
channel = transport.open_channel("direct-tcpip", dest_addr, local_addr)
# Create a NEW client and pass this channel to it as the `sock` (along
# with whatever credentials you need to auth into your REMOTE box
remote_client = SSHClient()
remote_client.connect(
'localhost',
port=55587,
username=remote_username,
password=remote_password,
sock=channel)
我得到的不是连接到远程服务器,而是
transport.py in start_client()
SSHException: Error reading SSH protocol banner
答案 0 :(得分:0)
终于找到了解决方案!类似于OSD的自动本地端口分配,不需要SSHTunnelForwarder的with语句。希望它可以帮助其他人-将问题的OSD输入变量与...配合使用
from sshtunnel import SSHTunnelForwarder
import cx_Oracle
server=SSHTunnelForwarder(
(proxy_hostname,proxy_port),
ssh_username=proxy_username,
ssh_password=proxy_password,
remote_bind_address=(remote_hostname,remote_port))
server.start()
db=cx_Oracle.connect('%s/%s@%s:%s/%s'%(remote_username,remote_password,'localhost',server.local_bind_port,remote_server_sid))
# do something with db
server.close()