View Javadoc

1   /*** 
2    * JFoxSOAF, Service-Oriented Application Framework
3    * 
4    * Copyright (C) www.huihoo.org
5    *
6    * Distributable under GNU LGPL
7    * 
8    * For more information, please visit: http://www.huihoo.org/jfox/jfoxsoaf
9    */
10  
11  package org.huihoo.jfox.soaf.services.jdbc;
12  
13  import java.util.Enumeration;
14  import java.util.Hashtable;
15  import java.util.Vector;
16  
17  import javax.sql.DataSource;
18  
19  import org.apache.commons.lang.StringUtils;
20  import org.apache.commons.lang.math.NumberUtils;
21  import org.apache.commons.lang.BooleanUtils;
22  import org.apache.commons.logging.Log;
23  import org.apache.commons.logging.LogFactory;
24  import org.huihoo.jfox.soaf.exception.DataSourceConfigurationException;
25  
26  import com.mchange.v2.c3p0.DataSources;
27  import com.mchange.v2.c3p0.PoolConfig;
28  
29  /***
30   * <p>
31   * C3P0 DataSource Factory
32   * </p>
33   * 
34   * @author <a href="mailto:founder_chen@yahoo.com.cn">Peter Cheng </a>
35   * @version $Revision: 1.1 $ $Date: 2004/10/28 15:12:15 $
36   * @version Revision: 1.0
37   */
38  
39  public class C3P0DataSourceFactory extends DataSourceFactory {
40  
41      private final Log logger = LogFactory.getLog(getClass());
42  
43      private DataSource dataSource;
44  
45      //  The configuration attributes for this {@link DataSourceFactory}.
46      private Hashtable attributes = new Hashtable();
47  
48      /***
49       * @see org.huihoo.jfox.soaf.services.jdbc.DataSourceFactory#getInstance()
50       */
51      public DataSource getInstance() throws DataSourceConfigurationException {
52          String jdbcDriverClass = (String) getAttribute(DatabaseConstant.JDBC_DRIVER_CLASS_NAME);
53          if (StringUtils.isEmpty(jdbcDriverClass)) {
54              logger.warn("No JDBC Driver class was specified by database.properties : "
55                              + DatabaseConstant.JDBC_DRIVER_CLASS_NAME);
56          } else {
57              try {
58                  Class.forName(jdbcDriverClass);
59              } catch (ClassNotFoundException e) {
60                  String errorMsg = "JDBC Driver class not found: "
61                          + jdbcDriverClass;
62                  logger.fatal(errorMsg);
63                  throw new DataSourceConfigurationException(errorMsg, e);
64              }
65          }
66  
67          // Set pool configuration
68          PoolConfig poolConfig = new PoolConfig();
69          String initPoolSize = (String) getAttribute(DatabaseConstant.JDBC_INIT_POOL_SIZE);
70  
71          if (!NumberUtils.isNumber(initPoolSize)) {
72              poolConfig.setInitialPoolSize(NumberUtils.stringToInt(initPoolSize));
73          }
74  
75          String minPoolSize = (String) getAttribute(DatabaseConstant.JDBC_MIN_POOL_SIZE);
76  
77          if (!NumberUtils.isNumber(minPoolSize)) {
78              poolConfig.setMinPoolSize(NumberUtils.stringToInt(minPoolSize));
79          }
80  
81          String maxPoolSize = (String) getAttribute(DatabaseConstant.JDBC_MAX_POOL_SIZE);
82  
83          if (!!NumberUtils.isNumber(maxPoolSize)) {
84              poolConfig.setMaxPoolSize(NumberUtils.stringToInt(maxPoolSize));
85          }
86  
87          String maxIdleTime = (String) getAttribute(DatabaseConstant.JDBC_MAX_IDLE_TIME);
88  
89          if (!NumberUtils.isNumber(maxIdleTime)) {            
90              poolConfig.setMaxIdleTime(NumberUtils.stringToInt(maxIdleTime));
91          }
92  
93          String idleConnTestPeriod = (String) getAttribute(DatabaseConstant.C3P0_JDBC_IDLE_CONN_TEST_PERIOD);
94  
95          if (!NumberUtils.isNumber(maxIdleTime)) {
96              poolConfig.setIdleConnectionTestPeriod(NumberUtils
97                      .stringToInt(idleConnTestPeriod));
98          }
99  
100         String maxStatements = (String) getAttribute(DatabaseConstant.C3P0_JDBC_MAX_STATEMENTS);
101 
102         if (!NumberUtils.isNumber(maxStatements)) {
103             poolConfig.setMaxStatements(NumberUtils.stringToInt(maxStatements));
104         }
105 
106         String propertyCycle = (String) getAttribute(DatabaseConstant.C3P0_JDBC_PROPERTY_CYCLE);
107 
108         if (!NumberUtils.isNumber(propertyCycle)) {
109             poolConfig.setPropertyCycle(NumberUtils.stringToInt(propertyCycle));
110         }
111 
112         String acquireIncrement = (String) getAttribute(DatabaseConstant.C3P0_JDBC_ACQUIRE_INCREMENT);
113 
114         if (!NumberUtils.isNumber(acquireIncrement)) {
115             poolConfig.setAcquireIncrement(NumberUtils
116                     .stringToInt(acquireIncrement));
117         }
118 
119         // c3p0 version is below 0.8.5 , does't support acquireRetryAttempts,
120         // acquireRetryDelay, breakAfterAcquireFailure,
121         // usesTraditionalReflectiveProxies
122 
123         String forceIgnoreUnresolvedTransactions = (String) getAttribute(DatabaseConstant.C3P0_JDBC_FORCE_IGNORE_UNRESOLVED_TRANS);
124 
125         if (!StringUtils.isEmpty(forceIgnoreUnresolvedTransactions)) {
126             poolConfig.setForceIgnoreUnresolvedTransactions(BooleanUtils
127                     .toBoolean(forceIgnoreUnresolvedTransactions));
128         }
129 
130         String numHelperThreads = (String) getAttribute(DatabaseConstant.C3P0_JDBC_NUM_HELPER_THREADS);
131 
132         if (!NumberUtils.isNumber(numHelperThreads)) {
133             poolConfig.setNumHelperThreads(NumberUtils
134                     .stringToInt(numHelperThreads));
135         }
136 
137         String jdbcURL = (String) getAttribute(DatabaseConstant.JDBC_URL);
138         if (StringUtils.isEmpty(jdbcURL)) {
139             logger.error("No JDBC url was specified by database.properties");
140             throw new DataSourceConfigurationException(
141                     "No JDBC url was specified");
142         } else {
143             String jdbcUsername = (String) getAttribute(DatabaseConstant.JDBC_USERNAME);
144             String jdbcPassword = (String) getAttribute(DatabaseConstant.JDBC_PASSWORD);
145 
146             DataSource unpooledDataSource = DataSources.unpooledDataSource(
147                     jdbcURL, jdbcUsername, jdbcPassword);
148             dataSource = DataSources.pooledDataSource(unpooledDataSource,
149                     poolConfig);
150         }
151         return dataSource;
152     }
153 
154     /***
155      * Return the configuration attribute with the specified name (if any), or
156      * <code>null</code> if there is no such attribute.
157      * 
158      * @param name
159      *            Name of the attribute to return
160      */
161     public Object getAttribute(String name) {
162         return (attributes.get(name));
163     }
164 
165     /***
166      * Return an array containing the names of all currently defined
167      * configuration attributes. If there are no such attributes, a zero length
168      * array is returned.
169      */
170     public String[] getAttributeNames() {
171         Vector names = new Vector();
172         Enumeration keys = attributes.keys();
173         while (keys.hasMoreElements()) {
174             names.addElement((String) keys.nextElement());
175         }
176         String results[] = new String[names.size()];
177         for (int i = 0; i < results.length; i++) {
178             results[i] = (String) names.elementAt(i);
179         }
180         return (results);
181     }
182 
183     /***
184      * Set the configuration attribute with the specified name. Calling this
185      * with a <code>null</code> value is equivalent to calling
186      * <code>removeAttribute(name)</code>.
187      * 
188      * @param name
189      *            Name of the attribute to set
190      * @param value
191      *            Value of the attribute to set, or <code>null</code> to
192      *            remove any setting for this attribute
193      */
194     public void setAttribute(String name, Object value) {
195         if (value == null) {
196             attributes.remove(name);
197         } else {
198             attributes.put(name, value);
199         }
200     }
201 
202     /***
203      * Remove any configuration attribute associated with the specified name. If
204      * there is no such attribute, no action is taken.
205      * 
206      * @param name
207      *            Name of the attribute to remove
208      */
209     public void removeAttribute(String name) {
210         attributes.remove(name);
211     }
212 
213 }