如何在 JAVA 中创建异步 HTTP 请求?
2022-08-31 11:38:41
我对Java相当陌生,所以这对某些人来说似乎很明显。我使用过很多ActionScript,它非常基于事件,我喜欢这一点。我最近尝试编写一小段执行POST请求的Java代码,但我遇到了一个问题,即它是一个同步请求,因此代码执行等待请求完成,超时或出现错误。
如何创建一个异步请求,其中代码继续执行,并在 HTTP 请求完成时调用回调?我瞥了一眼线程,但我认为这太过分了。
我对Java相当陌生,所以这对某些人来说似乎很明显。我使用过很多ActionScript,它非常基于事件,我喜欢这一点。我最近尝试编写一小段执行POST请求的Java代码,但我遇到了一个问题,即它是一个同步请求,因此代码执行等待请求完成,超时或出现错误。
如何创建一个异步请求,其中代码继续执行,并在 HTTP 请求完成时调用回调?我瞥了一眼线程,但我认为这太过分了。
如果您处于JEE7环境中,则必须有一个体面的JAXRS实现,这将允许您使用其客户端API轻松发出异步HTTP请求。
这看起来像这样:
public class Main {
public static Future<Response> getAsyncHttp(final String url) {
return ClientBuilder.newClient().target(url).request().async().get();
}
public static void main(String ...args) throws InterruptedException, ExecutionException {
Future<Response> response = getAsyncHttp("http://www.nofrag.com");
while (!response.isDone()) {
System.out.println("Still waiting...");
Thread.sleep(10);
}
System.out.println(response.get().readEntity(String.class));
}
}
当然,这只是使用期货。如果你可以再使用一些库,你可以看看RxJava,代码会看起来像这样:
public static void main(String... args) {
final String url = "http://www.nofrag.com";
rx.Observable.from(ClientBuilder.newClient().target(url).request().async().get(String.class), Schedulers
.newThread())
.subscribe(
next -> System.out.println(next),
error -> System.err.println(error),
() -> System.out.println("Stream ended.")
);
System.out.println("Async proof");
}
最后但并非最不重要的一点是,如果你想重用你的异步调用,你可能想看看Hystrix,除了一个超级酷的其他东西之外,它还允许你写这样的东西:
例如:
public class AsyncGetCommand extends HystrixCommand<String> {
private final String url;
public AsyncGetCommand(final String url) {
super(Setter.withGroupKey(HystrixCommandGroupKey.Factory.asKey("HTTP"))
.andCommandPropertiesDefaults(HystrixCommandProperties.Setter()
.withExecutionIsolationThreadTimeoutInMilliseconds(5000)));
this.url = url;
}
@Override
protected String run() throws Exception {
return ClientBuilder.newClient().target(url).request().get(String.class);
}
}
调用此命令将如下所示:
public static void main(String ...args) {
new AsyncGetCommand("http://www.nofrag.com").observe().subscribe(
next -> System.out.println(next),
error -> System.err.println(error),
() -> System.out.println("Stream ended.")
);
System.out.println("Async proof");
}
PS:我知道这个帖子很旧,但是没有人在投票的答案中提到Rx / Hystrix的方式,这感觉不对。