3

我正在使用async-http-client,但我遇到了麻烦NettyAsyncHttpProvider

它给出了这个警告:

Oct 28, 2014 12:50:16 PM org.jboss.netty.channel.socket.nio.AbstractNioWorkerPool
WARNING: Failed to get all worker threads ready within 10 second(s). Make sure to specify the executor which has more threads than the requested workerCount. If unsure, use Executors.newCachedThreadPool().

我的问题是即使我使用Executors.newCachedThreadPool()以下问题仍然存在。

一旦线程数达到corePoolSize,请求就会被丢弃。无论requestTimeoutInMs我尝试什么或其他选项,只有一小部分响应返回并且池中的线程停止。

ExecutorService executor = new CustomThreadPoolExecutor(2, 2, 60,
            TimeUnit.SECONDS, new LinkedBlockingQueue<Runnable>(), new ThreadFactory() {
        @Override
        public Thread newThread(Runnable r) {
            int number = threadCreationCount.incrementAndGet();
            LOG.info("newThread - {} ", number);

            Thread th = new Thread(r);
            th.setName("AsyncHttpClient-" + number);
            LOG.info("thread ={}", th);
            return th;
        }
    });

    AsyncHttpClientConfig.Builder builder = new AsyncHttpClientConfig.Builder();
    builder.setMaximumConnectionsTotal(-1)
            .setMaximumConnectionsPerHost(-1)
            .setConnectionTimeoutInMs(1000)
            .setIdleConnectionInPoolTimeoutInMs(60000)
            .setIdleConnectionTimeoutInMs(60000)
            .setRequestTimeoutInMs(3000)
            .setFollowRedirects(true)
            .setMaximumNumberOfRedirects(5)
            .setAllowPoolingConnection(true)
            .setIOThreadMultiplier(4)
            .build();

    builder.setExecutorService(executor);

    AsyncHttpClientConfig config = builder.build();
    AsyncHttpClient client = new AsyncHttpClient(new NettyAsyncHttpProvider(config), config);

    //Spin up 500 async requests to google.com
    for (int i = 1; i <= 500; i++) {
        LOG.info("i = {}", i);
        ListenableFuture<Response> future = client.prepareGet("http://www.google.com").execute(
                new AsyncCompletionHandler<Response>() {
                    @Override public Response onCompleted(Response response) throws Exception {
                        LOG.info("Response = {}, count = {}", response.getStatusCode(),
                                responseCount.incrementAndGet());
                        return response;
                    }

                    @Override
                    public void onThrowable(Throwable t) {
                        LOG.error("on throwable ={}", t);
                    }

                });
    }

现在,如果我从更改为NettyAsyncHttpProvider执行ApacheAsyncHttpProvider所有请求。

我在 github 上创建了一个示例项目来展示这个问题。异步 http 客户端调试

4

2 回答 2

1

使用默认执行程序服务时,我遇到了同样的问题。我没有调试原因,但是使用下面的这个配置,我没有得到 10 秒的延迟和警告消息。

AsyncHttpClientConfig.Builder builder = new AsyncHttpClientConfig.Builder();
    builder.setConnectTimeout(3000)
            .setExecutorService(new ThreadPoolExecutor(0, 20,
                    60L, TimeUnit.SECONDS,
                    new SynchronousQueue<>()))
            .setRequestTimeout(3000)
            .setReadTimeout(3000)
            .build();
于 2015-12-16T03:43:35.573 回答
-1

这不是线程问题。这里有两件事在起作用:

  • 您同时发送大量请求,没有任何背压,因此您尝试同时打开 500 个并发连接。你最好在 AHC 前面有一个队列和一个专用的 Executor,这样你就可以限制和控制并发飞行请求的数量。
  • 你在敲打 google.com。他们当然不允许您这样做,并阻止您的连接尝试。

PS:如果您改为在 AHC google group 上提问,您会得到更快的答案。

于 2016-01-06T12:47:37.423 回答