/* * Copyright 2008 Alberto Gimeno <gimenete at gmail.com> * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ package siena; import java.io.IOException; import java.lang.reflect.Modifier; import java.net.URL; import java.util.Map; import java.util.Properties; import java.util.concurrent.ConcurrentHashMap; import siena.logging.SienaLogger; import siena.logging.SienaLoggerFactory; /** * This is the class responsible of loading * <code>PersistenceManager</code> implementations. * Each group of persistent classes must be in the same * package. That package must have a <code>siena.properties</code> * file containing the information of the <code>PersistenceManager</code> * to be used. * * @author gimenete * */ public class PersistenceManagerFactory { private static PersistenceManagerFactory singleton; /** * Logger for PersistenceManagerFactory. */ protected static SienaLogger logger = SienaLoggerFactory.getLogger(PersistenceManagerFactory.class); private Map<String, PersistenceManager> configuration; public PersistenceManagerFactory() { configuration = new ConcurrentHashMap<String, PersistenceManager>(); } public static PersistenceManager getPersistenceManager(Class<?> clazz) { return getInstance().get(clazz); } private static PersistenceManagerFactory getInstance() { if(singleton == null) singleton = new PersistenceManagerFactory(); return singleton; } private PersistenceManager get(Class<?> clazz) { String pack = getPackage(clazz); PersistenceManager pm = configuration.get(pack); if(pm != null) return pm; URL url = clazz.getResource("siena.properties"); if(url == null) throw new SienaException("Cannot load siena.properties file for package: "+pack); Properties p = new Properties(); try { p.load(url.openStream()); } catch (IOException e) { throw new SienaException(e); } // Override with system properties String prefix = "siena."+pack+"."; Properties sysprops = System.getProperties(); for (Map.Entry<Object, Object> entry : sysprops.entrySet()) { String key = entry.getKey().toString(); if(key.startsWith(prefix)) { String value = entry.getValue().toString(); p.setProperty(key.substring(prefix.length()), value); } } // -- String impl = p.getProperty("implementation"); if(impl == null) throw new SienaException("key 'implementation' not found at "+url); try { pm = (PersistenceManager) Class.forName(impl).newInstance(); pm.init(p); } catch (Exception e) { throw new SienaException("Error while creating instance of: "+impl, e); } configuration.put(pack, pm); return pm; } public static void install(PersistenceManager pm, Class<?> clazz) { // if class is abstract, it is not installed if(!Modifier.isAbstract(clazz.getModifiers())){ getInstance().put(pm, getPackage(clazz)); } } public static void install(PersistenceManager pm, Iterable<Class<?>> clazzes) { for(Class<?> clazz: clazzes){ if(!Modifier.isAbstract(clazz.getModifiers())){ getInstance().put(pm, getPackage(clazz)); } } } private void put(PersistenceManager pm, String pack) { configuration.put(pack, pm); } private static String getPackage(Class<?> clazz) { String clazzName = clazz.getName(); return clazzName.substring(0, clazzName.lastIndexOf('.')); } }