Я пытаюсь понять, как создать настоящий асинхронный http-сервер с помощью Undertow. Как отправить ответ асинхронно, если у меня есть другой поток, который уже обрабатывает запрос?
Я написал такой код:
Undertow server = Undertow.builder()
.addHttpListener(8080, "localhost")
.setHandler(exchange -> {
CompletableFuture.runAsync(() -> {
try {
Thread.sleep(100);
} catch (InterruptedException e) {
throw new RuntimeException(e);
}
}).thenAccept(string -> {
exchange.getResponseHeaders()
.put(Headers.CONTENT_TYPE, "text/plain");
exchange.getResponseSender().send("Hello World");
exchange.endExchange();
}).exceptionally(throwable -> {
System.out.println(throwable.toString());
return null;
});
}).build();
server.start();
но этот ответ сервера 200 без данных и в журналах
java.lang.IllegalStateException: UT000127: ответ уже отправлен
Когда я использую метод io.undertow.server.HttpServerExchange#dispatch(java.lang.Runnable) следующим образом:
Undertow server = Undertow.builder()
.addHttpListener(8080, "localhost")
.setHandler(exchange -> {
exchange.dispatch(() -> {
CompletableFuture.runAsync(() -> {
try {
Thread.sleep(100);
} catch (InterruptedException e) {
throw new RuntimeException(e);
}
}).thenAccept(string -> {
exchange.getResponseHeaders()
.put(Headers.CONTENT_TYPE,"text/plain");
exchange.getResponseSender().send("Hello World");
exchange.endExchange();
}).exceptionally(throwable -> {
System.out.println(throwable.toString());
return null;
});
});
}).build();
server.start();
конечно, ответ «Hello World», как и ожидалось, но сервер создает новый поток для каждого запроса!