
org.ow2.bonita.runtime.ClassDataLoader Maven / Gradle / Ivy
/**
* Copyright (C) 2006 Bull S. A. S.
* Bull, Rue Jean Jaures, B.P.68, 78340, Les Clayes-sous-Bois
* This library is free software; you can redistribute it and/or modify it under the terms
* of the GNU Lesser General Public License as published by the Free Software Foundation
* version 2.1 of the License.
* This library is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
* without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
* See the GNU Lesser General Public License for more details.
* You should have received a copy of the GNU Lesser General Public License along with this
* program; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth
* Floor, Boston, MA 02110-1301, USA.
**/
package org.ow2.bonita.runtime;
import java.lang.reflect.Field;
import java.util.HashMap;
import java.util.Map;
import java.util.logging.Level;
import java.util.logging.Logger;
import org.ow2.bonita.pvm.internal.util.ReflectUtil;
import org.ow2.bonita.definition.ClassInfo;
import org.ow2.bonita.definition.PackageClassData;
import org.ow2.bonita.facade.uuid.PackageDefinitionUUID;
import org.ow2.bonita.services.Repository;
import org.ow2.bonita.util.BonitaRuntimeException;
import org.ow2.bonita.util.EngineEnvTool;
import org.ow2.bonita.util.Misc;
public final class ClassDataLoader {
private static final Logger LOG = Logger.getLogger(ClassDataLoader.class.getName());
private static Map packageClassLoaders =
new HashMap();
private ClassDataLoader() { }
public static Class< ? > getClass(final PackageDefinitionUUID packageUUID,
final String className) throws ClassNotFoundException {
if (LOG.isLoggable(Level.FINE)) {
LOG.fine("Looking for class " + className + ", in package : " + packageUUID);
}
Class< ? > result = null;
if (packageUUID != null) {
result = lookIntoPackageClassLoader(packageUUID, className);
}
if (result != null) {
return result;
}
if (LOG.isLoggable(Level.FINE)) {
LOG.fine("Class " + className + " not found in packageClassLoaders...");
}
result = lookIntoCommonClassLoader(className);
if (result != null) {
return result;
}
if (LOG.isLoggable(Level.FINE)) {
LOG.fine("Class " + className + " not found in globalClassLoaders...");
}
//maybe it is present in the current classLoader ? It may be a class delivered in bonita jar ?
return load(ClassDataLoader.class.getClassLoader(), className);
}
protected static Object getInstance(final PackageDefinitionUUID packageUUID, final ClassInfo classInfo) {
final String className = classInfo.getClassName();
try {
final Class< ? > clazz = getClass(packageUUID, className);
return getClassInstance(clazz, classInfo);
} catch (final ClassNotFoundException e) {
throw new BonitaRuntimeException("The following class was not found : " + className);
}
}
private static Object getClassInstance(final Class< ? > clazz, final ClassInfo classInfo) {
final Object obj = ReflectUtil.newInstance(clazz);
if (obj == null) {
throw new BonitaRuntimeException("Problem while creating a new instance of class : " + clazz.getName()
+ ", returned object is null");
}
final Map parameters = classInfo.getParameters();
if (parameters != null) {
for (final Map.Entry entry : parameters.entrySet()) {
final String fieldName = entry.getKey();
final String fieldvalue = entry.getValue();
final Field field = ReflectUtil.getField(clazz, fieldName);
ReflectUtil.set(field, obj, fieldvalue);
}
}
return obj;
}
private static Class< ? > lookIntoPackageClassLoader(final PackageDefinitionUUID packageUUID, final String className) {
final Repository repository = EngineEnvTool.getRepository();
final PackageClassData packageClassData = repository.getPackageClassData(packageUUID);
if (packageClassData != null) {
if (LOG.isLoggable(Level.FINE)) {
LOG.fine("Class " + className + " is defined in package : " + packageUUID);
}
if (!packageClassLoaders.containsKey(packageUUID)) {
final PackageClassLoader bonitaClassLoader = new PackageClassLoader(packageClassData.getClasses());
packageClassLoaders.put(packageUUID, bonitaClassLoader);
}
final ClassLoader classLoader = packageClassLoaders.get(packageUUID);
try {
final Class< ? > result = load(classLoader, className);
if (result != null && result.getClassLoader().equals(classLoader)) {
return result;
}
} catch (final ClassNotFoundException e) {
return null;
}
}
return null;
}
private static Class< ? > lookIntoCommonClassLoader(final String className) {
try {
synchronized (CommonClassLoader.LOCK) {
return load(CommonClassLoader.getCurrent(), className);
}
} catch (final ClassNotFoundException e) {
return null;
}
}
private static Class< ? > load(final ClassLoader classLoader, final String className) throws ClassNotFoundException {
final Class< ? > clazz = classLoader.loadClass(className);
if (classLoader instanceof PackageClassLoader
&& !PackageClassLoader.class.isAssignableFrom(clazz.getClassLoader().getClass())) {
//throw new BonitaRuntimeException("Problem while creating a new instance of class : " + className + ", wrong classLoader");
return null;
}
return clazz;
}
public static ClassLoader getPackageClassLoader(final PackageDefinitionUUID packageUUID) {
return packageClassLoaders.get(packageUUID);
}
@SuppressWarnings("unchecked")
public static T getInstance(final Class clazz, final PackageDefinitionUUID packageUUID, final ClassInfo classInfo) {
Misc.checkArgsNotNull(clazz, classInfo);
final Object obj = getInstance(packageUUID, classInfo);
final String className = classInfo.getClassName();
if (obj == null) {
throw new BonitaRuntimeException("Unable to create an instance of " + className);
}
if (obj.getClass().isAssignableFrom(clazz)) {
throw new BonitaRuntimeException("The given class : " + classInfo + " is not an instance of "
+ clazz.getName() + ". Obj = " + obj);
}
return (T)obj;
}
public static void removePackageClassLoader(final PackageDefinitionUUID packageUUID) {
packageClassLoaders.remove(packageUUID);
}
public static void clear() {
packageClassLoaders.clear();
CommonClassLoader.reset();
}
public static CommonClassLoader getCommonClassLoader() {
return CommonClassLoader.getCurrent();
}
public static Map getPackageClassLoaders() {
return packageClassLoaders;
}
public static void removeCommonClass(final String className) {
CommonClassLoader.reset();
}
}
© 2015 - 2025 Weber Informatics LLC | Privacy Policy