maxThreads
- リクエストを処理するスレッド数(workerスレッド)の上限
- 1リクエストを処理するために1workerスレッドを消費する
- コネクタ(HTTP1.1, AJPなど)ごとの上限
- ただしスレッドプールをexecutorプロパティで指定した場合、この上限は無視される
maxConnections
同時に受け付けるコネクション数の上限
workerスレッドに空きができるまで、リクエストは処理されない
Nioコネクタなら maxThreads < maxConnections が可能
- HTTP Keep Aliveごとにworkerスレッドを占有する必要がないから
- デフォルトは maxThreads=200, maxConnections=10000
- 詳細はブロッキングとかノンブロッキングを理解したい
acceptCount
保留されている(Socket#accept()されない)ソケットの上限
上限を超えたコネクションはTCPレベルで『connection refused』になる
ただしこの上限は実行環境へのヒントで、無視される可能性もある
maxConnectionsを超えたリクエストが来た場合、Acceptorスレッドを止めて待つ
図解
動作確認
検証環境
- Windows 10 Pro ver.1703
- Java HotSpot(TM) 64-Bit Server VM ver.1.8.0_25
- Apache Tomcat 8.5.23
検証コード
@RestController
@Slf4j
@SpringBootApplication
public class DemoxApplication {
@Bean
EmbeddedServletContainerCustomizer embeddedServletContainerCustomizer() {
return (container) -> {
TomcatEmbeddedServletContainerFactory factory = (TomcatEmbeddedServletContainerFactory) container;
factory.addConnectorCustomizers(
(connector) -> {
Http11NioProtocol handler = (Http11NioProtocol) connector.getProtocolHandler();
handler.setAcceptCount(1);
handler.setMaxConnections(2);
handler.setMaxThreads(1);
}
);
};
}
@GetMapping
public String hello() throws InterruptedException {
log.info("wait a seconds");
TimeUnit.SECONDS.sleep(5);
return "I'm sorry, I'm late";
}
public static void main(String[] args) {
SpringApplication.run(DemoxApplication.class);
}
}
実行結果
- コンソールログからmaxThreads分しか同時実行されない
- maxConnections + acceptCountを超えたリクエストは『connection refused』されている