source

별도의 스레드 풀에서 실행되는 스프링 부트 액추에이터

nicesource 2023. 9. 11. 21:53
반응형

별도의 스레드 풀에서 실행되는 스프링 부트 액추에이터

다음과 같은 액추에이터 요청을 처리할 수 있습니까?health"메인" 애플리케이션과 별도의 스레드 풀 내에 있습니까?

왜 묻는 거지?때때로 사용 가능한 모든 스레드를 다 사용할 수 있는 애플리케이션이 있는데 상태 엔드포인트 요청을 계산할 스레드를 사용할 수 없어 Kubernetes 상태 검사가 실패하고 있습니다.

애플리케이션의 부하가 얼마나 걸리든 간에 모든 보건 요청이 처리되도록 하고 싶습니다.

액츄에이터가 작동할 별도의 스레드 풀을 정의할까 생각 중이었는데, 어떻게 해야 할지 모르겠습니다.

Kubernetes에서 실행할 때 일부 앱에서 유사한 문제가 발생했습니다.원하는 효과를 얻기 위해 여러 개Tomcat 커넥터를 만들고 스프링 관리 포트를 변경하는 다양한 방법을 살펴보았지만 결코 얻을 수 없었습니다.

결국, 우리는 문제의 근원을 공격했는데, 그것은 포드 내부의 자원 기아였습니다.상태 체크 타임아웃이 발생한 앱에는 다양한 타사 스레드 풀에 대한 추가 스레드가 많이 포함되어 있음을 발견했습니다.경우에 따라서는 500개에 가까운 스레드를 가진 앱을 사용했기 때문에 중간 로드라고 생각한 상황에서도 Tomcat 풀은 부족해지고 새로운 요청을 처리할 수 없었습니다.

FWIW, 우리가 발견한 가장 큰 원인은 포드와 JDK에 대한 CPU 요청의 영향이었습니다.우리가 어떠한 요청도 설정하지 않았을 때, JDK는 프로세서의 수를 조회할 때 노드의 모든 CPU를 보게 됩니다.Java 에코시스템에는 다양한 스레드 풀을 초기화하는 데 사용되는 프로세서의 수가 많다는 사실을 알게 되었습니다.

우리의 경우, 각 노드에 36개의 프로세서가 있었고, 이 숫자를 사용하여 크기를 결정하는 약 10-12개의 스레드 풀을 찾았습니다.앱이 어떻게 500개의 스레드로 빠르게 성장할 수 있는지 알기란 어렵지 않습니다.

저는 비차단 스택(Webflux)으로 전환하는 것이 당신의 문제를 해결할 수 있다고 생각합니다. 이것이 당신에게 선택사항이 되어야 할까요?일부 차단 API(예: JDBC)를 사용하는 경우 별도의 스레드 풀(예: Schedulers.elastic())에 게시할 수 있습니다.따라서 HTTP 요청 스레드는 항상 수신 트래픽(상태 검사 포함) 처리에 사용 가능해야 하며, 장기간 실행되는 차단 작업은 전용 스레드 풀에서 처리됩니다.저는 비동기 서블릿 API나 그 위에 구축되는 어떤 것을 사용해도 비슷한 효과가 가능할 것이라고 생각합니다.

Spring Boot >= 2.2를 사용하는 경우 별도의 라이브러리 spring-boot-forc-health-forc를 사용하여 별도의 스레드 풀에서 상태 검사를 실행할 수 있습니다.

을 만 에 을 달기만 됩니다.HealthIndicator와 함께@AsyncHealth:

@AsyncHealth
@Component
public class AsynchronousHealthCheck implements HealthIndicator {

    @Override
    public Health health() { //will be executed on a separate thread pool
        actualCheck();
        return Health.up().build();
    }

}

면책 사항:나는 이 도서관을 정확한 목적으로 만들었습니다.

언급URL : https://stackoverflow.com/questions/58921470/spring-boot-actuator-to-run-in-separate-thread-pool

반응형