Reputation: 188
Sorry for formatting issue...
I've been trying to understand this for around 4 hours now. Basically I have a method that will call a private method that uses ThreadPoolTaskExecutor.
public ThreadPoolTaskExecutor someTaskExecutor() {
final ThreadPoolTaskExecutor taskExecutor = new ThreadPoolTaskExecutor();
taskExecutor.setCorePoolSize(0);
taskExecutor.setMaxPoolSize(3);
taskExecutor.setKeepAliveSeconds(60);
taskExecutor.setQueueCapacity(3);
taskExecutor.afterPropertiesSet();
return taskExecutor;}
This is how I use it. Dont mind the "DTO" and "Obj", just made it a placeholder
@Override
public void processMessage(final DTO dto) throws Exception {
log.info("MainThread BEFORE [{}] : [{}] - [{}]", dto.getTaskId(), Thread.currentThread().getName(), Thread.currentThread().getId());
final Object obj = save(dto);
log.info("MainThread SAVED [{}] : [{}] - [{}]", dto.getTaskId(), Thread.currentThread().getName(), Thread.currentThread().getId());
generateSomething(obj);
log.info("MainThread AFTER [{}] : [{}] - [{}]", dto.getTaskId(), Thread.currentThread().getName(), Thread.currentThread().getId());
}
private void generateSomething(final Object obj) {
someTaskExecutor.execute(() -> {
log.info("thread START [{}] : [{}] - [{}]", obj.getTaskId(), Thread.currentThread().getName(), Thread.currentThread().getId());
//SOME API CALL THAT TAKES 3 second
log.info("thread DONE [{}] : [{}] - [{}]", obj.getTaskId(), Thread.currentThread().getName(), Thread.currentThread().getId());
});
With the current setting of my threadpooltaskexecutor, when I have 10 concurrent call to the main method (which produces 10 main thread), only 6 thread successfully went through the "MainThread AFTER" which is called after calling the the private method which has threadpooltaskexecutor execute.
I am at lost currently, my understanding that the main/caller threads should not be affected by the new threads spawned by the threadpooltaskexecutor, and why is it being directly affected by queue capacity. If I make the queue capacity at 5 instead of 3, 8 main threads will go through properly. If I left it unset, all main thread will go through properly.
Thanks for the help, again sorry for the formatting.
Upvotes: 0
Views: 2322
Reputation: 116888
I am at lost currently, my understanding that the main/caller threads should not be affected by the new threads spawned by the threadpooltaskexecutor, and why is it being directly affected by queue capacity. If I make the queue capacity at 5 instead of 3, 8 main threads will go through properly. If I left it unset, all main thread will go through properly.
You are setting up a ThreadPoolTaskExecutor
(under the covers it is a ThreadPoolExecutor
) that has a maximum of 3 threads and a queue-limit of 3 as well. If you submit 10 jobs to this executor and the jobs take a while to complete, then 3 tasks will start running, 3 will go into the queue, and when you try to submit the 7th task, the caller will block. That's how it works. If you increase the number of queued tasks or increase the number of threads that can work on those tasks then the caller will block later.
Why is blocking important? Let's say you have an application that needs to do 1,000,000 jobs. You can't spawn 1,000,000 threads so you have to queue up jobs. If the jobs are large in memory you might run out of heap space holding that many – or think about scaling to 100 million. By blocking, the system keeps its thread and memory usage low while still keeping the throughput high. You want to queue up some jobs so the threads can easily take them off the queue and start working but not too many that they take memory resources that the application needs.
Upvotes: 1