是否可以执行比线程池中的线程更多的请求?

时间:2015-09-16 06:01:25

标签: java multithreading spring testing integration-testing

我使用Java和Spring开发Web应用程序。为了检查系统在多个请求到来时的行为,我创建了测试:

@Test
public void shouldHandleMultipleRequests() throws Exception {
    //given
    final String endpoint = "http://localhost:9000/upload";
    final File file = new File(format("src/test/resources/files/%s", 
        "file.txt"));  
    //when
    final CompletableFuture<String> response1 = CompletableFuture.supplyAsync(() -> 
        Try.ofFailable(() -> 
        HttpClientBuilder.create().build().execute(
        createHttpPost(endpoint, file))).orElse(null).getEntity().toString());
    final CompletableFuture<String> response2 = CompletableFuture.supplyAsync(() -> 
        Try.ofFailable(() -> 
        HttpClientBuilder.create().build().execute(
        createHttpPost(endpoint,file))).orElse(null).getEntity().toString());  
    assertThat(response1.get().contains("Something")); 
    assertThat(response2.get().contains("Something"));

}

一切正常,但是我注意到,如果我尝试运行3个以上的请求,前3个请求和下一个请求之间会有延迟。

我的问题是

  • 我是对的,这个行为与我的处理器上的线程数有关(4个线程处理器,3个线程用于请求和等待响应,1个用于应用程序)?
  • 如果有办法同时发送3个以上的请求(当然后来检索响应)?

2 个答案:

答案 0 :(得分:1)

Java线程称为软线程,与处理器核心/线程数无关。

通常,HTTP服务器和Servlet / App容器与线程池一起工作,这意味着一旦达到线程池上限,其余的请求仍然被阻止。这就是阻止方法。

但是,还有另一个选项可以配置非阻塞连接器。阅读Tomcat Connectors Document可以获得更深入的知识。因此,正如您所看到的,您可以调整服务器行为,因为它是连接器配置的问题。

当然,您可以同时生成三个以上的线程并获得Future个结果。

答案 1 :(得分:1)

CompletableFuture.supplyAsync使用公共ForkJoinPool提交任务,默认情况下线程数受Runtime.getRuntime().availableProcessors()返回的硬件线程数限制。但是,您可以使用双参数supplyAsync创建自己的池并将其用于任务:

ForkJoinPool myPool = new ForkJoinPool(100); // number of tasks executed in parallel

CompletableFuture.supplyAsync(..., myPool);

对于网络请求,拥有比CPU内核更多的线程是很正常的。