私はGWTサービスサーブレット(RemoteServiceServletのインスタンス)を作成しており、クライアントからfileIDが与えられているので、DBからファイルを取得してクライアントにプッシュすることが目的です。サーブレットは、エラー・メッセージをStringオブジェクトとして戻します。GWTでファイルをダウンロードするRemoteServiceServlet
私は間違っていますか?
私はこれをネット上で研究していますが、RemoteServiceServletから実行できないと主張する人もいます。
私の場合、サーバーはまずデータベースからファイルをフェッチしてからクライアントに送信する必要があるため、最初に準備する必要があります。ダウンロードをクライアントに「プッシュ」する方法はありますか、ダウンロード専用のサーブレットを作成する必要はありますか?誰かが私に例コードを与える方法はありますか?
ありがとうございます!
これは私がこれまで持っているコードと、それが生成する例外です:
public class MyServiceImpl extends RemoteServiceServlet implements MyService {
@Override
public String getFile(Long fileId) {
String errors = null;
File file = fetchFileByID(fileId);
try {
if (file != null && file.exists()) {
String name = fileLink.getName();
HttpServletResponse response = getThreadLocalResponse();
long fileLen = file.length();
if (fileLen > Integer.MAX_VALUE)
throw new IllegalStateException("File too large, cannot download using the browser.");
int length = (int) fileLen;
// do not cache
response.setHeader("Expires", "0");
response.setHeader("Cache-Control", "must-revalidate, post-check=0, pre-check=0");
response.setHeader("Pragma", "public");
// content length is needed for MSIE
response.setContentLength(length);
response.setHeader("Content-Type", "application/octet-stream;");
response.setHeader("Content-Disposition", "attachment;filename=\"" + name + "\"");
OutputStream os = response.getOutputStream();
FileInputStream is = new FileInputStream(file);
BufferedInputStream buf = new BufferedInputStream(is);
int readBytes=0;
while((readBytes=buf.read())!=-1) {
os.write(readBytes);
}
os.flush();
buf.close();
} else {
errors = "File not found.";
}
} catch (IOException e) {
errors = e.getMessage();
} finally {
if (file != null)
file.delete();
}
return errors;
}
}
サーバーは例外を生成します。
Starting Jetty on port 8888
[WARN] /saluweb/SaluService
java.lang.RuntimeException: Unable to report failure
at com.google.gwt.user.server.rpc.AbstractRemoteServiceServlet.doUnexpectedFailure(AbstractRemoteServiceServlet.java:107)
at com.google.gwt.user.server.rpc.AbstractRemoteServiceServlet.doPost(AbstractRemoteServiceServlet.java:67)
at javax.servlet.http.HttpServlet.service(HttpServlet.java:755)
at javax.servlet.http.HttpServlet.service(HttpServlet.java:848)
at org.eclipse.jetty.servlet.ServletHolder.handle(ServletHolder.java:686)
at org.eclipse.jetty.servlet.ServletHandler.doHandle(ServletHandler.java:501)
at org.eclipse.jetty.server.handler.ScopedHandler.handle(ScopedHandler.java:137)
at org.eclipse.jetty.security.SecurityHandler.handle(SecurityHandler.java:557)
at org.eclipse.jetty.server.session.SessionHandler.doHandle(SessionHandler.java:231)
at org.eclipse.jetty.server.handler.ContextHandler.doHandle(ContextHandler.java:1086)
at org.eclipse.jetty.servlet.ServletHandler.doScope(ServletHandler.java:428)
at org.eclipse.jetty.server.session.SessionHandler.doScope(SessionHandler.java:193)
at org.eclipse.jetty.server.handler.ContextHandler.doScope(ContextHandler.java:1020)
at org.eclipse.jetty.server.handler.ScopedHandler.handle(ScopedHandler.java:135)
at org.eclipse.jetty.server.handler.HandlerWrapper.handle(HandlerWrapper.java:116)
at org.eclipse.jetty.server.handler.RequestLogHandler.handle(RequestLogHandler.java:68)
at org.eclipse.jetty.server.handler.HandlerWrapper.handle(HandlerWrapper.java:116)
at org.eclipse.jetty.server.Server.handle(Server.java:370)
at org.eclipse.jetty.server.AbstractHttpConnection.handleRequest(AbstractHttpConnection.java:489)
at org.eclipse.jetty.server.AbstractHttpConnection.content(AbstractHttpConnection.java:960)
at org.eclipse.jetty.server.AbstractHttpConnection$RequestHandler.content(AbstractHttpConnection.java:1021)
at org.eclipse.jetty.http.HttpParser.parseNext(HttpParser.java:865)
at org.eclipse.jetty.http.HttpParser.parseAvailable(HttpParser.java:240)
at org.eclipse.jetty.server.AsyncHttpConnection.handle(AsyncHttpConnection.java:82)
at org.eclipse.jetty.io.nio.SelectChannelEndPoint.handle(SelectChannelEndPoint.java:668)
at org.eclipse.jetty.io.nio.SelectChannelEndPoint$1.run(SelectChannelEndPoint.java:52)
at org.eclipse.jetty.util.thread.QueuedThreadPool.runJob(QueuedThreadPool.java:608)
at org.eclipse.jetty.util.thread.QueuedThreadPool$3.run(QueuedThreadPool.java:543)
at java.lang.Thread.run(Thread.java:745)
Caused by: java.io.IOException: Closed
at org.eclipse.jetty.server.HttpOutput.write(HttpOutput.java:140)
at org.eclipse.jetty.server.HttpOutput.write(HttpOutput.java:117)
at com.google.gwt.user.server.rpc.RPCServletUtils.writeResponse(RPCServletUtils.java:375)
at com.google.gwt.user.server.rpc.RemoteServiceServlet.writeResponse(RemoteServiceServlet.java:460)
at com.google.gwt.user.server.rpc.RemoteServiceServlet.processPost(RemoteServiceServlet.java:313)
at com.google.gwt.user.server.rpc.AbstractRemoteServiceServlet.doPost(AbstractRemoteServiceServlet.java:62)
... 27 more
ファイルを直接読み込み、サーブレットをテストしようとしましたか?たぶんあなたのデータベースへのアクセスに時間がかかりますか?アプリケーションでは(私は知っている)、ファイルはまずバイト配列に入れられ、その後out.write、out.flush、out.closeが呼び出されます。そして、それは動作します。また、テスト用のMockrunner(サーブレット用)をお勧めします.GWTでうまく動作します。 – Akkusativobjekt
[この質問](http://stackoverflow.com/questions/2822667/download-dynamic-file-with-gwt)をご覧ください。 RPC呼び出しからのストリームバイナリデータを返すことはできません。標準のサーブレットから実行する必要があります。 – Baz
が、これは、専用のダウンロードサーブレットを呼び出して、ファイル名を返す経由ソリューション:)、およびクライアント側に私を導く、あなたのバズをありがとうございます。ありがとう! – Marcin