복붙노트

[SPRING] Spring ThreadPoolTaskExecutor는 하나의 쓰레드만을 실행합니다.

SPRING

Spring ThreadPoolTaskExecutor는 하나의 쓰레드만을 실행합니다.

우리는 JMS 소비자에서 ThreadPoolExecutor를 사용하여이를 DefaultMessageListenerContainer에 주입합니다. 이 많은 스레드에 대한 동시 스레드를 실행하는 것으로 기대하지만 우리의 로그는 스레드 ID가 변경되지 않습니다 보여줍니다. 우리의 로깅 메시지의 다른 처리에 대한 스레드 ID는 항상 동일합니다 보여줍니다 24.

이 시나리오의 스프링 구성입니다.

<bean class="org.springframework.jms.listener.DefaultMessageListenerContainer"       
         p:connectionFactory-ref="cachedConnectionFactory"
         p:destination-ref="formsCRRDestination"
         p:messageListener-ref="formServicePojo"
         p:concurrentConsumers="5"
         p:idleTaskExecutionLimit="1"
         p:maxConcurrentConsumers="25"
         p:taskExecutor-ref="threadPoolExecutor"         
         destroy-method="doShutdown"     
    >   


 <bean id="threadPoolExecutor" class="org.springframework.scheduling.concurrent.ThreadPoolTaskExecutor" >
        <property name="corePoolSize" value="1"/>
        <property name="maxPoolSize" value="15"/>
        <property name="keepAliveSeconds" value="30"/>
    </bean>

threadPoolExectuor 빈을 DefaultMessageListenerContainer에 삽입하지 않으면 메시지가 다른 스레드에서 실행 중입니다.

결과 구성은 다음과 같습니다.

<bean class="org.springframework.jms.listener.DefaultMessageListenerContainer"       
             p:connectionFactory-ref="cachedConnectionFactory"
             p:destination-ref="formsCRRDestination"
             p:messageListener-ref="formServicePojo"
             p:concurrentConsumers="5"
             p:idleTaskExecutionLimit="1"
             p:maxConcurrentConsumers="25"       
             destroy-method="doShutdown"     
        >   

설명서를 읽으려고했지만 왜 이런 일이 발생하는지 이해하지 못합니다. 설명이 뭐야?

해결법

  1. ==============================

    1.이 시도:

    이 시도:

    <bean id="threadPoolTaskExecutor"
            class="org.springframework.scheduling.concurrent.ThreadPoolTaskExecutor">
            <property name="corePoolSize" value="10" />
            <property name="maxPoolSize" value="25" />
            <property name="queueCapacity" value="30" />
    </bean>
    
  2. ==============================

    2.Spring의 ThreadPoolTaskExecutor 코드를 살펴본 후 ThreadPoolTaskExecutor에 대한 Java 문서를 읽은 후에 이것이 대답이라고 생각합니다.

    Spring의 ThreadPoolTaskExecutor 코드를 살펴본 후 ThreadPoolTaskExecutor에 대한 Java 문서를 읽은 후에 이것이 대답이라고 생각합니다.

    위의 설정에서 우리는 기본적으로 LinkedBlockingQueue를 사용했으며 corePoolSize는 1입니다. 따라서 maximumPoolSize는 아무런 효과가 없습니다.

  3. ==============================

    3.내가 선택한 대답이 잘못되었다고 생각합니다. IIRC, ThreadPoolTaskExecutor (결국 JDK의 ThreadPoolExecutor)가 작동하는 방식

    내가 선택한 대답이 잘못되었다고 생각합니다. IIRC, ThreadPoolTaskExecutor (결국 JDK의 ThreadPoolExecutor)가 작동하는 방식

    그래서 내가 생각하기에 문제는 1) 고객이 충분히 빠르다. 2) 요청을 너무 천천히 스태킹하고 있기 때문에 corePoolSize로 지정한 하나의 스레드가 새로운 들어오는 요청을 처리하기에 충분했다. + ThreadPoolTaskExecutor가 새 스레드를 만들지 않고 대기중인 작업을 처리하기에 충분했다. . 좀 더 세게 누르거나 작은 숫자 (예 : 5 ~ 10)로 큐의 용량을 설정하면 스레드 수가 증가하는 것을 볼 수 있습니다.

  4. ==============================

    4.corePoolSize를 10으로 변경하면 10 개의 스레드가 동시에 실행됩니다. Spring ThreadPoolTaskExecutor의 백본 인 java.util.concurrent.ThreadPoolExecutor의 javadoc을 읽으면 corePoolSize 및 maxPoolSize 및 queueCapacity를 구성하는 방법을 더 잘 이해할 수 있습니다.

    corePoolSize를 10으로 변경하면 10 개의 스레드가 동시에 실행됩니다. Spring ThreadPoolTaskExecutor의 백본 인 java.util.concurrent.ThreadPoolExecutor의 javadoc을 읽으면 corePoolSize 및 maxPoolSize 및 queueCapacity를 구성하는 방법을 더 잘 이해할 수 있습니다.

  5. from https://stackoverflow.com/questions/4269559/spring-threadpooltaskexecutor-only-running-one-thread by cc-by-sa and MIT license