Neo4j bolt连接超时提示配置及保活设置失效问题咨询
gds.graph.project.cypher超时问题排查与疑问解答 问题场景
使用Neo4j 5.10社区版作为图计算引擎,处理多套百万级节点、千万级关系的数据集做图算法计算。通过JavaScript客户端驱动调用gds.graph.project.cypher在内存中创建图时,偶尔会因处理时长超过120秒报错,提示连接丢失、服务器120000ms未响应。
排查过程
- 先排查服务端与客户端的事务超时配置,修改后无效果;
- 查看JavaScript驱动源码后发现,错误由
receiveTimeout设置导致,该值由服务端响应元数据提供,但当时找不到修改方法; - 后续在Go驱动源码的说明中找到解决方案:将服务端配置
dbms.connector.bolt.connection_keep_alive_for_requests设为OFF,重启服务后问题解决。
疑问解答
1. 如何在服务端配置中修改connection.recv_timeout_seconds元数据提示?
Neo4j 5.x版本中,connection.recv_timeout_seconds元数据对应的服务端配置项是dbms.connector.bolt.connection_recv_timeout_seconds,直接在neo4j.conf配置文件中添加或修改即可:
dbms.connector.bolt.connection_recv_timeout_seconds=300
修改完成后重启Neo4j服务,配置即可生效。该配置直接控制Bolt连接的接收超时时间,默认值为120秒,这也是之前触发超时报错的原因。
2. server.bolt.connection_keep_alive_streaming_scheduling_interval默认值为1m,为何该保活间隔未生效仍导致客户端120秒超时?
这个配置的作用是控制服务端向客户端发送保活心跳的调度间隔,但它生效的前提是dbms.connector.bolt.connection_keep_alive_for_requests处于默认的ON状态。
当connection_keep_alive_for_requests为ON时,服务端本应在长请求处理过程中主动发送心跳包维持连接,但如果像gds.graph.project.cypher这类长请求在执行时,服务端的计算线程被完全占用,没有空闲资源发送心跳包,即便配置了1分钟的间隔,心跳也无法按时发出,客户端还是会因为连续120秒未收到响应触发receiveTimeout。
而将connection_keep_alive_for_requests设为OFF后,服务端会关闭主动心跳机制,同时客户端的receiveTimeout会被禁用(视为无限大),长请求就不会因为超时被中断,这也是问题得以解决的核心原因。
内容的提问来源于stack exchange,提问作者Frank

