Search code examples
jakarta-eecdiweld

Local Thread linked with RequestScope


I have a web service built with VRaptor that uses CDI (weld 2.1.2.Final). I need to parallelize some of the processing made by the server (statistical analysis of industrial alarms). I'm doing that using a ExecutorService and Callable instances, unfortunately I need one Request Scoped dependence inside my Threads. Because of that dependence I'm facing this error:

WELD-001303: No active contexts for scope type javax.enterprise.context.RequestScoped

Is there a way to link the Threads to the Request where they were created using CDI?

*I know that I shouldn't be opening threads in the server, but this is the currently most viable option


Solution

  • Pass it as constructor argument of the callable.

    public class YourTask implements Callable<String> {
    
        private YourData data;
    
        public YourTask(YourData data) {
            this.data = data;
        }
    
        @Override
        public String call() {
            // Just use data.
        }
    
    }
    

    @Inject
    private YourRequestScopedBean bean;
    
    public void submit() {
        YourTask task = new YourTask(bean.getData());
        // ...
    }
    

    Note: do not pass the bean itself as it's basically a proxy whose instance doesn't exist in other thread.

    See also:


    Unrelated to the concrete problem, manually managing threads in a Java EE container, even though when done via a properly programmed ExecutorService, is frowned upon. It indicates you aren't aware of possibilities of Java EE's EJB scheduling and timer APIs. You may find the examples in this answer useful: Is it safe to start a new thread in a JSF managed bean?