使用neo4j休息http客户端的性能问题

ray*_*man 0 connection performance neo4j cypher apache-httpclient-4.x

用Apache http客户端替换neo4j-jdbc客户端之后挣扎.

似乎在运行仅执行查询的1k个并发用户时仍然存在问题.

这就是我们使用客户端的方式:https: //gist.github.com/IdanFridman/1989b600a0a032329a5e

这是我们使用该rest-client执行查询的方式:

https://gist.github.com/IdanFridman/22637f95ba696f498b6c

在分析后,我们看到上面的糟糕表现结果:

在此输入图像描述

每个请求的avg延迟为3秒.

我们应该抛弃neo4j吗?我们对表演结果感到绝望

谢谢.

Fyl*_*mTM 5

那么,您想要更多并发请求吗?让我们来探索一下我们在这里可以做些什么.

查询

首先 - 检查查询是否表现良好.复制粘贴Neo4j浏览器,前置PROFILE并探索输出.

可能是您的查询比您预期的要多得多.这会导致等待时间过长,因为Neo4j仍在执行查询.

客户

HttpClient配置

你正在使用PoolingHttpClientConnectionManager.来自文档:

PoolingHttpClientConnectionManager维护每个路由和总计的最大连接数限制.默认情况下,此实现将为每个给定路由创建不超过2个并发连接,并且总共不再有20个连接.

所以,我们应该增加限制.例:

PoolingHttpClientConnectionManager cnnMgr = new PoolingHttpClientConnectionManager();
cnnMgr.setMaxTotal(500);
cnnMgr.setDefaultMaxPerRoute(100);
Run Code Online (Sandbox Code Playgroud)

HttpRequest的

尝试添加keep-alive标头来请求.例:

request.setHeader("Connection", "keep-alive");
Run Code Online (Sandbox Code Playgroud)

然后,您应该尽快关闭您的回复.您不应该依赖于这样一个事实:当您正在耗尽流内容时,连接已关闭.码:

try(CloseableHttpResponse response = httpClient.execute(request)) {
    // do stuff with response here
    // close response when try-with-resource block ends
}
Run Code Online (Sandbox Code Playgroud)

请记住 - 您从服务器事务端点接收的内容将流式传输回客户端.

return createResultSet(new JsonObject(IOUtils.toString(response.getEntity().getContent())));
Run Code Online (Sandbox Code Playgroud)

因此,在此代码示例中,我们等待直到我们检索完整响应,然后才开始序列化.

在你的情况下,你正在寻找这样的东西:

String rawJsonResult = null;
try(CloseableHttpResponse response = httpClient.execute(request);) {
    rawJsonResult = IOUtils.toString(response.getEntity().getContent());
} catch (IOException e) {
    throw new RuntimeException(e);
}
return createResultSet(new JsonObject(rawJsonResult));
Run Code Online (Sandbox Code Playgroud)

通过这样做,我们确保在任何序列化发生之前检索结果并关闭连接.这将释放其他并发连接的资源.

服务器

Neo4j使用Jetty作为Web服务器.Jetty得到了支持BlockingQueue.这意味着x可以处理的并发HTTP请求数量.这x是队列大小.如果我们有超过x并发请求的数量,那么等待队列中的空闲点.

幸运的是,您可以配置队列的大小.您对这家酒店感兴趣:

org.neo4j.server.webserver.maxthreads=200
Run Code Online (Sandbox Code Playgroud)

注意:这里没有魔力.默认情况下,Neo4j正在使用cpuCount * 4大量的Web服务器线程.增加此数量可能会导致更多的并发请求,但每个请求都会变慢.

Linux的

你应该检查一下.每个TCP连接都是一个单独的文件.通常,大多数Linux发行版的默认值是1024.你需要增加它.你可以试试40000.

请记住 - 这不仅适用于服务器,也适用于客户端.您不仅希望接收连接,还需要打开它们.

一般注意事项

你不应该相信分析结果那么多.我们在发出HTTP请求时等待是完全可以的.总的来说 - 这是沟通中最昂贵的部分.

此外,您应确保您的客户端和服务器位于同一本地网络上.通过公共网络执行请求会显着降低性能.

最后一个 - 并发HTTP连接的上限.传递此限制可能会使数据库几乎无响应(类似于任何其他Web应用程序).您可能需要考虑水平扩展(Neo4j Cluster)才能生成更多并发请求.


祝好运!