简体   繁体   English

Java Web应用程序与Web服务之间的线程间通信

[英]inter thread communication between java web application and web service

some premise changed on my original question posted in inter-thread communication between java application and jax-ws web service ( i am also simplifying the question to make it simpler to understand (and hence get answered)... hope that's ok with the moderators.) 在Java应用程序和jax-ws Web服务之间的线程间通信中发布的原始问题的某些前提发生了变化(我也在简化该问题,以使其更易于理解(并因此得到回答)...希望主持人可以)

a web service thread (THREAD-1) places a request on a socket and goes to sleep waiting for the response. Web服务线程(THREAD-1)在套接字上发出请求,然后进入睡眠状态以等待响应。 another listener thread (THREAD-2) (running as a separate web application, once it receives the response) has to wake up THREAD-1 out of its sleep. 另一个侦听器线程(THREAD-2)(一旦收到响应,就作为单独的Web应用程序运行)必须将THREAD-1唤醒。

how do i do that ( in a push notification way)? 我该怎么做(以推送通知的方式)?

They both have access to a database table. 他们俩都可以访问数据库表。 The THREAD-1 can put its unique id in the table before it goes to sleep. THREAD-1可以在睡觉之前将其唯一的ID放在表中。 THREAD-2, once it receives the response and determines it belongs to THREAD-1, it updates the appropriate row in the database table. THREAD-2,一旦收到响应并确定它属于THREAD-1,就更新数据库表中的相应行。 Now THREAD-1 can do polling (at regular intervals) on the database table to check if the response has arrived. 现在,THREAD-1可以(定期)对数据库表进行轮询,以检查响应是否到达。

But I am looking to do it in a push-notification way. 但我希望以推送通知的方式进行。 The THREAD-1 should be notified right away when the response has arrived without it having to poll every few seconds. 响应到达时应立即通知THREAD-1,而不必每隔几秒钟轮询一次。

If your backend request completes quickly and you won't have a torrent of client requests to handle, you can have the web service wait for a response over the same socket it just opened. 如果您的后端请求很快完成,并且您将没有大量的客户端请求要处理,则可以让Web服务在刚刚打开的同一套接字上等待响应。 It can block waiting to read the response. 它可以阻止等待读取响应。

However, if you have access to Servlet 3.0 (eg Tomcat 7), you can use asynchronous HTTP requests . 但是,如果可以访问Servlet 3.0(例如Tomcat 7),则可以使用异步HTTP请求 It allows you to release the thread handling the web service client back into the pool without responding to the client's request. 它允许您将处理Web服务客户端的线程释放回池中,而无需响应客户端的请求。 When a response message arrives from the backend service, the grabs the appropriate web service client request from the servlet container and sends the final response back to the web service client. 当响应消息从后端服务到达时,抓取将从servlet容器中获取适当的Web服务客户端请求,并将最终响应发送回Web服务客户端。

Well, as the comment suggest: better don't try to implement this yourself. 好吧,正如评论所建议的那样:最好不要尝试自己实现这一点。 However, basically you could use standard Java thread-synchronization with wait()/notify() 但是,基本上,您可以将标准Java线程同步与wait()/ notify()结合使用

  • Thread-1 sets of remote call to Thread-2 together with a unique call-ID. 线程1对线程2的远程调用集以及唯一的调用ID。
  • Thread-1 does now wait() on a synchronization object (instead of sleep() ) 线程1现在在同步对象上执行了wait() (而不是sleep()
  • Thread-2 does the work and to return the result it calls some remote callback method in the JVM Thread-1 resides in - call-ID is passed together with the result 线程2进行工作,并返回结果,它在JVM线程1中驻留了一些远程回调方法-调用ID与结果一起传递
  • The callback method on the Thread-1 side makes the result available via call-ID and wakes up all waiting threads by means of notifyAll() Thread-1端的回调方法使结果可通过call-ID获得,并通过notifyAll()唤醒所有等待的线程
  • Threads incl. 含螺纹 Thread-1 check if their result arrived, if yes they continue to work if no the wait() again. 线程1检查其结果是否到达,如果是,则再次继续执行wait() ,它们将继续工作。

Pseudo code for the Thread-1 side: 线程1端的伪代码:

HashMap<String, Object> results;

// Called by Thread-1 to access Thread-2
public void doIt() {
    String callId = "aUniqueCallId";
    Object result = null;
    remoteCallToThread2(callId);
    synchronized(results) {
        while((result = results.remove(callId)) == null) {
            results.wait();
        }
    }
    doSomethingWith(result);
}

// Called remotely by Thread-2 when result is available
public void callback(String callId, Object result) {    
    synchronized(results) {
        results.put(callId, result);
        results.notifyAll();
    } 
}

Of course this is just the basic idea and can not be used as such, there's a lot of stuff to be considered here. 当然,这只是基本思想,不能被如此使用,这里有很多东西要考虑。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM