KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > com > mchange > v2 > c3p0 > DataSources


1 /*
2  * Distributed as part of c3p0 v.0.9.1
3  *
4  * Copyright (C) 2005 Machinery For Change, Inc.
5  *
6  * Author: Steve Waldman <swaldman@mchange.com>
7  *
8  * This library is free software; you can redistribute it and/or modify
9  * it under the terms of the GNU Lesser General Public License version 2.1, as
10  * published by the Free Software Foundation.
11  *
12  * This software 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 Lesser General Public License for more details.
16  *
17  * You should have received a copy of the GNU Lesser General Public License
18  * along with this software; see the file LICENSE. If not, write to the
19  * Free Software Foundation, Inc., 59 Temple Place, Suite 330,
20  * Boston, MA 02111-1307, USA.
21  */

22
23
24 package com.mchange.v2.c3p0;
25
26 import com.mchange.v2.log.*;
27 import java.beans.PropertyChangeEvent JavaDoc;
28 import java.beans.PropertyVetoException JavaDoc;
29 import java.util.Arrays JavaDoc;
30 import java.util.Collections JavaDoc;
31 import java.util.HashMap JavaDoc;
32 import java.util.HashSet JavaDoc;
33 import java.util.Iterator JavaDoc;
34 import java.util.Map JavaDoc;
35 import java.util.Properties JavaDoc;
36 import java.util.Set JavaDoc;
37 import java.sql.SQLException JavaDoc;
38 import javax.sql.DataSource JavaDoc;
39 import javax.sql.ConnectionPoolDataSource JavaDoc;
40 import com.mchange.v2.sql.SqlUtils;
41 import com.mchange.v2.beans.BeansUtils;
42
43 /**
44  * <p>A simple factory class for creating DataSources. Generally, users will call <tt>DataSources.unpooledDataSource()</tt> to get
45  * a basic DataSource, and then get a pooled version by calling <tt>DataSources.pooledDataSource()</tt>.</p>
46  *
47  * <p>Most users will not need to worry about configuration details. If you want to use a PreparedStatement cache, be sure to call
48  * the version of <tt>DataSources.pooledDataSource()</tt> that accepts a <tt>statement_cache_size</tt> parameter, and set that to
49  * be a number (much) greater than zero. (For maximum performance, you would set this to be several times the number kinds of
50  * PreparedStatements you expect your application to use.)</p>
51  *
52  * <p>For those interested in detailed configuration, note that c3p0 pools can be configured by explicit method calls on PoolConfig objects,
53  * by defining System properties, or by defining a <tt>c3p0.properties</tt> file in your resource path. See {@link com.mchange.v2.c3p0.PoolConfig}
54  * for details.</p>
55  *
56  */

