数据源拒绝建立连接,来自服务器的消息:“连接太多”

Posted

技术标签:

【中文标题】数据源拒绝建立连接,来自服务器的消息:“连接太多”【英文标题】:Data source rejected establishment of connection, message from server: "Too many connections" 【发布时间】:2012-08-18 18:31:37 【问题描述】:

我正在使用 hibenate 和 spring,并且在我们从 250 个用户的 jmeter 中获得以下异常

“原因:com.mysql.jdbc.exceptions.jdbc4.MySQLNonTransientConnectionException:

hibernate_cfg.xml

<property name="hibernate.dialect">org.hibernate.dialect.MySQLDialect</property>
    <property name="hibernate.connection.driver_class">com.mysql.jdbc.Driver</property>
    <property name="hibernate.connection.url">jdbc:mysql://localhost:3306/my_db</property>
    <property name="hibernate.connection.username">user1</property>
    <property name="hibernate.connection.pool_size">1</property>
    <property name="hibernate.c3p0.min_size">5</property>
    <property name="hibernate.c3p0.max_size">50</property>
    <property name="hibernate.c3p0.timeout">300</property>
    <property name="hibernate.c3p0.max_statements">500</property>
    <property name="hibernate.c3p0.idle_test_period">3000</property>
    <property name="hibernate.current_session_context_class">thread</property>
    <property name="hibernate.hbm2ddl.auto">update</property>`

春天

<bean id="dataSource" scope="prototype" class="org.springframework.jdbc.datasource.DriverManagerDataSource"> 
    <property name="driverClassName">
        <value>$dbDriver</value>
    </property>  
    <property name="url">
        <value>$dbURL</value> 
    </property>
    <property name="username">
        <value>$dbUsername</value>
    </property>
    <property name="password">
        <value>$dbPassword</value>
    </property>
</bean>

【问题讨论】:

【参考方案1】:

您需要在应用程序和数据库服务器中都对其进行跟踪。

    检查数据库配置以获得可能的最大打开连接数。 如果您正在使用来自其他客户端的数据库连接,请检查数据库服务器中当前打开的连接。 如果您打开的连接过多而不是关闭它们,请检查您的应用程序。

您需要在数据库服务器设置中增加 max open connections 的值。

要更改最大打开连接数,您需要在数据库服务器下的 my.cnf 文件中编辑 max_connectionsmax_user_connections

您还可以授予/编辑每个用户的最大连接数。 more info available here

【讨论】:

我在 mysql wamp 服务器中提供了无限连接 mysql 默认 max_connections = 151,每个应用程序 1000 个用户应该使用多少个连接 max_connections 应该是,您希望同时使用您的应用程序。如果有多个应用程序访问数据库,您还需要包括这些连接。【参考方案2】:

这是来自服务器的消息,因此,我将检查服务器报告的已连接客户端的数量。如果这是一个预期的数字,比如 500 左右,那么我会增加服务器上的这个限制,如果你真的希望你的应用程序有那个级别的并发。否则,请减少客户端数量。

关于它如何工作的一些背景知识:每个客户端都是服务器上的一个线程,每个线程将至少消耗一个连接。如果你做得对,一旦线程完成,连接将返回到池中(即:一旦响应发送到客户端)。因此,在最好的情况下,如果您连接了大约 500 个用户,您将拥有 500 个连接。如果看到的数字接近并发用户数的倍数(即:2 个用户,4 个连接),那么您可能每个线程消耗了多个连接(这是您不使用提供的数据源所付出的代价您的应用程序服务器,如果您使用的是一个)。如果您看到一个非常高的数字(例如,用户数量的 10 倍),那么您可能在某处存在连接泄漏。如果您忘记关闭连接,可能会发生这种情况。

我真的建议使用由您的应用程序服务器管理的 EntityManager,并使用它也提供的 DataSource。然后,您不必担心管理连接池。

【讨论】:

我可以,但最好看一下文档。 Oracle 的网站上有一个很好的 Java EE 教程,它的网站上也有一个很好的 Hibernate 文档。 我正在使用 session = Hy5HibernateUtil.getSessionFactory().openSession(); 并关闭 finally 块 openSession() 和 getCurrentSession() 的区别是什么,哪个是最好的 我已经在spring数据源中添加了连接池,工作正常 &lt;bean id="dataSource" class="com.mchange.v2.c3p0.ComboPooledDataSource" destroy-method="close" &gt; &lt;property name="driverClass" value="$dbDriver"&gt;&lt;/property&gt; &lt;property name="jdbcUrl" value="$dbURL"&gt;&lt;/property&gt; &lt;property name="user" value="$dbUsername"&gt;&lt;/property&gt; &lt;property name="password" value="$dbPassword"&gt;&lt;/property&gt; &lt;property name="initialPoolSize" value="5"&gt;&lt;/property&gt; &lt;property name="maxPoolSize" value="50"/&gt; &lt;property name="minPoolSize" value="5"/&gt; &lt;property name="maxIdleTime" value="3000"/&gt;【参考方案3】:

如果每次都创建连接可能会导致此问题。解决方法很简单。单上。每个 sessin 的连接。所以我在我的帖子底部发布了一些代码。检查不正确和正确的编码。 1-不正确,2-正确

private  EntityManagerFactory emf = null;

@SuppressWarnings("unchecked")
public BaseDAO() 


        emf = Persistence.createEntityManagerFactory("aaHIBERNATE");
        persistentClass = (Class<T>) ((ParameterizedType) getClass()
                .getGenericSuperclass()).getActualTypeArguments()[0];




private static EntityManagerFactory emf = null;

@SuppressWarnings("unchecked")
public BaseDAO() 

    if (emf == null) 
        emf = Persistence.createEntityManagerFactory("aaHIBERNATE");
        persistentClass = (Class<T>) ((ParameterizedType) getClass()
                .getGenericSuperclass()).getActualTypeArguments()[0];



【讨论】:

【参考方案4】:

我认为您的问题是您的数据源没有连接池。 来自 org.springframework.jdbc.datasource.DriverManagerDataSource javadocs:

注意:这个类不是一个真正的连接池;它实际上并没有 * 池连接。

在该类的 javadocs 中也说使用 Apache 的 Jakarta Commons DBCP,以防您确实需要连接池。

如果您需要 J2EE 容器之外的“真实”连接池, 考虑Apache's Jakarta Commons DBCP 或 C3P0。 Commons DBCP 的 BasicDataSource 和 C3P0 的 ComboPooledDataSource 是全连接的 池bean,支持与此类相同的基本属性加上 特定设置(例如最小/最大池大小等)。

我用过它,它就像一个魅力:)

希望我能帮上忙。

【讨论】:

以上是关于数据源拒绝建立连接,来自服务器的消息:“连接太多”的主要内容,如果未能解决你的问题,请参考以下文章

Data source rejected establishment of connection, message from server: "Too many connections&qu

本地主机拒绝来自应用程序的连接

从远程队列中读取消息

正确的数据库设置 - 连接太多?

PHP Laravel:无法建立连接,因为目标计算机主动拒绝它

WinSCP:权限被拒绝。错误代码:3来自服务器的错误消息:权限被拒绝[关闭]