I'm running a very simplistic Undertow configuration. Whole code included:
public class HelloWorldUndertow {
public static void main(String[] args) {
Undertow undertow = Undertow.builder()
.addHttpListener(9090, "0.0.0.0")
.setHandler(new HttpHandler() {
@Override
public void handleRequest(HttpServerExchange exchange) throws Exception {
exchange.setResponseCode(200);
exchange.getResponseSender().send("hello!");
}
}).build();
undertow.start();
}
}
I try to test how many requests per second it can handle. I'm using apache ab
tool for measurements:
ab -n 100000 -c 10 http://localhost:9090/test
The biggest number I managed to get is around 10000 3/sec:
Concurrency Level: 10
Time taken for tests: 10.664 seconds
Complete requests: 100000
Failed requests: 0
Total transferred: 10000000 bytes
HTML transferred: 600000 bytes
Requests per second: 9377.69 [#/sec] (mean)
Time per request: 1.066 [ms] (mean)
Time per request: 0.107 [ms] (mean, across all concurrent requests)
Transfer rate: 915.79 [Kbytes/sec] received
Connection Times (ms)
min mean[+/-sd] median max
Connect: 0 0 0.2 0 1
Processing: 0 1 0.5 1 11
Waiting: 0 1 0.5 1 11
Total: 0 1 0.5 1 11
Percentage of the requests served within a certain time (ms)
50% 1
66% 1
75% 1
80% 1
90% 2
95% 2
98% 2
99% 2
100% 11 (longest request)
I get that it is BIG, but I'm curoius what is a limiting factor in this case. It's not processor (the app is running below 20% when sampled using Java Mission Control) and not memory. I'm running it on Windows - maybe that is the reason?
I can't tell you how to make it perform better when running in Windows, but if you run it in Linux you can do the tuning recommended for Jetty here: https://eclipse.dev/jetty/documentation/jetty-9/index.html#high-load
In summary:
sysctl -w net.core.rmem_max=16777216
sysctl -w net.core.wmem_max=16777216
sysctl -w net.ipv4.tcp_rmem="4096 87380 16777216"
sysctl -w net.ipv4.tcp_wmem="4096 16384 16777216"
sysctl -w net.core.somaxconn=4096
sysctl -w net.core.netdev_max_backlog=16384
sysctl -w net.ipv4.tcp_max_syn_backlog=8192
sysctl -w net.ipv4.tcp_syncookies=1
sysctl -w net.ipv4.ip_local_port_range="1024 65535"
sysctl -w net.ipv4.tcp_tw_recycle=1
sysctl -w net.ipv4.tcp_congestion_control=cubic
Include the -server
JVM param when you run your code.
Then try:
ab -n 100000 -c 100 http://localhost:9090/test
(make 100,000 requests using 100 connections)
When I try that in a Linux VM running in VMware Player on my Windows 7 laptop (3 years old) I get over 100,000 requests per second.