How do I properly do a background thread when using Spring Data and Hibernate?

后端 未结 3 745
小鲜肉
小鲜肉 2020-11-28 11:00

I\'m building a simple Tomcat webapp that\'s using Spring Data and Hibernate. There\'s one end point that does a lot of work, so I want to offload the work to a background t

3条回答
  •  情歌与酒
    2020-11-28 11:11

    With Spring you don't need your own executor. A simple annotation @Async will do the work for you. Just annotate your heavyMethod in your service with it and return void or a Future object and you will get a background thread. I would avoid using the async annotation on the controller level, as this will create an asynchronous thread in the request pool executor and you might run out of 'request acceptors'.

    The problem with your lazy exception comes as you suspected from the new thread which does not have a session. To avoid this issue your async method should handle the complete work. Don't provide previously loaded entities as parameters. The service can use an EntityManager and can also be transactional.

    I for myself dont merge @Async and @Transactional so i can run the service in either way. I just create async wrapper around the service and use this one instead if needed. (This simplifies testing for example)

    @Service
    public class AsyncService {
    
        @Autowired
        private Service service;
    
        @Async
        public void doAsync(int entityId) {
            service.doHeavy(entityId);
        }
    }
    
    @Service
    public class Service {
    
        @PersistenceContext
        private EntityManager em;
    
        @Transactional
        public void doHeavy(int entityId) {
            // some long running work
        }
    }
    

提交回复
热议问题