57 public final class DataSources
58 {
59     final static MLogger logger = MLog.getLogger( DataSources.class );
60
61     final static Set JavaDoc WRAPPER_CXN_POOL_DATA_SOURCE_OVERWRITE_PROPS; //22 -- includes factory class location
62
final static Set JavaDoc POOL_BACKED_DATA_SOURCE_OVERWRITE_PROPS; //2 -- includes factory class location, excludes pool-owner id token
63

64     static
65     {
66     // As of c3p0-0.9.1
67
//
68
// This list is no longer updated, as the PoolConfig approach to setting up DataSources
69
// is now deprecated. (This was getting to be hard to maintain as new config properties
70
// were added.)
71
String JavaDoc[] props = new String JavaDoc[]
72     {
73         "checkoutTimeout", //1
74
"acquireIncrement", //2
75
"acquireRetryAttempts", //3
76
"acquireRetryDelay", //4
77
"autoCommitOnClose", //5
78
"connectionTesterClassName", //6
79
"forceIgnoreUnresolvedTransactions", //7
80
"idleConnectionTestPeriod", //8
81
"initialPoolSize", //9
82
"maxIdleTime", //10
83
"maxPoolSize", //11
84
"maxStatements", //12
85
"maxStatementsPerConnection", //13
86
"minPoolSize", //14
87
"propertyCycle", //15
88
"breakAfterAcquireFailure", //16
89
"testConnectionOnCheckout", //17
90
"testConnectionOnCheckin", //18
91
"usesTraditionalReflectiveProxies", //19
92
"preferredTestQuery", //20
93
"automaticTestTable", //21
94
"factoryClassLocation" //22
95
};
96
97     WRAPPER_CXN_POOL_DATA_SOURCE_OVERWRITE_PROPS = Collections.unmodifiableSet( new HashSet JavaDoc( Arrays.asList( props ) ) );
98
99     // As of c3p0-0.9.1
100
//
101
// This list is no longer updated, as the PoolConfig approach to setting up DataSources
102
// is now deprecated. (This was getting to be hard to maintain as new config properties
103
// were added.)
104
props = new String JavaDoc[]
105     {
106         "numHelperThreads",
107         "factoryClassLocation"
108     };
109
110     POOL_BACKED_DATA_SOURCE_OVERWRITE_PROPS = Collections.unmodifiableSet( new HashSet JavaDoc( Arrays.asList( props ) ) );
111     }
112
113     /**
114      * Defines an unpooled DataSource all of whose paramateres (especially jdbcUrl)
115      * should be set in config files.
116      */

117     public static DataSource JavaDoc unpooledDataSource() throws SQLException JavaDoc
118     {
119     DriverManagerDataSource out = new DriverManagerDataSource();
120     return out;
121     }
122
123     public static DataSource JavaDoc unpooledDataSource(String JavaDoc jdbcUrl) throws SQLException JavaDoc
124     {
125     DriverManagerDataSource out = new DriverManagerDataSource();
126     out.setJdbcUrl( jdbcUrl );
127     return out;
128     }
129
130     /**
131      * Defines an unpooled DataSource on the specified JDBC URL, authenticating with a username and password.
132      */

133     public static DataSource JavaDoc unpooledDataSource(String JavaDoc jdbcUrl, String JavaDoc user, String JavaDoc password) throws SQLException JavaDoc
134     {
135     Properties JavaDoc props = new Properties JavaDoc();
136     props.put(SqlUtils.DRIVER_MANAGER_USER_PROPERTY, user);
137     props.put(SqlUtils.DRIVER_MANAGER_PASSWORD_PROPERTY, password);
138     return unpooledDataSource( jdbcUrl, props );
139     }
140
141     /**
142      * Defines an unpooled DataSource on the specified JDBC URL.
143      *
144      * @param driverProps the usual DriverManager properties for your JDBC driver
145      * (e.g. "user" and "password" for all drivers that support
146      * authentication)
147      *
148      * @see java.sql.DriverManager
149      */

150     public static DataSource JavaDoc unpooledDataSource(String JavaDoc jdbcUrl, Properties JavaDoc driverProps) throws SQLException JavaDoc
151     {
152     DriverManagerDataSource out = new DriverManagerDataSource();
153     out.setJdbcUrl( jdbcUrl );
154     out.setProperties( driverProps );
155     return out;
156     }
157
158     /**
159      * <p>Creates a pooled version of an unpooled DataSource using default configuration information.</p>
160      * <p><b>NOTE:</b> By default, statement pooling is turned off, because for simple databases that do
161      * not pre-parse and optimize PreparedStatements, statement caching is a net
162      * performance loss. But if your database <i>does</i> optimize PreparedStatements
163      * you'll want to turn StatementCaching on via {@link #pooledDataSource(javax.sql.DataSource, int)}.</p>
164      * @return a DataSource that can be cast to a {@link PooledDataSource} if you are interested in pool statistics
165      */

166     public static DataSource JavaDoc pooledDataSource( DataSource JavaDoc unpooledDataSource ) throws SQLException JavaDoc
167     { return pooledDataSource( unpooledDataSource, null, (Map JavaDoc) null ); }
168
169     /**
170      * <p>Creates a pooled version of an unpooled DataSource using default configuration information
171      * and the specified startement cache size.
172      * Use a value greater than zero to turn statement caching on.</p>
173      *
174      * @return a DataSource that can be cast to a {@link PooledDataSource} if you are interested in pool statistics
175      */

176     public static DataSource JavaDoc pooledDataSource( DataSource JavaDoc unpooledDataSource, int statement_cache_size ) throws SQLException JavaDoc
177     {
178 // PoolConfig pcfg = new PoolConfig();
179
// pcfg.setMaxStatements( statement_cache_size );
180

181     Map JavaDoc overrideProps = new HashMap JavaDoc();
182     overrideProps.put( "maxStatements", new Integer JavaDoc( statement_cache_size ) );
183     return pooledDataSource( unpooledDataSource, null, overrideProps );
184     }
185
186     /**
187      * <p>Creates a pooled version of an unpooled DataSource using configuration
188      * information supplied explicitly by a {@link com.mchange.v2.c3p0.PoolConfig}.
189      *
190      * @return a DataSource that can be cast to a {@link PooledDataSource} if you are interested in pool statistics
191      *
192      * @deprecated if you want to set properties programmatically, please construct a ComboPooledDataSource and
193      * set its properties rather than using PoolConfig
194      */

195     public static DataSource JavaDoc pooledDataSource( DataSource JavaDoc unpooledDataSource, PoolConfig pcfg ) throws SQLException JavaDoc
196     {
197     try
198         {
199         WrapperConnectionPoolDataSource wcpds = new WrapperConnectionPoolDataSource();
200         wcpds.setNestedDataSource( unpooledDataSource );
201         
202         // set PoolConfig info -- WrapperConnectionPoolDataSource properties
203
BeansUtils.overwriteSpecificAccessibleProperties( pcfg, wcpds, WRAPPER_CXN_POOL_DATA_SOURCE_OVERWRITE_PROPS );
204         
205         PoolBackedDataSource nascent_pbds = new PoolBackedDataSource();
206         nascent_pbds.setConnectionPoolDataSource( wcpds );
207         BeansUtils.overwriteSpecificAccessibleProperties( pcfg, nascent_pbds, POOL_BACKED_DATA_SOURCE_OVERWRITE_PROPS );
208
209         return nascent_pbds;
210         }
211 // catch ( PropertyVetoException e )
212
// {
213
// e.printStackTrace();
214
// PropertyChangeEvent evt = e.getPropertyChangeEvent();
215
// throw new SQLException("Illegal value attempted for property " + evt.getPropertyName() + ": " + evt.getNewValue());
216
// }
217
catch ( Exception JavaDoc e )
218         {
219         //e.printStackTrace();
220
SQLException JavaDoc sqle = SqlUtils.toSQLException("Exception configuring pool-backed DataSource: " + e, e);
221         if (Debug.DEBUG && Debug.TRACE >= Debug.TRACE_MED && logger.isLoggable( MLevel.FINE ) && e != sqle)
222             logger.log( MLevel.FINE, "Converted exception to throwable SQLException", e );
223         throw sqle;
224         }
225     }
226
227     /*
228     public static DataSource pooledDataSource( DataSource unpooledDataSource, String overrideDefaultUser, String overrideDefaultPassword ) throws SQLException
229     {
230     Map overrideProps;
231
232     if (overrideDefaultUser != null)
233         {
234         overrideProps = new HashMap();
235         overrideProps.put( "overrideDefaultUser", overrideDefaultUser );
236         overrideProps.put( "overrideDefaultPassword", overrideDefaultPassword );
237         }
238     else
239         overrideProps = null;
240
241     return pooledDataSource( unpooledDataSource, null, overrideProps );
242     }
243     */

244
245     public static DataSource JavaDoc pooledDataSource( DataSource JavaDoc unpooledDataSource, String JavaDoc configName ) throws SQLException JavaDoc
246     { return pooledDataSource( unpooledDataSource, configName, null ); }
247
248     public static DataSource JavaDoc pooledDataSource( DataSource JavaDoc unpooledDataSource, Map JavaDoc overrideProps ) throws SQLException JavaDoc
249     { return pooledDataSource( unpooledDataSource, null, overrideProps ); }
250
251     public static DataSource JavaDoc pooledDataSource( DataSource JavaDoc unpooledDataSource, String JavaDoc configName, Map JavaDoc overrideProps ) throws SQLException JavaDoc
252     {
253     try
254         {
255         WrapperConnectionPoolDataSource wcpds = new WrapperConnectionPoolDataSource(configName);
256         wcpds.setNestedDataSource( unpooledDataSource );
257         if (overrideProps != null)
258             BeansUtils.overwriteAccessiblePropertiesFromMap( overrideProps,
259                                      wcpds,
260                                      false,
261                                      null,
262                                      true,
263                                      MLevel.WARNING,
264                                      MLevel.WARNING,
265                                      false);
266         
267         PoolBackedDataSource nascent_pbds = new PoolBackedDataSource(configName);
268         nascent_pbds.setConnectionPoolDataSource( wcpds );
269         if (overrideProps != null)
270             BeansUtils.overwriteAccessiblePropertiesFromMap( overrideProps,
271                                      nascent_pbds,
272                                      false,
273                                      null,
274                                      true,
275                                      MLevel.WARNING,
276                                      MLevel.WARNING,
277                                      false);
278
279         return nascent_pbds;
280         }
281 // catch ( PropertyVetoException e )
282
// {
283
// e.printStackTrace();
284
// PropertyChangeEvent evt = e.getPropertyChangeEvent();
285
// throw new SQLException("Illegal value attempted for property " + evt.getPropertyName() + ": " + evt.getNewValue());
286
// }
287
catch ( Exception JavaDoc e )
288         {
289         //e.printStackTrace();
290
SQLException JavaDoc sqle = SqlUtils.toSQLException("Exception configuring pool-backed DataSource: " + e, e);
291         if (Debug.DEBUG && Debug.TRACE >= Debug.TRACE_MED && logger.isLoggable( MLevel.FINE ) && e != sqle)
292             logger.log( MLevel.FINE, "Converted exception to throwable SQLException", e );
293         throw sqle;
294         }
295     }
296
297     /**
298      * <p>Creates a pooled version of an unpooled DataSource using configuration
299      * information supplied explicitly by a Java Properties object.</p>
300      *
301      * @return a DataSource that can be cast to a {@link PooledDataSource} if you are interested in pool statistics
302      * @see com.mchange.v2.c3p0.PoolConfig
303      */

304     public static DataSource JavaDoc pooledDataSource( DataSource JavaDoc unpooledDataSource, Properties JavaDoc props ) throws SQLException JavaDoc
305     {
306     //return pooledDataSource( unpooledDataSource, new PoolConfig( props ) );
307

308     Properties JavaDoc peeledProps = new Properties JavaDoc();
309     for (Iterator JavaDoc ii = props.keySet().iterator(); ii.hasNext(); )
310         {
311         String JavaDoc propKey = (String JavaDoc) ii.next();
312         String JavaDoc propVal = props.getProperty( propKey );
313         String JavaDoc peeledKey = (propKey.startsWith("c3p0.") ? propKey.substring(5) : propKey );
314         peeledProps.put( peeledKey, propVal );
315         }
316     return pooledDataSource( unpooledDataSource, null, peeledProps );
317     }
318
319     /**
320      * <p>Immediately releases resources (Threads and database Connections) that are
321      * held by a C3P0 DataSource.
322      *
323      * <p>Only DataSources created by the poolingDataSource() method hold any
324      * non-memory resources. Calling this method on unpooled DataSources is
325      * effectively a no-op.</p>
326      *
327      * <p>You can safely presume that destroying a pooled DataSource that is wrapped around
328      * another DataSource created by this library destroys both the outer and the wrapped
329      * DataSource. There is no reason to hold a reference to a nested DataSource in order
330      * to explicitly destroy it.</p>
331      *
332      * @see com.mchange.v2.c3p0.PoolConfig
333      */

334     public static void destroy( DataSource JavaDoc pooledDataSource ) throws SQLException JavaDoc
335     { destroy( pooledDataSource, false ); }
336
337
338     /**
339      * @deprecated forceDestroy() is no longer meaningful, as a set of pools is now
340      * directly associated with a DataSource, and not potentially shared.
341      * (This simplification was made possible by canonicalization of
342      * JNDI-looked-up DataSources within a virtual machine.) Just use
343      * DataSources.destroy().
344      *
345      * @see #destroy
346      */

347     public static void forceDestroy( DataSource JavaDoc pooledDataSource ) throws SQLException JavaDoc
348     { destroy( pooledDataSource, true ); }
349
350     private static void destroy( DataSource JavaDoc pooledDataSource, boolean force ) throws SQLException JavaDoc
351     {
352     if ( pooledDataSource instanceof PoolBackedDataSource)
353         {
354         ConnectionPoolDataSource JavaDoc cpds = ((PoolBackedDataSource) pooledDataSource).getConnectionPoolDataSource();
355         if (cpds instanceof WrapperConnectionPoolDataSource)
356             destroy( ((WrapperConnectionPoolDataSource) cpds).getNestedDataSource(), force );
357         }
358     if ( pooledDataSource instanceof PooledDataSource )
359         ((PooledDataSource) pooledDataSource).close( force );
360     }
361
362     private DataSources()
363     {}
364 }
365
366
367
368
369
Popular Tags