如何在 JAVA 中创建异步 HTTP 请求?

2022-08-31 11:38:41

我对Java相当陌生,所以这对某些人来说似乎很明显。我使用过很多ActionScript,它非常基于事件,我喜欢这一点。我最近尝试编写一小段执行POST请求的Java代码,但我遇到了一个问题,即它是一个同步请求,因此代码执行等待请求完成,超时或出现错误。

如何创建一个异步请求,其中代码继续执行,并在 HTTP 请求完成时调用回调?我瞥了一眼线程,但我认为这太过分了。


答案 1

如果您处于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的方式,这感觉不对。


答案 2

您可能还想看看异步 Http 客户端


推荐