KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > org > opensubsystems > core > persist > db > connectionpool > ProxoolDatabaseConnectionFactoryImpl


1 /*
2  * Copyright (c) 2003 - 2007 OpenSubsystems s.r.o. Slovak Republic. All rights reserved.
3  *
4  * Project: OpenSubsystems
5  *
6  * $Id: ProxoolDatabaseConnectionFactoryImpl.java,v 1.5 2007/01/07 06:14:58 bastafidli Exp $
7  *
8  * This program is free software; you can redistribute it and/or modify
9  * it under the terms of the GNU General Public License as published by
10  * the Free Software Foundation; version 2 of the License.
11  *
12  * This program is distributed in the hope that it will be useful,
13  * but WITHOUT ANY WARRANTY; without even the implied warranty of
14  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15  * GNU General Public License for more details.
16  *
17  * You should have received a copy of the GNU General Public License
18  * along with this program; if not, write to the Free Software
19  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
20  */

21
22 package org.opensubsystems.core.persist.db.connectionpool;
23
24 import java.sql.Connection JavaDoc;
25 import java.sql.DriverManager JavaDoc;
26 import java.sql.SQLException JavaDoc;
27 import java.util.Properties JavaDoc;
28
29 import org.logicalcobwebs.proxool.ProxoolConstants;
30 import org.logicalcobwebs.proxool.ProxoolException;
31 import org.logicalcobwebs.proxool.ProxoolFacade;
32 import org.opensubsystems.core.error.OSSConfigException;
33 import org.opensubsystems.core.error.OSSDatabaseAccessException;
34 import org.opensubsystems.core.error.OSSException;
35 import org.opensubsystems.core.persist.db.DatabaseImpl;
36 import org.opensubsystems.core.persist.db.DatabaseTransactionFactoryImpl;
37
38 /**
39  * Implementation of connection pool using Objectweb Proxool package
40  * (http://proxool.sourceforge.net/).
41  *
42  * Design of Proxool doesn't allow us to use separate instance of Proxool
43  * for each database connection factory. This is because ConnectionPoolManager
44  * singleton accessible only through ProxoolFacade. This is causing multiple
45  * connection factories to underneath share the same connection pools, which
46  * can result in bugs such as #1275551 when multiple factories cannot create
47  * pool with the same name. The solution to this problem would be for Proxool
48  * ConnectionPoolManager to do not be a singleton so each
49  * ProxoolDatabaseConnectionFactoryImpl can have its own connection pool manager.
50  *
51  * @version $Id: ProxoolDatabaseConnectionFactoryImpl.java,v 1.5 2007/01/07 06:14:58 bastafidli Exp $
52  * @author Julo Legeny
53  * @code.reviewer Miro Halas
54  * @code.reviewed 1.2 2005/09/01 02:51:45 bastafidli
55  */

