这几天一直在压测服务器的性能问题,当并发量大时,服务器会报mong的错误:
Too many threads are already waiting for a connection. Max number of threads (maxWaitQueueSize) of 50 has been exceeded.
原来在我的配置文件中,没有设置mongo连接的最大线程数,所以默认最大的为50
之前的配置如下
新的配置如下
threads-allowed-to-block-for-connection-multiplier="10"
connect-timeout="10000"
max-wait-time="120000"
auto-connect-retry="false"
socket-keep-alive="false"
socket-timeout="0"
slave-ok="false"
write-number="1"
write-timeout="0"
write-fsync="true"
/>
dbname="${mongo.dbName}" username="${mongo.username}" password="${mongo.password}" id="mongoDbFactory" />
各个参数说明:
#对mongo实例来说,每个host允许链接的最大链接数,这些链接空闲时会放入池中,如果链接被耗尽,任何请求链接的操作会被阻塞等待链接可用,推荐配置10
connectionsPerHost=10
#当链接空闲时,空闲线程池中最大链接数
minPoolsSize=5
#此参数跟connectionsPerHost的乘机为一个线程变为可用的最大阻塞数,超过此乘机数之后的所有线程将及时获取一个异常.eg.connectionsPerHost=10 and threadsAllowedToBlockForConnectionMultiplier=5,最多50个线程等级一个链接,推荐配置为5
threadsAllowedToBlockForConnectionMultiplier=5
#一个线程等待链接可用的最大等待毫秒数,0表示不等待,负数表示等待时间不确定,推荐配置120000
maxWaitTime=120000
#链接超时的毫秒数,0表示不超时,此参数只用在新建一个新链接时,推荐配置10,000.
connectTimeout=10000
#此参数表示socket I/O读写超时时间,推荐为不超时,即 0 Socket.setSoTimeout(int)
socketTimeout=0
#该标志用于控制socket保持活动的功能,通过防火墙保持连接活着
socketKeepAlive=false
#true:假如链接不能建立时,驱动将重试相同的server,有最大的重试次数,默认为15次,这样可以避免一些server因为一些阻塞操作零时down而驱动抛出异常,这个对平滑过度到一个新的master,也是很有用的,注意:当集群为复制集时,驱动将在这段时间里,尝试链接到旧的master上,而不会马上链接到新master上
#false 当在进行socket读写时,不会阻止异常抛出,驱动已经有自动重建破坏链接和重试读操作. 推荐配置false
autoConnectRetry=false
#重新打开链接到相同server的最大毫秒数,推荐配置为0,如果 autoConnectRetry=true,表示时间为15s
#com.jd.mongodbclient2.mongo.JDClientMongo.maxAutoConnectRetryTime=false
#表示当没有手动关闭游标时,是否有一个自动释放游标对象的方法,如果你总是很小心的关闭游标,则可以将其设为false 推荐配置true
#com.jd.mongodbclient2.mongo.JDClientMongo.cursorFinalizerEnabled=true
#安全模式
#为true表示读写分离
com.jd.mongodbclient2.driver.MongoDBDriver.slaveOk=false
我最终设置的最大值是1000,压测完美通过,不过是测试环境,不怕出现问题,但是有个顾虑,就是怕设置过大,怕影响mongo的数据库的性能。不知道有哪位大神知道这个上限在哪??
可参考官网:
http://docs.spring.io/spring-data/data-mongodb/docs/current/reference/html/
http://api.mongodb.org/java/current/com/mongodb/MongoOptions.html#connectionsPerHost