在对通过Java客户端API访问MarkLogic服务器的基于Java的中间件进行了一些压力测试之后,我遇到了无法再打开HTTP连接且出现死锁的情况。我正在使用一个DatabaseClient共享实例,但是在每个请求上创建一个JSONDocumentManager(带有JacksonHandle用于读取,没有处理任何特定的关闭关注)。可能存在连接未正确关闭的问题,还是我必须自己照顾?

通过查看无法处理更多连接的点的netstat,我确实看到到localhost:8040中与MarkLogic服务器(在FIN_WAIT_2上运行)的109个连接:

ffffff8045f765a0 31c91c01 tcp4       0      0  localhost.8040     localhost.65396    FIN_WAIT_2


CLOSE_WAIT中相同数目的TCP连接(109):

ffffff804ff83400 73965e73 tcp4       0      0  localhost.49286    localhost.8040     CLOSE_WAIT


我正在将MarkLogic服务器7.0.4与Java 1.7(Mac OSX 10.9.5)和MarkLogic客户端API 2.0.4一起使用。这是线程转储的第一部分(有10个类似的线程似乎正在等待服务器响应):

"http-nio-8080-exec-10" #31 daemon prio=5 os_prio=31 tid=0x00007fc61f344000 nid=0x7c03 waiting on condition [0x00000001265bb000]
   java.lang.Thread.State: WAITING (parking)
    at sun.misc.Unsafe.park(Native Method)
    - parking to wait for  <0x00000007a59cfff8> (a java.util.concurrent.locks.AbstractQueuedSynchronizer$ConditionObject)
    at java.util.concurrent.locks.LockSupport.park(LockSupport.java:175)
    at java.util.concurrent.locks.AbstractQueuedSynchronizer$ConditionObject.await(AbstractQueuedSynchronizer.java:2039)
    at org.apache.http.impl.conn.tsccm.WaitingThread.await(WaitingThread.java:159)
    at org.apache.http.impl.conn.tsccm.ConnPoolByRoute.getEntryBlocking(ConnPoolByRoute.java:398)
    at org.apache.http.impl.conn.tsccm.ConnPoolByRoute$1.getPoolEntry(ConnPoolByRoute.java:298)
    at org.apache.http.impl.conn.tsccm.ThreadSafeClientConnManager$1.getConnection(ThreadSafeClientConnManager.java:238)
    at org.apache.http.impl.client.DefaultRequestDirector.execute(DefaultRequestDirector.java:423)
    at org.apache.http.impl.client.AbstractHttpClient.doExecute(AbstractHttpClient.java:863)
    at org.apache.http.impl.client.CloseableHttpClient.execute(CloseableHttpClient.java:115)
    at org.apache.http.impl.client.CloseableHttpClient.execute(CloseableHttpClient.java:57)
    at com.sun.jersey.client.apache4.ApacheHttpClient4Handler.handle(ApacheHttpClient4Handler.java:170)
    at com.marklogic.client.impl.DigestChallengeFilter.handle(DigestChallengeFilter.java:34)
    at com.sun.jersey.api.client.filter.HTTPDigestAuthFilter.handle(HTTPDigestAuthFilter.java:493)
    at com.sun.jersey.api.client.Client.handle(Client.java:648)
    at com.sun.jersey.api.client.WebResource.handle(WebResource.java:680)
    at com.sun.jersey.api.client.WebResource.access$200(WebResource.java:74)
    at com.sun.jersey.api.client.WebResource$Builder.get(WebResource.java:507)
    at com.marklogic.client.impl.JerseyServices.getDocumentImpl(JerseyServices.java:612)
    at com.marklogic.client.impl.JerseyServices.getDocument(JerseyServices.java:568)
    at com.marklogic.client.impl.DocumentManagerImpl.read(DocumentManagerImpl.java:270)
    at com.marklogic.client.impl.DocumentManagerImpl.read(DocumentManagerImpl.java:204)
    at com.marklogic.client.impl.DocumentManagerImpl.read(DocumentManagerImpl.java:164)
    at com.acme.dashboard.service.ReportMetadataRepository.getByName(ReportMetadataRepository.java:64)


省略了堆栈跟踪的更多详细信息,以提高可读性。
在查看JerseyServices之后,我还尝试调整以下系统属性(不幸的是,没有任何改进):

com.marklogic.client.maximumRetrySeconds: 3 (default: 120)
com.marklogic.client.minimumRetries: 3 (default: 8)

最佳答案

听起来您可能遇到了JacksonHandle和TuplesHandle没有关闭它们的连接的错误(github问题#89)。此问题已在Java Client API 2.0.5中修复。您是否可以在ML Server的7.0-5实例上运行测试并使用Java客户端API的2.0.5版本?

07-24 09:37
查看更多