001: /**
002: * Objective Database Abstraction Layer (ODAL)
003: * Copyright (c) 2004, The ODAL Development Group
004: * All rights reserved.
005: * For definition of the ODAL Development Group please refer to LICENCE.txt file
006: *
007: * Distributable under LGPL license.
008: * See terms of license at gnu.org.
009: */package com.completex.objective.components.persistency.core.adapter;
010:
011: import com.completex.objective.components.log.Log;
012: import com.completex.objective.components.log.adapter.StdErrorLogAdapter;
013: import com.completex.objective.components.persistency.core.DatabasePolicy;
014: import com.completex.objective.components.persistency.core.impl.DatabasePolicyFactory;
015: import com.completex.objective.components.persistency.connect.ConnectionManager;
016: import com.completex.objective.components.persistency.datasource.DataSourceFactory;
017: import com.completex.objective.components.persistency.OdalRuntimePersistencyException;
018: import com.completex.objective.components.persistency.ocache.adapter.PersistencyCacheFactoryAdapter;
019: import com.completex.objective.util.PropertyMap;
020:
021: import javax.sql.DataSource;
022: import java.io.FileInputStream;
023: import java.io.IOException;
024: import java.util.Properties;
025:
026: /**
027: * Persistency implementation that uses internal Datasource implementation
028: *
029: * @author Gennady Krizhevsky
030: */
031: public class DefaultPersistencyAdapter extends BasicPersistencyAdapter {
032:
033: protected static final Log DEFAULT_LOG = StdErrorLogAdapter
034: .newLogInstance();
035: protected static final int NULL_STMT_CACHE_VALUE = -1;
036: /**
037: * Properties that are used to instatite the class
038: */
039: /**
040: * Drive string, example: org.hsqldb.jdbcDriver
041: */
042: public static final String PROP_DRIVER = ConnectionManager.PROP_DRIVER;
043: /**
044: * Connection string URL, example: jdbc:hsqldb:file:testdb
045: */
046: public static final String PROP_URL = ConnectionManager.PROP_URL;
047: /**
048: * User name used for database connection
049: */
050: public static final String PROP_USER = ConnectionManager.PROP_USER;
051: /**
052: * Password name used for database connection
053: */
054: public static final String PROP_PASSWORD = ConnectionManager.PROP_PASSWORD;
055: /**
056: * Prepared statements cache size. If the cache is not desirable or it is provided by the driver - do not set it.
057: */
058: public static final String PROP_STMT_CACHE_SIZE = "stmtCacheSize";
059: /**
060: * Maximum pooled connections limit
061: */
062: public static final String PROP_MAX_CONNECTIONS = DataSourceFactory.PROP_MAX_CONNECTIONS;
063: /**
064: * Timeout in ms on getting connection from pool
065: */
066: public static final String PROP_TIMEOUT = DataSourceFactory.PROP_TIMEOUT;
067: /**
068: * Set it to TRUE to run persistency in batch mode
069: */
070: public static final String PROP_USE_BATCH_MODIFY = "useBatchModify";
071:
072: /**
073: * SDL Map with cache factory configuration
074: *
075: * @see com.completex.objective.components.persistency.ocache.adapter.PersistencyCacheFactoryAdapter
076: */
077: public static final String PROP_CACHE_FACTORY = "cacheFactory";
078:
079: /**
080: * Set it to TRUE to disable query context
081: *
082: * @see com.completex.objective.components.persistency.core.impl.query.QueryContext
083: */
084: public static final String PROP_DISABLE_QUERY_CONTEXT = "disableQueryContext";
085: /**
086: * Set it to TRUE to disable default logging
087: */
088: public static final String PROP_DISABLE_LOGGER = "disableLogger";
089:
090: /**
091: * Correct types come from DefaultTransactionManagerFactory.TYPE_XXX constants
092: */
093: public static final String PROP_TRANSACTION_MANAGER_TYPE = "transactionManagerType";
094:
095: private PropertyMap properties;
096:
097: /**
098: * Initializes parameters and starts the persistency.
099: *
100: * @param configPath path to .sdl configuration file that looks like:
101: * <PRE>
102: * ####################################
103: * # Persistency Properties
104: * ####################################
105: * # {
106: * # driver="org.hsqldb.jdbcDriver"
107: * # url="jdbc:hsqldb:file:data/petstore"
108: * # user=sa
109: * # password=""
110: * #
111: * # disableQueryContext = FALSE
112: * # disableLogger = FALSE
113: * # transactionManagerType = JDBC
114: * #
115: * # cacheFactory = {
116: * # global = {
117: * # disabled = FALSE
118: * # }
119: * #
120: * # caches = {
121: * # categoryCache = {
122: * # class = com.completex.objective.components.ocache.impl.ExpiringLruCache
123: * # transactionSensitive = TRUE
124: * # maxSize = 100
125: * # cacheFlushInterval = "24:00:00.000"
126: * # entryFlushInterval = "24:00:00.000"
127: * # disabled = FALSE
128: * # }
129: * #
130: * # productCache = {
131: * # class = com.completex.objective.components.ocache.impl.ExpiringLruCache
132: * # transactionSensitive = TRUE
133: * # maxSize = 100
134: * # cacheFlushInterval = "24:00:00.000"
135: * # entryFlushInterval = "24:00:00.000"
136: * # disabled = FALSE
137: * # }
138: * # }
139: * # }
140: * # }
141: * </PRE>
142: * @throws IOException
143: */
144: public DefaultPersistencyAdapter(String configPath)
145: throws IOException {
146: PropertyMap properties = new PropertyMap();
147: if (configPath.endsWith(".properties")) {
148: properties.load(new FileInputStream(configPath));
149: } else if (configPath.endsWith(".sdl")) {
150: properties.loadSdl(configPath);
151: } else {
152: throw new OdalRuntimePersistencyException(
153: "Unrecognized config file extension : "
154: + configPath);
155: }
156: setup(properties, getDefaultPolicyFactory(), null);
157: start();
158: }
159:
160: /**
161: * Initializes parameters and starts the persistency
162: *
163: * @param properties one of PROP_XXX constants as keys. To configure object cache instance of PropertyMap should be used.
164: */
165: public DefaultPersistencyAdapter(Properties properties) {
166: this (properties, null);
167: }
168:
169: /**
170: * Initializes parameters and starts the persistency
171: *
172: * @param properties
173: * @param logger
174: */
175: public DefaultPersistencyAdapter(Properties properties, Log logger) {
176: this (properties, getDefaultPolicyFactory(), logger);
177: }
178:
179: /**
180: * Initializes parameters and starts the persistency
181: *
182: * @param properties
183: * @param policyFactory
184: * @param logger
185: */
186: public DefaultPersistencyAdapter(Properties properties,
187: DatabasePolicyFactory policyFactory, Log logger) {
188: setup(properties, policyFactory, logger);
189: start();
190: }
191:
192: public DefaultPersistencyAdapter(Properties properties,
193: DataSource dataSource, Log logger) {
194: setDataSource(dataSource);
195: setup(properties, getDefaultPolicyFactory(), logger);
196: start();
197: }
198:
199: /**
200: * Initializes parameters and starts the persistency
201: *
202: * @param policy
203: * @param driver
204: * @param url
205: * @param user
206: * @param password
207: * @param stmtCacheSize
208: * @param maxConnections
209: * @param timeout
210: * @param logger
211: */
212: public DefaultPersistencyAdapter(DatabasePolicy policy,
213: String driver, String url, String user, String password,
214: int stmtCacheSize, int maxConnections, int timeout,
215: Log logger) {
216: this (policy, driver, url, user, password, stmtCacheSize,
217: maxConnections, timeout, null, logger);
218: }
219:
220: public DefaultPersistencyAdapter(DatabasePolicy policy,
221: String driver, String url, String user, String password,
222: int stmtCacheSize, int maxConnections, int timeout,
223: String transactionManagerType, Log logger) {
224: setDatabasePolicy(policy);
225: setStmtCacheSize(stmtCacheSize);
226: setLogger(logger);
227: setTransactionManagerType(transactionManagerType);
228: if (DefaultTransactionManagerFactory
229: .isJdbcType(getTransactionManagerType())) {
230: setup0(driver, url, user, password, maxConnections,
231: timeout, logger);
232: }
233: start();
234: }
235:
236: public static DefaultPersistencyAdapter newPrimitiveDefaultPersistencyAdapter(
237: DatabasePolicy policy, int stmtCacheSize, Log logger) {
238: return new DefaultPersistencyAdapter(policy, null, null, null,
239: null, stmtCacheSize, 0, 0,
240: DefaultTransactionManagerFactory.TYPE_JDBC_PRIMITIVE,
241: logger);
242: }
243:
244: protected void setup0(String driver, String url, String user,
245: String password, int maxConnections, int timeout, Log logger) {
246: logger = setDefaultLogger(logger);
247: initDataSource(driver, url, user, password, maxConnections,
248: timeout, logger);
249: getLogger().info(
250: "Connected to database [url: " + url + "; user: "
251: + user + "; password: " + password + "]");
252: }
253:
254: /**
255: * Partially Initializes parameters and does not starts the persistency
256: *
257: * @param databasePolicy
258: * @param stmtCacheSize
259: * @param logger
260: */
261: protected DefaultPersistencyAdapter(DatabasePolicy databasePolicy,
262: int stmtCacheSize, Log logger) {
263: super (databasePolicy, stmtCacheSize, logger);
264: }
265:
266: protected void initDataSource(String driver, String url,
267: String user, String pass, int maxConnections, int timeout,
268: Log logger) {
269:
270: if (getDataSource() == null) {
271: initDefaultDataSource(driver, url, user, pass,
272: maxConnections, logger);
273: }
274: }
275:
276: protected void initDefaultDataSource(String driver, String url,
277: String user, String pass, int maxConnections, Log logger) {
278: DefaultDataSourceFactory dataSourceFactory;
279: if (properties == null) {
280: dataSourceFactory = new DefaultDataSourceFactory();
281: dataSourceFactory.setDriver(driver);
282: dataSourceFactory.setUrl(url);
283: dataSourceFactory.setUser(user);
284: dataSourceFactory.setPassword(pass);
285: dataSourceFactory.setMaxConnections(maxConnections);
286: } else {
287: dataSourceFactory = new DefaultDataSourceFactory(properties);
288: }
289:
290: dataSourceFactory.setLogger(logger);
291: DataSource dataSource = dataSourceFactory.newDataSource();
292: setDataSource(dataSource);
293: }
294:
295: private Log setDefaultLogger(Log logger) {
296: if (logger == null) {
297: setLogger(DEFAULT_LOG);
298: } else {
299: setLogger(logger);
300: }
301: return getLogger();
302: }
303:
304: private void setup(Properties props,
305: DatabasePolicyFactory policyFactory, Log logger) {
306: policyFactory = policyFactory == null ? getDefaultPolicyFactory()
307: : policyFactory;
308: properties = PropertyMap.toPropertyMap(props);
309: String driver = properties.getProperty(PROP_DRIVER, true);
310: String url = properties.getProperty(PROP_URL, true);
311: String user = properties.getProperty(PROP_USER, true);
312: String password = properties.getProperty(PROP_PASSWORD, "");
313: int stmtCacheSize = properties.getInt(PROP_STMT_CACHE_SIZE,
314: NULL_STMT_CACHE_VALUE);
315: int maxConnections = properties.getInt(PROP_MAX_CONNECTIONS,
316: DEFAULT_MAX_CONNECTIONS);
317: int timeout = properties.getInt(PROP_TIMEOUT, 0);
318: boolean useBatchModify = properties
319: .getBoolean(PROP_USE_BATCH_MODIFY);
320: boolean disableQueryContext = properties
321: .getBoolean(PROP_DISABLE_QUERY_CONTEXT);
322: boolean disableLogger = properties
323: .getBoolean(PROP_DISABLE_LOGGER);
324:
325: setDisableQueryContext(disableQueryContext);
326: setUseBatchModify(useBatchModify);
327: DatabasePolicy databasePolicy = policyFactory
328: .getDatabasePolicy(url);
329: setDatabasePolicy(databasePolicy);
330: //
331: // This is the only case when we set stmtCacheSize to DEFAULT_STMT_CACHE_SIZE
332: // since the value is not set. In other constructors it has to be provided explicitely
333: //
334: stmtCacheSize = stmtCacheSize == NULL_STMT_CACHE_VALUE ? DEFAULT_STMT_CACHE_SIZE
335: : stmtCacheSize;
336: setStmtCacheSize(stmtCacheSize);
337: if (disableLogger) {
338: logger = Log.NULL_LOGGER;
339: }
340: setup0(driver, url, user, password, maxConnections, timeout,
341: logger);
342:
343: PropertyMap cacheFactoryMap = properties
344: .getPropertyMap(PROP_CACHE_FACTORY);
345: if (cacheFactoryMap != null) {
346: setCacheFactoryManager(new PersistencyCacheFactoryAdapter(
347: cacheFactoryMap));
348: }
349: }
350:
351: public PropertyMap getProperties() {
352: return properties;
353: }
354:
355: public String toString() {
356: return super .toString() + ": " + getTransactionManager();
357: }
358:
359: }
|