mirror of https://github.com/longtai-cn/hippo4j
扩展 Web Server 容器线程池动态调参、监控. (#68)
parent
42a13cd3a5
commit
1e912e2223
@ -0,0 +1,45 @@
|
||||
package cn.hippo4j.starter.controller;
|
||||
|
||||
import cn.hippo4j.common.api.ThreadDetailState;
|
||||
import cn.hippo4j.common.model.PoolParameterInfo;
|
||||
import cn.hippo4j.common.model.PoolRunStateInfo;
|
||||
import cn.hippo4j.common.web.base.Result;
|
||||
import cn.hippo4j.common.web.base.Results;
|
||||
import cn.hippo4j.starter.handler.web.WebThreadPoolRunStateHandler;
|
||||
import cn.hippo4j.starter.handler.web.WebThreadPoolService;
|
||||
import lombok.AllArgsConstructor;
|
||||
import org.springframework.web.bind.annotation.*;
|
||||
|
||||
import java.util.concurrent.Executor;
|
||||
|
||||
/**
|
||||
* Web thread pool controller.
|
||||
*
|
||||
* @author chen.ma
|
||||
* @date 2022/1/19 20:54
|
||||
*/
|
||||
@CrossOrigin
|
||||
@RestController
|
||||
@AllArgsConstructor
|
||||
public class WebThreadPoolController {
|
||||
|
||||
private final WebThreadPoolService webThreadPoolService;
|
||||
|
||||
private final ThreadDetailState threadDetailState;
|
||||
|
||||
private final WebThreadPoolRunStateHandler webThreadPoolRunStateHandler;
|
||||
|
||||
@GetMapping("/web/run/state")
|
||||
public Result<PoolRunStateInfo> getPoolRunState() {
|
||||
Executor webThreadPool = webThreadPoolService.getWebThreadPool();
|
||||
PoolRunStateInfo poolRunState = webThreadPoolRunStateHandler.getPoolRunState(null, webThreadPool);
|
||||
return Results.success(poolRunState);
|
||||
}
|
||||
|
||||
@PostMapping("/web/update/pool")
|
||||
public Result<Void> updateWebThreadPool(@RequestBody PoolParameterInfo poolParameterInfo) {
|
||||
webThreadPoolService.updateWebThreadPool(poolParameterInfo);
|
||||
return Results.success();
|
||||
}
|
||||
|
||||
}
|
@ -0,0 +1,38 @@
|
||||
package cn.hippo4j.starter.handler.web;
|
||||
|
||||
import java.util.concurrent.Executor;
|
||||
|
||||
/**
|
||||
* Abstract web thread pool service.
|
||||
*
|
||||
* @author chen.ma
|
||||
* @date 2022/1/19 21:20
|
||||
*/
|
||||
public abstract class AbstractWebThreadPoolService implements WebThreadPoolService {
|
||||
|
||||
/**
|
||||
* Thread pool executor.
|
||||
*/
|
||||
protected volatile Executor executor;
|
||||
|
||||
/**
|
||||
* Get web thread pool by server.
|
||||
*
|
||||
* @return
|
||||
*/
|
||||
protected abstract Executor getWebThreadPoolByServer();
|
||||
|
||||
@Override
|
||||
public Executor getWebThreadPool() {
|
||||
if (executor == null) {
|
||||
synchronized (AbstractWebThreadPoolService.class) {
|
||||
if (executor == null) {
|
||||
executor = getWebThreadPoolByServer();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return executor;
|
||||
}
|
||||
|
||||
}
|
@ -0,0 +1,61 @@
|
||||
package cn.hippo4j.starter.handler.web;
|
||||
|
||||
import cn.hippo4j.common.model.PoolParameterInfo;
|
||||
import lombok.AllArgsConstructor;
|
||||
import lombok.extern.slf4j.Slf4j;
|
||||
import org.springframework.boot.web.embedded.tomcat.TomcatWebServer;
|
||||
import org.springframework.boot.web.servlet.context.ServletWebServerApplicationContext;
|
||||
|
||||
import java.util.concurrent.Executor;
|
||||
import java.util.concurrent.ThreadPoolExecutor;
|
||||
import java.util.concurrent.TimeUnit;
|
||||
import java.util.concurrent.atomic.AtomicBoolean;
|
||||
|
||||
/**
|
||||
* Tomcat web thread pool handler.
|
||||
*
|
||||
* @author chen.ma
|
||||
* @date 2022/1/19 20:57
|
||||
*/
|
||||
@Slf4j
|
||||
@AllArgsConstructor
|
||||
public class TomcatWebThreadPoolHandler extends AbstractWebThreadPoolService {
|
||||
|
||||
private final ServletWebServerApplicationContext applicationContext;
|
||||
|
||||
private final AtomicBoolean cacheFlag = new AtomicBoolean(Boolean.FALSE);
|
||||
|
||||
private static String EXCEPTION_MESSAGE;
|
||||
|
||||
@Override
|
||||
protected Executor getWebThreadPoolByServer() {
|
||||
if (cacheFlag.get()) {
|
||||
log.warn("Exception getting Tomcat thread pool. Exception message :: {}", EXCEPTION_MESSAGE);
|
||||
return null;
|
||||
}
|
||||
|
||||
Executor tomcatExecutor = null;
|
||||
try {
|
||||
tomcatExecutor = ((TomcatWebServer) applicationContext.getWebServer()).getTomcat().getConnector().getProtocolHandler().getExecutor();
|
||||
} catch (Exception ex) {
|
||||
cacheFlag.set(Boolean.TRUE);
|
||||
EXCEPTION_MESSAGE = ex.getMessage();
|
||||
log.error("Failed to get Tomcat thread pool. Message :: {}", EXCEPTION_MESSAGE);
|
||||
}
|
||||
|
||||
return tomcatExecutor;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void updateWebThreadPool(PoolParameterInfo poolParameterInfo) {
|
||||
ThreadPoolExecutor tomcatExecutor = (ThreadPoolExecutor) executor;
|
||||
try {
|
||||
tomcatExecutor.setCorePoolSize(poolParameterInfo.getCoreSize());
|
||||
tomcatExecutor.setMaximumPoolSize(poolParameterInfo.getMaxSize());
|
||||
tomcatExecutor.setKeepAliveTime(poolParameterInfo.getKeepAliveTime(), TimeUnit.SECONDS);
|
||||
} catch (Exception ex) {
|
||||
log.error("Failed to modify the Tomcat thread pool parameter.", ex);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
@ -0,0 +1,30 @@
|
||||
package cn.hippo4j.starter.handler.web;
|
||||
|
||||
import cn.hippo4j.common.model.PoolParameterInfo;
|
||||
import lombok.AllArgsConstructor;
|
||||
import org.springframework.boot.web.servlet.context.ServletWebServerApplicationContext;
|
||||
|
||||
import java.util.concurrent.Executor;
|
||||
|
||||
/**
|
||||
* Undertow web thread pool handler.
|
||||
*
|
||||
* @author chen.ma
|
||||
* @date 2022/1/19 21:19
|
||||
*/
|
||||
@AllArgsConstructor
|
||||
public class UndertowWebThreadPoolHandler extends AbstractWebThreadPoolService {
|
||||
|
||||
private final ServletWebServerApplicationContext applicationContext;
|
||||
|
||||
@Override
|
||||
protected Executor getWebThreadPoolByServer() {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void updateWebThreadPool(PoolParameterInfo poolParameterInfo) {
|
||||
|
||||
}
|
||||
|
||||
}
|
@ -0,0 +1,19 @@
|
||||
package cn.hippo4j.starter.handler.web;
|
||||
|
||||
import cn.hippo4j.common.model.PoolRunStateInfo;
|
||||
import cn.hippo4j.starter.handler.AbstractThreadPoolRuntime;
|
||||
|
||||
/**
|
||||
* Web thread pool run state handler.
|
||||
*
|
||||
* @author chen.ma
|
||||
* @date 2022/1/19 21:05
|
||||
*/
|
||||
public class WebThreadPoolRunStateHandler extends AbstractThreadPoolRuntime {
|
||||
|
||||
@Override
|
||||
protected PoolRunStateInfo supplement(PoolRunStateInfo basePoolRunStateInfo) {
|
||||
return basePoolRunStateInfo;
|
||||
}
|
||||
|
||||
}
|
@ -0,0 +1,29 @@
|
||||
package cn.hippo4j.starter.handler.web;
|
||||
|
||||
import cn.hippo4j.common.model.PoolParameterInfo;
|
||||
|
||||
import java.util.concurrent.Executor;
|
||||
|
||||
/**
|
||||
* Web thread pool service.
|
||||
*
|
||||
* @author chen.ma
|
||||
* @date 2022/1/19 20:51
|
||||
*/
|
||||
public interface WebThreadPoolService {
|
||||
|
||||
/**
|
||||
* Get web thread pool.
|
||||
*
|
||||
* @return Tomcat、Jetty、Undertow ThreadPoolExecutor
|
||||
*/
|
||||
Executor getWebThreadPool();
|
||||
|
||||
/**
|
||||
* Update web thread pool.
|
||||
*
|
||||
* @param poolParameterInfo
|
||||
*/
|
||||
void updateWebThreadPool(PoolParameterInfo poolParameterInfo);
|
||||
|
||||
}
|
Loading…
Reference in new issue