将序列化数据发送到servlet时发生java.io.EOFException
我正在从Java本地应用程序上传一个包含文件到服务器的对象。我的计划是在tomcat上运行的servlet将使用doGet
方法中的ObjectInputStream
获取对象。但我得到一个EOFE
xception`。将序列化数据发送到servlet时发生java.io.EOFException
下面是客户端代码
import java.io.*;
import java.net.*;
public class Client {
public static void main(String[] args) throws IOException {
FileInputStream inputStream = new FileInputStream("c:\\rafi.txt");
ByteArrayOutputStream output = new ByteArrayOutputStream();
byte[] buffer = new byte[1024];
int n = 0;
while (-1 != (n = inputStream.read(buffer))) {
output.write(buffer, 0, n);
}
inputStream.close();
File2 c2 = new File2(buffer);
URL url = new URL("http://localhost:8080/servertest/Server");
URLConnection cnx = url.openConnection();
cnx.setDoInput(true);
cnx.setDoOutput(true);
cnx.setRequestProperty("Content-Type", "application/octet-stream");
InputStream in = cnx.getInputStream();
OutputStream out = cnx.getOutputStream();
cnx.connect();
ObjectOutputStream oos = new ObjectOutputStream(out);
oos.writeObject(c2);
oos.flush();
oos.close();
ObjectInputStream ois = new ObjectInputStream(in);
boolean readBoolean = ois.readBoolean();
System.out.println(readBoolean);
ois.close();
in.close();
out.close();
}
}
这里是服务器的Servlet
import java.io.*;
import javax.servlet.*;
@WebServlet("/Server")
public class Server extends HttpServlet {
private static final long serialVersionUID = 1L;
public Server() {
super();
}
protected void doGet(HttpServletRequest req, HttpServletResponse res)
throws ServletException, IOException {
InputStream in = req.getInputStream();
OutputStream out = res.getOutputStream();
ObjectOutputStream oos = new ObjectOutputStream(out);
ObjectInputStream ois = new ObjectInputStream(in);
File2 data_in;
try {
data_in = (File2) ois.readObject();
byte[] a = new byte[data_in.mybytearray.length];
System.arraycopy(data_in.mybytearray, 0, a, 0,data_in.mybytearray.length);
System.out.println(a.toString());
oos.writeBoolean(true);
} catch (ClassNotFoundException e) {
// TODO Auto-generated catch block
e.printStackTrace();
oos.writeBoolean(false);
}
finally{
oos.close();
}
res.setContentType("java-internal/" + File2.class.getName());
in.close();
}
}
当调试服务器端和运行客户端我得到的异常此行中
ObjectOutputStream oos = new ObjectOutputStream(out);
这是我得到的错误
SEVERE: Servlet.service() for servlet [test1.Server] in context with path [/servertest] threw exception
java.io.EOFException
at java.io.ObjectInputStream$PeekInputStream.readFully(Unknown Source)
at java.io.ObjectInputStream$BlockDataInputStream.readShort(Unknown Source)
at java.io.ObjectInputStream.readStreamHeader(Unknown Source)
at java.io.ObjectInputStream.<init>(Unknown Source)
at test1.Server.doGet(Server.java:38)
at javax.servlet.http.HttpServlet.service(HttpServlet.java:621)
at javax.servlet.http.HttpServlet.service(HttpServlet.java:722)
at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:304)
at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:210)
at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:240)
at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:164)
at org.apache.catalina.authenticator.AuthenticatorBase.invoke(AuthenticatorBase.java:462)
at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:164)
at org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:100)
at org.apache.catalina.valves.AccessLogValve.invoke(AccessLogValve.java:562)
at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:118)
at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:395)
at org.apache.coyote.http11.Http11Processor.process(Http11Processor.java:250)
at org.apache.coyote.http11.Http11Protocol$Http11ConnectionHandler.process(Http11Protocol.java:188)
at org.apache.coyote.http11.Http11Protocol$Http11ConnectionHandler.process(Http11Protocol.java:166)
at org.apache.tomcat.util.net.JIoEndpoint$SocketProcessor.run(JIoEndpoint.java:302)
at java.util.concurrent.ThreadPoolExecutor.runWorker(Unknown Source)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(Unknown Source)
at java.lang.Thread.run(Unknown Source)
我看到这个question,但我没有帮助我。我使用Tomcat 7
InputStream in = cnx.getInputStream();
OutputStream out = cnx.getOutputStream();
的URLConnection#getInputStream()
将立即发送HTTP请求到服务器,以便检索响应主体。就像你编写代码的方式一样,这发生在之前你已经写了任何位到HTTP请求主体。因此服务器端的EOFException
。
您需要通过URLConnection#getInputStream()
后索要HTTP响应身体,你已经写了必要的数据到HTTP请求主体。这里有一个重写:
URLConnection connection = new URL("http://localhost:8080/servertest/Server").openConnection();
connection.setDoOutput(true);
connection.setRequestProperty("Content-Type", "application/octet-stream");
ObjectOutputStream oos = new ObjectOutputStream(connection.getOutputStream());
oos.writeObject(c2);
oos.close();
ObjectInputStream ois = new ObjectInputStream(connection.getInputStream());
boolean readBoolean = ois.readBoolean();
ois.close();
System.out.println(readBoolean);
而且,因为你基本上发送一个HTTP POST请求,您需要在servlet的doPost()
方法,而不是doGet()
的方法来处理这个问题。
无关到具体的问题:这是不是真的通过HTTP发送文件的最好方法。虽然它可能工作,但这与Java序列化机制紧密相关。我建议改为发送HTTP multipart/form-data
请求。这可以通过客户端上的Apache HttpComponents Client和服务器端上的Apache Commons FileUpload来实现。这样,servlet就可以用于其他目的,例如前面的<input type="file">
的HTML表单。此外,客户端可以通过这种方式将文件上传到其他HTTP网站。
我解决了这个PBM与客户端:
HttpURLConnection cnx = (HttpURLConnection) new URL("http://localhost:8080/web").openConnection();
cnx.setRequestMethod("PUT");
确定i'l检查这些阿帕奇包。 btw连接命令在哪里消失? 我试着在几个地方添加它,并且我在java.io.ObjectInputStream处获得了 $ PeekInputStream.readFully(Unknown Source) – 2011-05-17 20:52:53
您不需要它。你也开了太早。 'getInputStream()'会在适当的时候隐式地运行'connect()'。只需按照我的回答完全使用代码即可。在你原来的客户端代码中,你需要用'out.close()'替换'URL url'。这正是你所需要的,并且已经以正确的顺序。 – BalusC 2011-05-17 21:00:28
要了解更多关于使用'URLConnection'的信息,请查看这篇文章http:// *。com/questions/2793150/how-to-use-java-net-urlconnection-fire-and-handle-http-requests – BalusC 2011-05-17 21:01:32