56 public class ProxoolDatabaseConnectionFactoryImpl extends PooledDatabaseConnectionFactoryImpl
57 {
58    // Constructors /////////////////////////////////////////////////////////////
59

60    /**
61     * Constructor for new instance using default database properties.
62     *
63     * @throws OSSConfigException - if there was an error accessing default database
64     * properties
65     * @throws OSSDatabaseAccessException - problem accessing the database
66     */

67    public ProxoolDatabaseConnectionFactoryImpl(
68    ) throws OSSConfigException,
69             OSSDatabaseAccessException
70    {
71       super();
72       
73       // Use the default database properties
74
loadDefaultDatabaseProperties();
75
76       // Do not start it now because when we are creating pool we need to know
77
// what database we are running on and it would create circular dependency
78
// with DatabaseImpl
79
// start();
80
}
81    
82    /**
83     * Constructor for new instance using default database properties.
84     *
85     * @param transactionFactory - transaction factory to use for this
86     * connection factory, can be null
87     * @throws OSSConfigException - if there was an error accessing default database
88     * properties
89     * @throws OSSDatabaseAccessException - problem accessing the database
90     */

91    public ProxoolDatabaseConnectionFactoryImpl(
92       DatabaseTransactionFactoryImpl transactionFactory
93    ) throws OSSConfigException,
94             OSSDatabaseAccessException
95    {
96       super(transactionFactory);
97
98       // Use the default database properties
99
loadDefaultDatabaseProperties();
100
101       // Do not start it know because when we are creating pool we need to know
102
// what database we are running on and it would create circular dependency
103
// with DatabaseImpl
104
// start();
105
}
106    
107    /**
108     * Constructor for new instance using explicitely specified properties.
109     *
110     * @param strDriver - JDBC driver to connect to the database
111     * @param strURL - URL of database to connect to
112     * @param strUser - user name to connect to the database
113     * @param strPassword - password to the database
114     * @param transactionFactory - transaction factory to use for this
115     * connection factory, can be null
116     * @throws OSSConfigException - problem accessing or locating the config file.
117     * @throws OSSDatabaseAccessException - problem accessing the database
118     */

119    public ProxoolDatabaseConnectionFactoryImpl(
120       String JavaDoc strDriver,
121       String JavaDoc strURL,
122       String JavaDoc strUser,
123       String JavaDoc strPassword,
124       DatabaseTransactionFactoryImpl transactionFactory
125    ) throws OSSConfigException,
126             OSSDatabaseAccessException
127    {
128       super(strDriver, strURL, strUser, strPassword, transactionFactory);
129       
130       // Do not start it now because when we are creating pool we need to know
131
// what database we are running on and it would create circular dependency
132
// with DatabaseImpl
133
// start();
134
}
135
136    // Helper methods ///////////////////////////////////////////////////////////
137

138    /**
139     * {@inheritDoc}
140     */

141    protected Connection JavaDoc getPooledConnection(
142       ConnectionPoolDefinition connectionpool
143    ) throws OSSDatabaseAccessException
144    {
145       Connection JavaDoc conReturn;
146       
147       try
148       {
149          conReturn = DriverManager.getConnection(connectionpool.m_connectionPool.toString());
150       }
151       catch (Exception JavaDoc eExc)
152       {
153          // ObjectPool throws Exception so convert it to something more meaningful here
154
throw new OSSDatabaseAccessException("Cannot get database connection from pool.",
155                                                  eExc);
156       }
157       
158       return conReturn;
159    }
160
161    /**
162     * {@inheritDoc}
163     */

164    protected Connection JavaDoc getPooledConnection(
165       ConnectionPoolDefinition connectionpool,
166       String JavaDoc strUser,
167       String JavaDoc strPassword
168    ) throws OSSDatabaseAccessException
169    {
170       Connection JavaDoc cntDBConnection;
171       
172       // Proxool doesn't provide any way how to get it so ask for nonpooled connection
173
try
174       {
175          cntDBConnection = DriverManager.getConnection(connectionpool.m_connectionPool.toString(),
176                                                        strUser,
177                                                        strPassword);
178          if (cntDBConnection != null)
179          {
180             m_mpNotPooledConnections.put(cntDBConnection, cntDBConnection);
181          }
182       }
183       catch (SQLException JavaDoc sqleExc)
184       {
185          throw new OSSDatabaseAccessException("Cannot get database connection" +
186                                                  " for explicitely specified user.",
187                                                  sqleExc);
188       }
189       
190       return cntDBConnection;
191    }
192
193    /**
194     * {@inheritDoc}
195     */

196    protected Object JavaDoc createConnectionPool(
197       String JavaDoc strConnectionPoolName,
198       String JavaDoc strDriverName,
199       String JavaDoc strUrl,
200       String JavaDoc strUser,
201       String JavaDoc strPassword
202    ) throws OSSException
203    {
204       PooledDatabaseConnectionFactorySetupReader setupReader
205           = new PooledDatabaseConnectionFactorySetupReader(strConnectionPoolName);
206
207       int iMinimalPoolSize = setupReader.getIntegerParameterValue(
208                PooledDatabaseConnectionFactorySetupReader.DBPOOL_MIN_SIZE).intValue();
209       int iMaximalPoolSize = setupReader.getIntegerParameterValue(
210                PooledDatabaseConnectionFactorySetupReader.DBPOOL_MAX_SIZE).intValue();
211 // DBPOOL_CAN_GROW and DBPOOL_WAIT_PERIOD is not supported Proxool at this time
212
// As soon as connection are exhausted, proxool throws an exception
213
// See mailing list at:
214
// http://sourceforge.net/mailarchive/forum.php?thread_id=2232720&forum_id=31278
215
// http://sourceforge.net/mailarchive/forum.php?thread_id=4827193&forum_id=31278
216
// boolean bCanGrow = setupReader.getBooleanParameterValue(
217
// PooledDatabaseConnectionFactorySetupReader.DBPOOL_CAN_GROW).booleanValue();
218
// long lMaxWaitTimeForConnection = setupReader.getLongParameterValue(
219
// PooledDatabaseConnectionFactorySetupReader.DBPOOL_WAIT_PERIOD).longValue();
220
boolean bValidateOnBorrow = setupReader.getBooleanParameterValue(
221                PooledDatabaseConnectionFactorySetupReader.DBPOOL_VALIDATE_BORROW).booleanValue();
222       boolean bValidateOnReturn = setupReader.getBooleanParameterValue(
223                PooledDatabaseConnectionFactorySetupReader.DBPOOL_VALIDATE_RETURN).booleanValue();
224       long lTimeBetweenEvictionRunsMillis = setupReader.getLongParameterValue(
225                PooledDatabaseConnectionFactorySetupReader.DBPOOL_IDLE_CHECK_PERIOD).longValue();
226 // int iTransactionIsolation
227
// = DatabaseImpl.getInstance().getTransactionIsolation(
228
// PooledDatabaseConnectionFactorySetupReader.convertTransactionIsolationToConstant(
229
// setupReader.getStringParameterValue(
230
// PooledDatabaseConnectionFactorySetupReader.DBPOOL_TRANSACTION_ISOLATION)
231
// .toString()));
232
// int iPreparedStatementCacheSize = setupReader.getIntegerParameterValue(
233
// PooledDatabaseConnectionFactorySetupReader.DBPOOL_PREPSTATEMENT_CACHE_SIZE)
234
// .intValue();
235

236       try
237       {
238          Class.forName("org.logicalcobwebs.proxool.ProxoolDriver");
239       }
240       catch (ClassNotFoundException JavaDoc cnfeExc)
241       {
242          throw new OSSDatabaseAccessException("Cannot found proxool driver " +
243                                               "'org.logicalcobwebs.proxool.ProxoolDriver'.",
244                                               cnfeExc);
245       }
246
247       Properties JavaDoc info = new Properties JavaDoc();
248
249       // bCanGrow is not supported, c3p0 pool size cannot grow when all connections
250
// are already requested.
251
// lMaxWaitTimeForConnection is not supported, the pool returns error immediately
252
// FATAL_SQL_EXCEPTION - not used
253
// FATAL_SQL_EXCEPTION_WRAPPER_CLASS - not used
254
info.setProperty(ProxoolConstants.HOUSE_KEEPING_SLEEP_TIME_PROPERTY,
255                        Integer.toString((int)lTimeBetweenEvictionRunsMillis));
256       info.setProperty(ProxoolConstants.HOUSE_KEEPING_TEST_SQL_PROPERTY,
257                        DatabaseImpl.getInstance().getConnectionTestStatement());
258       // INJECTABLE_CONNECTION_INTERFACE_NAME - not used
259
// INJECTABLE_STATEMENT_INTERFACE_NAME - not used
260
// INJECTABLE_PREPARED_STATEMENT_INTERFACE_NAME - not used
261
// INJECTABLE_CALLABLE_STATEMENT_INTERFACE_NAME - not used
262
// JMX_PROPERTY - not used
263
// JMX_AGENT_ID - not used
264
// JNDI_NAME - not used
265
// Set this to maximal value since we do not want connection pool killing
266
// our threads
267
info.setProperty(ProxoolConstants.MAXIMUM_ACTIVE_TIME_PROPERTY,
268                        Integer.toString(Integer.MAX_VALUE));
269       info.setProperty(ProxoolConstants.MAXIMUM_CONNECTION_COUNT_PROPERTY,
270                        Integer.toString(iMaximalPoolSize));
271       // Set this to maximal value since we do not want connection pool killing
272
// our connections
273
info.setProperty(ProxoolConstants.MAXIMUM_CONNECTION_LIFETIME_PROPERTY,
274                        Integer.toString(Integer.MAX_VALUE));
275       info.setProperty(ProxoolConstants.MINIMUM_CONNECTION_COUNT_PROPERTY,
276                        Integer.toString(iMinimalPoolSize));
277       // OVERLOAD_WITHOUT_REFUSAL_LIFETIME - not used
278
// PROTOTYPE_COUNT - not used
279
// RECENTLY_STARTED_THRESHOLD - not used
280
// SIMULTANEOUS_BUILD_THROTTLE - not used
281
// STATISTICS - not used
282
// STATISTICS_LOG_LEVEL - not used
283
info.setProperty(ProxoolConstants.TEST_BEFORE_USE_PROPERTY,
284                        Boolean.toString(bValidateOnBorrow));
285       info.setProperty(ProxoolConstants.TEST_AFTER_USE_PROPERTY,
286                        Boolean.toString(bValidateOnReturn));
287       info.setProperty(ProxoolConstants.USER_PROPERTY, strUser);
288       info.setProperty(ProxoolConstants.PASSWORD_PROPERTY, strPassword);
289       // TRACE - not used
290
// VERBOSE - not used
291

292       StringBuffer JavaDoc sbProxoolURL = new StringBuffer JavaDoc();
293       
294       sbProxoolURL.append("proxool.");
295       sbProxoolURL.append(strConnectionPoolName);
296       sbProxoolURL.append(":");
297       sbProxoolURL.append(strDriverName);
298       sbProxoolURL.append(":");
299       sbProxoolURL.append(strUrl);
300       
301       try
302       {
303          ProxoolFacade.registerConnectionPool(sbProxoolURL.toString(), info);
304       }
305       catch (ProxoolException peExc)
306       {
307          throw new OSSDatabaseAccessException("Unexpected error when registering" +
308                                                  " connection pool.", peExc);
309       }
310       
311       return sbProxoolURL.toString();
312    }
313
314    /**
315     * {@inheritDoc}
316     */

317    protected void closeConnectionPool(
318       ConnectionPoolDefinition connectionpool
319    ) throws OSSException
320    {
321       try
322       {
323          ProxoolFacade.removeConnectionPool(connectionpool.getConnectionPoolName());
324       }
325       catch (Exception JavaDoc eExc)
326       {
327          // ObjectPool throws Exception so convert it to something more meaningful here
328
throw new OSSDatabaseAccessException("Cannot close connection pool.", eExc);
329       }
330    }
331 }
332
Popular Tags