【问题标题】:HttpClient and LocalServerTestBase is really slowHttpClient 和 LocalServerTestBase 真的很慢
【发布时间】:2016-09-09 10:59:37
【问题描述】:

我正在尝试在使用HttpClient 版本4.5 的类上编写测试。我写的测试真的很慢,所以我试图隔离问题。我可以编写一个测试来证明我的问题:

public class RequeteurRESTTest extends LocalServerTestBase {

    private String startServer(String urlSuffix, HttpRequestHandler handler) throws Exception{
        this.serverBootstrap.registerHandler(urlSuffix, handler);
        HttpHost target = start();
        String serverUrl = "http://localhost:" + target.getPort();
        return serverUrl;
    }

    @Test
    public void testCase() throws Exception{
        String baseURL = startServer("/api", new HttpRequestHandler() {
            @Override
            public void handle(HttpRequest request, HttpResponse response,     HttpContext context) throws HttpException, IOException {
                response.setStatusCode(HttpStatus.SC_OK);
            }
        });

        HttpClient httpClient;
        httpClient = HttpClients.custom().build();

        HttpGet method = new HttpGet(baseURL + "/api");
        HttpResponse response = httpClient.execute(method);
    }
}

我遇到的问题是指令:

httpClient.execute(method)

执行需要 10 秒。这很慢,但我不明白为什么这么慢。我是否在测试中犯了任何错误,或者忘记了什么?

【问题讨论】:

  • 它执行正确吗?即您的被测服务器是否被调用?
  • 处理程序被正确调用,是的

标签: performance testing apache-httpclient-4.x


【解决方案1】:

这很可能是因为您没有对响应对象执行任何操作。至少应该关闭它。

【讨论】:

【解决方案2】:

由于我无法理解的原因,使用基类的httpclient可以正常工作,如下:

@Test
public void testCase() throws Exception{
    String baseURL = startServer("/api", new HttpRequestHandler() {
        @Override
        public void handle(HttpRequest request, HttpResponse response,     HttpContext context) throws HttpException, IOException {
            response.setStatusCode(HttpStatus.SC_OK);
        }
    });

    HttpGet method = new HttpGet(baseURL + "/api");
    HttpResponse response = this.httpclient.execute(method);

}

【讨论】:

    【解决方案3】:

    如果你查看LocalServerTestBase类的源代码,你可以看到如下方法:

    @After
    public void shutDown() throws Exception {
        if(this.httpclient != null) {
            this.httpclient.close();
        }
    
        if(this.server != null) {
            this.server.shutdown(10L, TimeUnit.SECONDS);
        }
    
    }
    

    通过在您自己的测试用例中覆盖它,您可以将超时设置为 0 秒。这应该可以消除您在执行中看到的延迟。

    示例实现:

    public class MyClassTest extends LocalServerTestBase{
        HttpHost httpHost;
        @Before
        public void setUp() throws Exception {
          super.setUp();
          this.serverBootstrap.registerHandler("/*", new HttpRequestHandler() {
            @Override
            public void handle(HttpRequest request, HttpResponse response, HttpContext context) 
                              throws HttpException, IOException {
                System.out.println(request.getRequestLine().getMethod());
                response.setStatusCode(HttpStatus.SC_OK);                
            }
    
          });
    
          httpHost = start();
    
        }
    
        @Test
        public void myMethodTest() throws Exception {
            //Create an instance and give the server url it should call
            MyClass instance = new MyClass(httpHost.toURI());
            //Test method that calls the server
            instance.myMethod();
        }
    
        @After @Override
        public void shutDown() throws Exception {
         if(this.httpclient != null) {
            this.httpclient.close();
         }
        if(this.server != null) {
            this.server.shutdown(0L, TimeUnit.SECONDS);
        }
       }
    
    }
    

    【讨论】:

      【解决方案4】:

      我遇到了同样的问题。原因似乎是请求完成后服务器没有关闭连接。我不确定这是否是测试的特殊行为,或者当您与真实服务器通信时也会发生。在我的谷歌搜索中,我发现关闭连接客户端并不常见/不容易支持,这让我相信这种连接不关闭只是测试行为。当我将测试服务器设置为从不重用连接时,它为我解决了 10 秒的延迟。

      this.serverBootstrap.setConnectionReuseStrategy((response, context) -> false);
      

      【讨论】:

        猜你喜欢
        • 2017-11-10
        • 2010-12-28
        • 2013-01-25
        • 1970-01-01
        • 2012-01-30
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多