2013-06-05 18 views
5

Ich habe mehrere Fragen durchlaufen, this ist etwas verwandt, aber beantwortet meine Frage nicht.Stellt c3p0 Connection Pooling maximale Poolgröße sicher?

Stellt das c3p0-Verbindungs-Pooling maxPoolSize sicher, dass die Anzahl der Verbindungen zu einem bestimmten Zeitpunkt diese Grenze nie überschreitet? Was ist, wenn die und 10 Benutzer die App genau zur selben Zeit benutzen?

Meine App. Konfigurationen

<bean id="dataSource" class="com.mchange.v2.c3p0.ComboPooledDataSource" destroy-method="close"> 
     <property name="driverClass"><value>${database.driverClassName}</value>/property> 
     <property name="jdbcUrl"><value>${database.url}</value></property> 
     <property name="user"><value>${database.username}</value></property> 
     <property name="password"><value>${database.password}</value></property> 
     <property name="initialPoolSize"><value>${database.initialPoolSize}</value>/property> 
     <property name="minPoolSize"><value>${database.minPoolSize}</value></property> 
     <property name="maxPoolSize"><value>${database.maxPoolSize}</value></property> 
     <property name="idleConnectionTestPeriod"><value>200</value></property> 
     <property name="acquireIncrement"><value>1</value></property> 
     <property name="maxStatements"><value>0</value></property> 
     <property name="numHelperThreads"><value>3</value></property> 
    </bean> 

    <bean id="entityManagerFactory" class="org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean"> 
     <property name="dataSource" ref="dataSource"/>    
    </bean> 

    <bean id="transactionManager" class="org.springframework.orm.jpa.JpaTransactionManager"> 
     <property name="entityManagerFactory" ref="entityManagerFactory"/> 
     <property name="dataSource" ref="dataSource"/> 
    </bean> 

Antwort

11

ist es wichtig, zwischen Datasource und Verbindungspools zu unterscheiden.

maxPoolSize wird von c3p0 auf pro Pool erzwungen. Eine einzelne DataSource kann jedoch mehrere Verbindungspools besitzen, da für jeden Satz von Authentifizierungsdaten ein eigener Pool vorhanden ist (und sein muss). Wenn nur die Standardmethode dataSource.getConnection() aufgerufen wird, ist maxPoolSize die maximale Anzahl von Verbindungen, die der Pool erwirbt und verwaltet. Wenn jedoch Verbindungen mit dataSource.getConnection(user, password) erfasst werden, kann die DataSource Verbindungen bis zu (maxPoolSize * num_distinct_users) enthalten.

um Ihre spezifische Frage zu beantworten, wenn maxPoolSize ist 5 und 10 Clients gleichzeitig eine c3p0 DataSource, nicht mehr als 5 von ihnen erhalten Verbindungen zuerst. Die verbleibenden Clients werden wait() bis Verbindungen zurückgegeben werden (oder c3p0.checkoutTimeout ist abgelaufen).

einige Vorbehalte: c3p0 erzwingt maxPoolSize wie oben beschrieben. Es gibt jedoch keine Garantie dafür, dass selbst wenn nur ein einziger Pool pro Auth verwendet wird, nicht gelegentlich mehr als maxPoolSize Verbindungen ausgecheckt werden. Zum Beispiel läuft c3p0 ab und zerstört Verbindungen asynchron. Soweit es c3p0 betrifft, ist eine Verbindung weg, sobald sie für Clients nicht mehr verfügbar gemacht und zur Zerstörung markiert wurde, nicht wenn sie tatsächlich zerstört wurde. Es ist also möglich, dass, wenn maxPoolSize 5 ist, Sie gelegentlich 6 offene Verbindungen in der Datenbank beobachten. 5 Verbindungen wären im Pool aktiv, während der 6. in der Warteschlange für die Zerstörung steht, aber noch nicht zerstört ist.

Ein weiterer Umstand, bei dem Sie möglicherweise unerwartet viele Connections öffnen, ist, wenn Sie die Eigenschaften des Verbindungspools zur Laufzeit ändern. In der Tat ist die Konfiguration der inneren Verbindungspools unveränderlich. Wenn Sie einen Pool-Parameter zur Laufzeit "ändern", passiert tatsächlich, dass ein neuer Pool mit der neuen Konfiguration gestartet wird und der alte Pool in einen "Abwicklungs" -Modus versetzt wird. Verbindungen, die aus dem alten Pool ausgecheckt wurden, bleiben aktiv und gültig, aber wenn sie eingecheckt werden, werden sie zerstört. Nur wenn alle alten Pool-Verbindungen wieder eingecheckt wurden, ist der Pool wirklich tot. Wenn Sie also einen Pool mit maxPoolSize Verbindungen ausgecheckt haben und dann einen Konfigurationsparameter ändern, sehen Sie möglicherweise vorübergehend einen Spike von bis zu (2 * maxPoolSize), wenn der neue Pool mit viel Verkehr belegt wird, bevor Verbindungen ausgecheckt wurden Der alte Pool wurde zurückgegeben. In der Praxis ist dies sehr selten ein Problem, da eine dynamische Rekonfiguration nicht so häufig ist und Connection-Checkouts in der Regel sehr kurz sein sollten und daher die alten Poolverbindungen schnell verschwinden. aber es kann passieren!

ich hoffe, das hilft.

ps acquireIncrement ist am besten etwas größer als 1 gesetzt. acquireIncrement von 1 bedeutet, dass keine Verbindungen vorab abgerufen werden, so dass bei jeder Erhöhung der Last einige Threads direkt die Latenz der Verbindungserfassung erfahren.

Verwandte Themen