2

尽管在网络上进行了许多研究,但我找不到任何解决我的问题的方法。我想从 GUI 调用服务。服务(一种 Rest 方法)使用线程启动异步处理。我希望服务立即对 GUI 做出响应,这样 GUI 就不会被阻塞。在线程结束时,服务应该给出第二个响应,指示处理完成的 GUI。

我想做的似乎对应于 Reasteasy 的异步 HTTP 部分。所以,我试过这段代码(我只让我的问题的重要部分):

@PUT
@Path("/duplicate/1")
public void duplicate(  UcModel uc,
                                final @Suspend(TIMEOUT_ASYNCHRONOUS_DUPLICATION) AsynchronousResponse response) throws BusinessException {


        Thread t = new Thread() {
            @Override
            public void run() {

                try {
                    Thread.sleep(40000);
                } catch (InterruptedException e) {
                }

                Response jaxrs = Response.ok(result).build();
                response.setResponse(jaxrs);
            }
        };
        t.start();
    }
}

在我的 web.xml 中,我输入了以下代码:

<servlet>
    <servlet-name>resteasy-servlet</servlet-name>
    <servlet-class>
        org.jboss.resteasy.plugins.server.servlet.HttpServlet30Dispatcher
    </servlet-class>
    <async-supported>true</async-supported>
</servlet>

问题是:Web 服务没有立即给出响应。它仅在线程结束时给出响应,并且 GUI 被阻塞。通过查看代码,我什至不明白服务如何立即给出“无效”结果的响应。

有关信息:Web 服务的调用是在 ExtJS(一个 Javascript 框架)中进行的。它执行 Ajax 请求。

如果有人可以帮助我解决这个问题,那就太好了。提前致谢

塞德里克

4

1 回答 1

5

您应该使用两种不同的 Web 服务来解决此问题。

主要AsynchronousResponse是为了帮助服务器线程池性能,而不是为了客户端。

服务器在线程池中的线程数量有限,可以为客户端的请求提供服务,在您的帮助下,AsynchronousResponse您可以将耗时的作业放在后台线程中。

客户端将不得不等待异步进程完成或超时。只有在那之后才会提交响应,因此对于客户端而言,完成请求几乎需要相同的时间。

其他选择是尝试ChunkedOutput可以在此处找到的 java 类。

这是用于以“类型化”块发送消息。对于需要产生部分响应的长时间运行的进程很有用。

一个例子:

@Path("/test")
public class TestResource {
    @GET
    public ChunkedOutput getTestResponse() {
        final ChunkedOutput chunkedOutputs = new ChunkedOutput(String.class); 
        new Thread() {
            public void run() {
                try {                   
                    while (hasNextValue()) {                         
                         chunkedOutputs.write(getNextLongRunningOperationValue());
                    }                    
                } catch (IOException e) {
                    (...)
                } finally {
                    chunkedOutputs.close();                        
                }
            }
        }.start(); 
        //the chunkedOutputs will be probably returned even before a first value is written by the new thread
        return chunkedOutputs;
    }   

    private boolean hasNextValue() {
        (...)
    }

    private String getNextLongRunningOperationValue() {
        (...) //this takes a lot of time, so it's time for a coffee :)        
    }
}
于 2013-08-29T15:52:53.570 回答