Java 发出命令后关闭Ganymed会话和连接时发生套接字关闭错误

Java 发出命令后关闭Ganymed会话和连接时发生套接字关闭错误,java,python,ssh,Java,Python,Ssh,我有一个用Java构建的Android应用程序,每当有动作需要时,我会按需向服务器发送SSH命令到Python包。为了解释上下文,我打开一个到服务器的Ganymed连接,然后打开一个会话,然后从该会话启动一个交互式shell,这样我就可以导入我的自定义Python类,并在应用程序上发生更新时从该类调用一个函数来输入数据。我不能发出单独的命令,因为每次打开Python实例、导入、打开服务器上的ZMQ套接字等都需要很长时间 下面是打开shell的代码: session = connection.op

我有一个用Java构建的Android应用程序,每当有动作需要时,我会按需向服务器发送SSH命令到Python包。为了解释上下文,我打开一个到服务器的Ganymed连接,然后打开一个会话,然后从该会话启动一个交互式shell,这样我就可以导入我的自定义Python类,并在应用程序上发生更新时从该类调用一个函数来输入数据。我不能发出单独的命令,因为每次打开Python实例、导入、打开服务器上的ZMQ套接字等都需要很长时间

下面是打开shell的代码:

session = connection.openSession();
session.requestDumbPTY();
session.startShell();
os = session.getStdin();
os.write("python\n".getBytes());
os.write("from package.data_receiver import DataReceiver\n".getBytes());
os.write("DR=DataReceiver()\n".getBytes());
os.write("DR.open_socket()\n".getBytes()); //opens the zmq socket on server
os
是Java类中的一个
OutputStream
全局变量,我的另一个方法可以调用它
write()
on在Python类
DR
上运行命令

但是,当我想关闭连接/会话/输出流时,问题就会出现

os.write("DR.close_socket()\n".getBytes()); //closes the zmq socket on server
os.write("exit()\n".getBytes()); //exits python
os.write("exit\n".getBytes()); //exits the shell

os.close();
session.close();
connection.close();
当运行此代码时,我得到
W/TransportManager:Receive thread:receiveLoop中的错误:Socket closed
,最后一行:
DR.close\u Socket()
没有运行。我不完全确定是否需要关闭任何或所有这些,因为我可以关闭OutputStream,最后一个命令仍将在远程服务器上执行。任何提示都将不胜感激。谢谢


编辑:是的,刚刚检查过,如果我没有调用
connection.close()
,那么以前的连接对服务器仍然保持活动状态,但是如果我只调用了这个连接,我会收到错误,最后一个命令不会运行。

我想我找到了解决这个特定问题的方法:无论出于什么原因,如果我删除该行以退出shell,并且只保留关闭连接的行,那么最后的命令仍然会执行,并且连接也会成功关闭。我之前遇到的错误仍然发生在我使用
connection.close()
时,但似乎一切正常

我删除了:

os.write("exit\n".getBytes());
我保持:

connection.close();

哪一行抛出异常?@user207421对,关闭连接代码与上述代码位于同一类中的单独方法中,因此它可以访问全局类变量os、session和connection。第一个块位于名为getSession()的方法中,第二个块位于closeConnection()中,因此无论何时必须关闭连接,都可以调用第二个块。无论何时调用session.close(),还是调用connection.close(),而不是os.close(),都会发生错误。我建议
os.close()
关闭会话。我需要它来终止与服务器的连接,但是如果我只运行
os.close()
,它将保持打开状态。无论是否关闭OutputStream,最后一个命令都能完美地执行,但是它会保持连接打开。关闭连接会抛出错误,最后一个命令不会执行,但它确实成功地关闭了连接。它几乎就像是在我的
close_socket
行之前运行。对输出流的写入是在后台完成的吗?啊,我现在明白了。OutputStream只将命令写入交互式shell而不等待,远程服务器按顺序接收这些命令,立即连续执行每个命令。但是,如果不检查应用程序端的输出,它就无法知道何时完成。我完全假设它一直等到每个命令都是用
os.write编写的,但是现在我正在检查服务器是否返回了响应代码,然后等待!现在可以很好地工作了。接下来:实际的问题是,在关闭SSH连接之前,我没有等待最后一个命令运行。我将其设置为Python服务器通过打印一个文本字符串进行响应,并等待Android应用程序收到该特定输出,然后关闭连接。现在效果很好!