Note that there are some explanatory texts on larger screens.

plurals
  1. POHow can I implement or find the equivalent of a thread-safe CompletionService?
    text
    copied!<p>I have a simple web service running inside a Tomcat container, which by nature is multi-threaded. In each request that comes into the service, I want to make concurrent calls to an external service. The ExecutorCompletionService in java.util.concurrent gets me partly there. I can provide it a thread pool, and it will take care of executing my concurrent calls and I will be notified when any of the results are ready.</p> <p>The code to process a particular incoming request might look like:</p> <pre><code>void handleRequest(Integer[] input) { // Submit tasks CompletionService&lt;Integer&gt; completionService = new ExecutorCompletionService&lt;Integer&gt;(Executors.newCachedThreadPool()); for (final Integer i : input) { completionService.submit(new Callable&lt;Integer&gt;() { public Integer call() { return -1 * i; } }); } // Do other stuff... // Get task results try { for (int i = 0; i &lt; input.size; i++) { Future&lt;Integer&gt; future = completionService.take(); Integer result = future.get(); // Do something with the result... } } catch (Exception e) { // Handle exception } } </code></pre> <p>This should work fine and dandy, but is quite inefficient since a new thread pool is being allocated for each incoming request. If I move the CompletionService out as a shared instance, I will run into thread-safety problems with multiple requests sharing the same CompletionService and thread pool. As requests submit tasks and get results, the results they get not be the ones they submitted.</p> <p>Thus, what I need is a thread-safe CompletionService that allows me to share a common thread pool across all incoming requests. As each thread completes a task, the appropriate thread for the incoming request should be notified so that it can gather the results.</p> <p>What's the most straightforward way to implement this sort of functionality? I'm sure this pattern has been applied many times; I'm just not sure if this is something provided by the Java concurrency library, or if can be easily built using some of the Java concurrency building blocks.</p> <p><strong>UPDATE:</strong> one caveat I forgot to mention is that I would like to be notified as soon as any of my submitted tasks complete. That's the primary advantage of using a CompletionService, as it decouples the production and consumption of the tasks and results. I don't actually care about the order in which I get the results back, and I'd like to avoid unnecessarily blocking while waiting for the results to be returned in order.</p>
 

Querying!

 
Guidance

SQuiL has stopped working due to an internal error.

If you are curious you may find further information in the browser console, which is accessible through the devtools (F12).

Reload