MentaContainer

Compare Revisions

Ignore whitespace Rev 4 → Rev 3

/trunk/src/main/java/org/mentacontainer/impl/MentaContainer.java
7,165 → 7,171
import java.util.Set;
 
import org.mentacontainer.Container;
import org.mentacontainer.util.InjectionUtils;
 
public class MentaContainer implements Container {
private Map<String, Component> beans = new HashMap<String, Component>();
private Map<String, Object> singletons = new HashMap<String, Object>();
private Set<Dependency> dependencies = new HashSet<Dependency>();
 
private Map<String, Component> beans = new HashMap<String, Component>();
public Object get(String key) {
 
private Map<String, Object> singletons = new HashMap<String, Object>();
 
private Set<Dependency> dependencies = new HashSet<Dependency>();
 
public Object get(String key) {
 
if (!beans.containsKey(key)) throw new RuntimeException("Container does not have this bean set: " + key);
 
Component c = beans.get(key);
 
Object target = null;
 
try {
 
if (c.isSingleton()) {
 
if (singletons.containsKey(key)) {
 
target = singletons.get(key);
 
return target;
 
} else {
 
target = c.getInstance();
 
singletons.put(key, target);
}
 
} else {
 
target = c.getInstance();
 
}
 
if (target != null) {
 
for (Dependency d : dependencies) {
 
// has dependency ?
Method m = d.getMethod(target.getClass());
 
if (m != null) {
 
String sourceKey = d.getSource();
 
if (sourceKey.equals(key)) {
 
// cannot depend on itself...
// also avoid recursive StackOverflow...
 
continue;
 
if (!beans.containsKey(key)) throw new RuntimeException("Container does not have this bean set: " + key);
Component c = beans.get(key);
Object target = null;
try {
if (c.isSingleton()) {
if (singletons.containsKey(key)) {
target = singletons.get(key);
return target;
} else {
target = c.getInstance();
singletons.put(key, target);
}
} else {
target = c.getInstance();
}
if (target != null) {
for(Dependency d : dependencies) {
 
Object source = get(sourceKey);
// has dependency ?
Method m = d.getMethod(target.getClass());
if (m != null) {
boolean hasAlreadyReceived = d.hasAlreadyReceived(target);
// has already received the dependency?
if (!hasAlreadyReceived) {
String sourceKey = d.getSource();
// get dependency from action input
if (sourceKey.equals(key)) {
// cannot depend on itself...
// also avoid recusive StackOverflow...
continue;
}
Object source = get(sourceKey);
boolean isAssignable = source != null && d.getDependencyClass().isAssignableFrom(source.getClass());
// check if we can find the dependency and if it is assignable to the target dependency
if (isAssignable) {
try {
// inject
m.invoke(target, source);
// flag it has received
d.setAlreadyReceived(target);
} catch(Exception e) {
throw new RuntimeException("AutoWiringFilter cannot inject dependency: method = " + (m != null ? m.getName() : "NULL") + " / source = " + (source != null ? source : "NULL") + " / target = " + target, e);
}
}
}
}
}
}
 
boolean isAssignable = source != null && d.getDependencyClass().isAssignableFrom(source.getClass());
 
// check if we can find the dependency and if it is
// assignable to the target dependency
if (isAssignable) {
 
try {
 
// inject
m.invoke(target, source);
 
} catch (Exception e) {
 
throw new RuntimeException("Cannot inject dependency: method = " + (m != null ? m.getName() : "NULL") + " / source = "
+ (source != null ? source : "NULL") + " / target = " + target, e);
 
}
 
}
}
return target; // return target nicely with all the dependencies injected
} catch(Exception e) {
throw new RuntimeException(e);
}
}
}
 
return target; // return target nicely with all the dependencies
// injected
 
} catch (Exception e) {
 
throw new RuntimeException(e);
public Container ioc(String key, Class<? extends Object> klass, boolean singleton) {
if (beans.containsKey(key)) throw new RuntimeException("Container already set for the bean key: " + key);
Component c = new Component(klass, singleton);
beans.put(key, c);
return this;
}
}
 
public Container ioc(String key, Class<? extends Object> klass, boolean singleton) {
 
if (beans.containsKey(key)) throw new RuntimeException("Container already set for the bean key: " + key);
 
Component c = new Component(klass, singleton);
 
beans.put(key, c);
 
return this;
}
 
public Container ioc(String key, Class<? extends Object> klass) {
 
return ioc(key, klass, false);
}
 
public Container autowire(String property, Class<? extends Object> klass, String source) {
 
Dependency d = new Dependency(property, klass, source);
 
if (dependencies.contains(d)) throw new RuntimeException("Dependency is already set: " + property);
if (!klass.isInterface()) throw new RuntimeException("Dependency must be an interface!");
public Container ioc(String key, Class<? extends Object> klass) {
return ioc(key, klass, false);
}
 
dependencies.add(d);
public Container autowire(String property, Class<? extends Object> klass, String source) {
Dependency d = new Dependency(property, klass, source);
if (dependencies.contains(d)) throw new RuntimeException("Dependency is already set: " + property);
dependencies.add(d);
return this;
}
 
return this;
}
public Container autowire(String property, Class<? extends Object> klass) {
return autowire(property, klass, property);
}
 
public Container autowire(String property, Class<? extends Object> klass) {
return autowire(property, klass, property);
}
public Container init(String key, Object value) {
 
public Container init(String key, Object value) {
if (!beans.containsKey(key)) throw new RuntimeException("Container does not have this bean set: " + key);
Component c = beans.get(key);
c.addInitValue(value);
return this;
}
 
if (!beans.containsKey(key)) throw new RuntimeException("Container does not have this bean set: " + key);
public Container set(String key, String name, Object value) {
if (!beans.containsKey(key)) throw new RuntimeException("Container does not have this bean set: " + key);
Component c = beans.get(key);
c.addProperty(name, value);
return this;
}
 
Component c = beans.get(key);
 
c.addInitValue(value);
 
return this;
}
 
public Container set(String key, String name, Object value) {
 
if (!beans.containsKey(key)) throw new RuntimeException("Container does not have this bean set: " + key);
 
Component c = beans.get(key);
 
c.addProperty(name, value);
 
return this;
}
 
public Container populate(Object bean) throws Exception {
 
InjectionUtils.getObject(bean, this, false, null, true, false, true);
return this;
}
public boolean contains(String key) {
return beans.containsKey(key);
}
public Container populate(Object bean) {
// TODO Auto-generated method stub
return null;
}
}
/trunk/src/main/java/org/mentacontainer/impl/Dependency.java
17,6 → 17,8
private Map<String, Method> cache = new HashMap<String, Method>();
private Map<Object, Object> received = new WeakHashMap<Object, Object>();
public Dependency(String target, Class<? extends Object> klass, String source) {
this.klass = klass;
103,4 → 105,30
 
return null;
}
/*
* Check if this object has already received the dependency, because we don't want to
* inject every time. Injecting just once is the correct behavior.
*/
public boolean hasAlreadyReceived(Object target) {
 
synchronized(received) {
 
return received.containsKey(target);
 
}
}
/*
* Flag that this object has already received the dependency.
*/
public void setAlreadyReceived(Object target) {
 
synchronized(received) {
 
received.put(target, null);
 
}
}
 
}
/trunk/src/main/java/org/mentacontainer/Container.java
105,13 → 105,5
* @param bean The bean to be populated with other beans from the container.
* @return The container itself. (Fluent API)
*/
public Container populate(Object bean) throws Exception;
/**
* Check whether the container is configured to provide a bean with name 'key'.
*
* @param key The key representing the bean inside the container.
* @return true if the container contains this bean.
*/
public boolean contains(String key);
public Container populate(Object bean);
}
/trunk/src/main/java/org/mentacontainer/util/InjectionUtils.java
3,846 → 3,688
import java.lang.reflect.Field;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.text.DateFormat;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.Iterator;
import java.util.List;
import java.util.Locale;
import java.util.Map;
 
import org.mentacontainer.Container;
 
public class InjectionUtils {
 
/**
* The character used to separate the prefix from the value name when you
* are using the getObject method with a prefix. You can change the value of
* this prefix if you want to by changing this static variable.
*
* Ex: getObject(User.class, "user") will get all values that begin with
* "user.".
*/
public static char PREFIX_SEPARATOR = '.';
/**
* The character used to separate the prefix from the value name when you
* are using the getObject method with a prefix. You can change the value of
* this prefix if you want to by changing this static variable.
*
* Ex: getObject(User.class, "user") will get all values that begin with
* "user.".
*/
public static char PREFIX_SEPARATOR = '.';
 
private static Map<Class<? extends Object>, Map<String, Object>> settersMaps = new HashMap<Class<? extends Object>, Map<String, Object>>();
private static Map<Class<? extends Object>, Map<String, Object>> settersMaps = new HashMap<Class<? extends Object>, Map<String, Object>>();
 
private static Map<Class<? extends Object>, Map<String, Object>> fieldsMaps = new HashMap<Class<? extends Object>, Map<String, Object>>();
private static Map<Class<? extends Object>, Map<String, Object>> fieldsMaps = new HashMap<Class<? extends Object>, Map<String, Object>>();
 
public static void prepareForInjection(Class<? extends Object> klass, Map<String, Object> setters, Map<String, Object> fields) {
public static void prepareForInjection(Class<? extends Object> klass,
Map<String, Object> setters, Map<String, Object> fields) {
 
StringBuffer sb = new StringBuffer(32);
StringBuffer sb = new StringBuffer(32);
 
Method[] methods = klass.getMethods();
Method[] methods = klass.getMethods();
 
for (int i = 0; i < methods.length; i++) {
for (int i = 0; i < methods.length; i++) {
 
Method m = methods[i];
Method m = methods[i];
 
String name = m.getName();
String name = m.getName();
 
Class[] types = m.getParameterTypes();
Class[] types = m.getParameterTypes();
 
if (name.startsWith("set") && name.length() > 3 && types.length == 1) {
if (name.startsWith("set") && name.length() > 3
&& types.length == 1) {
 
String var = name.substring(3);
String var = name.substring(3);
 
if (var.length() > 1) {
if (var.length() > 1) {
 
sb.delete(0, sb.length());
sb.delete(0, sb.length());
 
sb.append(var.substring(0, 1).toLowerCase());
sb.append(var.substring(0, 1).toLowerCase());
 
sb.append(var.substring(1));
sb.append(var.substring(1));
 
var = sb.toString();
var = sb.toString();
 
} else {
} else {
 
var = var.toLowerCase();
}
var = var.toLowerCase();
}
 
m.setAccessible(true);
m.setAccessible(true);
 
if (setters.containsKey(var)) {
if (setters.containsKey(var)) {
 
Object obj = setters.get(var);
Object obj = setters.get(var);
 
if (obj instanceof List) {
if (obj instanceof List) {
 
List<Method> list = (List<Method>) obj;
List<Method> list = (List<Method>) obj;
 
list.add(m);
list.add(m);
 
} else if (obj instanceof Method) {
} else if (obj instanceof Method) {
 
List<Method> list = new ArrayList<Method>();
List<Method> list = new ArrayList<Method>();
 
list.add((Method) obj);
list.add((Method) obj);
 
list.add(m);
list.add(m);
 
setters.put(var, list);
setters.put(var, list);
 
}
}
 
} else {
} else {
 
setters.put(var, m);
setters.put(var, m);
 
}
}
}
}
}
 
if (fields == null) return;
if (fields == null)
return;
 
Field[] f = klass.getDeclaredFields();
Field[] f = klass.getDeclaredFields();
 
for (int i = 0; i < f.length; i++) {
for (int i = 0; i < f.length; i++) {
 
Field field = f[i];
Field field = f[i];
 
field.setAccessible(true);
field.setAccessible(true);
 
String name = field.getName();
String name = field.getName();
 
if (setters.containsKey(name)) {
if (setters.containsKey(name)) {
 
Object obj = setters.get(name);
Object obj = setters.get(name);
 
if (obj instanceof Method) {
if (obj instanceof Method) {
 
Method m = (Method) obj;
Method m = (Method) obj;
 
Class[] types = m.getParameterTypes();
Class[] types = m.getParameterTypes();
 
Class type = field.getType();
Class type = field.getType();
 
if (type.isAssignableFrom(types[0])) continue; // don't
// choose a
// field when
// we already
// have
// a
// method...
if (type.isAssignableFrom(types[0]))
continue; // don't choose a field when we already have
// a method...
 
} else if (obj instanceof List) {
} else if (obj instanceof List) {
 
List<Method> list = (List<Method>) obj;
List<Method> list = (List<Method>) obj;
 
Iterator<Method> iter = list.iterator();
Iterator<Method> iter = list.iterator();
 
boolean found = false;
boolean found = false;
 
while (iter.hasNext()) {
while (iter.hasNext()) {
 
Method m = iter.next();
Method m = iter.next();
 
Class[] types = m.getParameterTypes();
Class[] types = m.getParameterTypes();
 
Class type = field.getType();
Class type = field.getType();
 
if (type.isAssignableFrom(types[0])) {
if (type.isAssignableFrom(types[0])) {
 
found = true;
found = true;
 
break;
}
}
break;
}
}
 
if (found) continue; // don't choose a field when we already
// have
// a method...
if (found)
continue; // don't choose a field when we already have
// a method...
 
}
}
}
}
 
fields.put(name, field);
fields.put(name, field);
 
}
}
}
 
public static boolean checkPrimitives(Class target, Class<? extends Object> source) {
public static boolean checkPrimitives(Class target,
Class<? extends Object> source) {
 
if (target.equals(int.class) && source.equals(Integer.class)) return true;
if (target.equals(int.class) && source.equals(Integer.class))
return true;
 
if (target.equals(boolean.class) && source.equals(Boolean.class)) return true;
if (target.equals(boolean.class) && source.equals(Boolean.class))
return true;
 
if (target.equals(byte.class) && source.equals(Byte.class)) return true;
if (target.equals(byte.class) && source.equals(Byte.class))
return true;
 
if (target.equals(short.class) && source.equals(Short.class)) return true;
if (target.equals(short.class) && source.equals(Short.class))
return true;
 
if (target.equals(char.class) && source.equals(Character.class)) return true;
if (target.equals(char.class) && source.equals(Character.class))
return true;
 
if (target.equals(long.class) && source.equals(Long.class)) return true;
if (target.equals(long.class) && source.equals(Long.class))
return true;
 
if (target.equals(float.class) && source.equals(Float.class)) return true;
if (target.equals(float.class) && source.equals(Float.class))
return true;
 
if (target.equals(double.class) && source.equals(Double.class)) return true;
if (target.equals(double.class) && source.equals(Double.class))
return true;
 
return false;
return false;
 
}
}
 
public static Object tryToConvert(Object source, Class targetType) {
public static Object tryToConvert(Object source, Class targetType,
Locale loc) {
 
return tryToConvert(source, targetType, false);
}
 
public static Object tryToConvert(Object source, Class targetType, boolean tryNumber) {
 
String value = null;
 
if (source instanceof String) {
 
value = (String) source;
 
} else if (tryNumber && source instanceof Number) {
 
value = source.toString();
 
} else {
 
return null;
return tryToConvert(source, targetType, loc, false);
}
 
Object newValue = null;
public static Object tryToConvert(Object source, Class targetType,
Locale loc, boolean tryNumber) {
 
String className = targetType.getName();
String value = null;
 
if (className.equals("int") || className.equals("java.lang.Integer")) {
int x = -1;
try {
x = Integer.parseInt(value);
} catch (Exception e) {
return null;
}
newValue = new Integer(x);
} else if (className.equals("short") || className.equals("java.lang.Short")) {
short x = -1;
try {
x = Short.parseShort(value);
} catch (Exception e) {
return null;
}
newValue = new Short(x);
if (source instanceof String) {
 
} else if (className.equals("char") || className.equals("java.lang.Character")) {
value = (String) source;
 
if (value.length() != 1) {
return null;
}
} else if (tryNumber && source instanceof Number) {
 
newValue = new Character(value.charAt(0));
value = source.toString();
 
} else if (className.equals("long") || className.equals("java.lang.Long")) {
long x = -1;
try {
x = Long.parseLong(value);
} catch (Exception e) {
return null;
}
newValue = new Long(x);
} else if (className.equals("float") || className.equals("java.lang.Float")) {
float x = -1;
try {
x = Float.parseFloat(value);
} catch (Exception e) {
return null;
}
newValue = new Float(x);
} else if (className.equals("double") || className.equals("java.lang.Double")) {
double x = -1;
try {
x = Double.parseDouble(value);
} catch (Exception e) {
return null;
}
newValue = new Double(x);
} else if (className.equals("boolean") || className.equals("java.lang.Boolean")) {
try {
int x = Integer.parseInt(value);
if (x == 1) {
newValue = Boolean.TRUE;
} else if (x == 0) {
newValue = Boolean.FALSE;
} else {
return null;
 
return null;
}
} catch (Exception e) {
if (value.equalsIgnoreCase("true") || value.equals("on")) {
newValue = Boolean.TRUE;
} else if (value.equalsIgnoreCase("false")) {
newValue = Boolean.FALSE;
} else {
return null;
}
}
} else if (targetType.isEnum()) {
 
try {
Object newValue = null;
 
newValue = Enum.valueOf(targetType, value);
String className = targetType.getName();
 
} catch (Exception e) {
if (className.equals("int") || className.equals("java.lang.Integer")) {
int x = -1;
try {
x = Integer.parseInt(value);
} catch (Exception e) {
return null;
}
newValue = new Integer(x);
} else if (className.equals("short")
|| className.equals("java.lang.Short")) {
short x = -1;
try {
x = Short.parseShort(value);
} catch (Exception e) {
return null;
}
newValue = new Short(x);
 
return null;
}
} else if (className.equals("char")
|| className.equals("java.lang.Character")) {
 
}
if (value.length() != 1) {
return null;
}
 
return newValue;
newValue = new Character(value.charAt(0));
 
}
} else if (className.equals("long")
|| className.equals("java.lang.Long")) {
long x = -1;
try {
x = Long.parseLong(value);
} catch (Exception e) {
return null;
}
newValue = new Long(x);
} else if (className.equals("float")
|| className.equals("java.lang.Float")) {
float x = -1;
try {
x = Float.parseFloat(value);
} catch (Exception e) {
return null;
}
newValue = new Float(x);
} else if (className.equals("double")
|| className.equals("java.lang.Double")) {
double x = -1;
try {
x = Double.parseDouble(value);
} catch (Exception e) {
return null;
}
newValue = new Double(x);
} else if (className.equals("boolean")
|| className.equals("java.lang.Boolean")) {
try {
int x = Integer.parseInt(value);
if (x == 1) {
newValue = Boolean.TRUE;
} else if (x == 0) {
newValue = Boolean.FALSE;
} else {
return null;
}
} catch (Exception e) {
if (value.equalsIgnoreCase("true") || value.equals("on")) {
newValue = Boolean.TRUE;
} else if (value.equalsIgnoreCase("false")) {
newValue = Boolean.FALSE;
} else {
return null;
}
}
} else if (className.equals("java.util.Date") && loc != null) {
DateFormat df = DateFormat.getDateInstance(DateFormat.SHORT, loc); // change
// this.
df.setLenient(false);
try {
newValue = df.parse(value);
} catch (Exception e) {
return null;
}
} else if (targetType.isEnum()) {
 
public static Object shouldConvertToNull(Object value, Class<? extends Object> targetType) {
try {
 
if (targetType.equals(String.class)) {
newValue = Enum.valueOf(targetType, value);
 
return value;
} catch (Exception e) {
 
} else if (targetType.isPrimitive()) {
return null;
}
 
return value;
}
}
 
return null;
}
return newValue;
 
public static Class getPrimitiveFrom(Object w) {
if (w instanceof Boolean) {
return Boolean.TYPE;
} else if (w instanceof Byte) {
return Byte.TYPE;
} else if (w instanceof Short) {
return Short.TYPE;
} else if (w instanceof Character) {
return Character.TYPE;
} else if (w instanceof Integer) {
return Integer.TYPE;
} else if (w instanceof Long) {
return Long.TYPE;
} else if (w instanceof Float) {
return Float.TYPE;
} else if (w instanceof Double) {
return Double.TYPE;
}
return null;
}
 
public static Class getPrimitiveFrom(Class klass) {
public static Object shouldConvertToNull(Object value,
Class<? extends Object> targetType) {
 
String s = klass.getName();
if (targetType.equals(String.class)) {
 
if (s.equals("java.lang.Boolean")) {
return Boolean.TYPE;
} else if (s.equals("java.lang.Byte")) {
return Byte.TYPE;
} else if (s.equals("java.lang.Short")) {
return Short.TYPE;
} else if (s.equals("java.lang.Character")) {
return Character.TYPE;
} else if (s.equals("java.lang.Integer")) {
return Integer.TYPE;
} else if (s.equals("java.lang.Long")) {
return Long.TYPE;
} else if (s.equals("java.lang.Float")) {
return Float.TYPE;
} else if (s.equals("java.lang.Double")) {
return Double.TYPE;
}
return null;
}
return value;
 
public static Field getField(Object target, String name) {
return getField(target.getClass(), name);
}
} else if (targetType.isPrimitive()) {
 
public static Field getField(Class<? extends Object> target, String name) {
Field fields[] = target.getDeclaredFields();
for (int i = 0; i < fields.length; i++) {
if (name.equals(fields[i].getName())) {
return fields[i];
}
return value;
}
 
return null;
}
return null;
}
 
public static Method findMethodToGet(Class<? extends Object> target, String name) {
public static Class getPrimitiveFrom(Object w) {
if (w instanceof Boolean) {
return Boolean.TYPE;
} else if (w instanceof Byte) {
return Byte.TYPE;
} else if (w instanceof Short) {
return Short.TYPE;
} else if (w instanceof Character) {
return Character.TYPE;
} else if (w instanceof Integer) {
return Integer.TYPE;
} else if (w instanceof Long) {
return Long.TYPE;
} else if (w instanceof Float) {
return Float.TYPE;
} else if (w instanceof Double) {
return Double.TYPE;
}
return null;
}
 
StringBuffer sb = new StringBuffer(128);
public static Class getPrimitiveFrom(Class klass) {
 
sb.append("get").append(name.substring(0, 1).toUpperCase());
String s = klass.getName();
 
if (name.length() > 1) sb.append(name.substring(1));
 
try {
 
return target.getMethod(sb.toString(), (Class[]) null);
 
} catch (Exception e) {
 
if (s.equals("java.lang.Boolean")) {
return Boolean.TYPE;
} else if (s.equals("java.lang.Byte")) {
return Byte.TYPE;
} else if (s.equals("java.lang.Short")) {
return Short.TYPE;
} else if (s.equals("java.lang.Character")) {
return Character.TYPE;
} else if (s.equals("java.lang.Integer")) {
return Integer.TYPE;
} else if (s.equals("java.lang.Long")) {
return Long.TYPE;
} else if (s.equals("java.lang.Float")) {
return Float.TYPE;
} else if (s.equals("java.lang.Double")) {
return Double.TYPE;
}
return null;
}
 
sb.setLength(0);
 
sb.append("is").append(name.substring(0, 1).toUpperCase());
 
if (name.length() > 1) {
 
sb.append(name.substring(1));
public static Field getField(Object target, String name) {
return getField(target.getClass(), name);
}
 
try {
 
return target.getMethod(sb.toString(), (Class[]) null);
 
} catch (Exception e) {
 
public static Field getField(Class<? extends Object> target, String name) {
Field fields[] = target.getDeclaredFields();
for (int i = 0; i < fields.length; i++) {
if (name.equals(fields[i].getName())) {
return fields[i];
}
}
return null;
}
 
return null;
}
public static Method findMethodToGet(Class<? extends Object> target,
String name) {
 
public static Method findMethodToInject(Class<? extends Object> target, String name, Class source) {
StringBuffer sb = new StringBuffer(128);
 
StringBuffer sb = new StringBuffer(128);
sb.append("get").append(name.substring(0, 1).toUpperCase());
 
sb.append("set").append(name.substring(0, 1).toUpperCase());
if (name.length() > 1)
sb.append(name.substring(1));
 
if (name.length() > 1) sb.append(name.substring(1));
try {
 
String methodName = sb.toString();
return target.getMethod(sb.toString(), (Class[]) null);
 
Method m = null;
} catch (Exception e) {
 
try {
}
 
m = FindMethod.getMethod(target, methodName, new Class[] { source });
sb.setLength(0);
 
} catch (Exception e) {
}
sb.append("is").append(name.substring(0, 1).toUpperCase());
 
if (m == null) {
if (name.length() > 1) {
 
Class primitive = getPrimitiveFrom(source);
sb.append(name.substring(1));
}
 
if (primitive != null) {
 
try {
 
m = target.getMethod(methodName, new Class[] { primitive });
return target.getMethod(sb.toString(), (Class[]) null);
 
} catch (Exception e) {
 
}
 
}
return null;
}
 
if (m != null) {
m.setAccessible(true);
}
public static Method findMethodToInject(Class<? extends Object> target,
String name, Class source) {
 
return m;
StringBuffer sb = new StringBuffer(128);
 
}
sb.append("set").append(name.substring(0, 1).toUpperCase());
 
public static Field findFieldToInject(Class<? extends Object> target, String name, Class<? extends Object> source) {
if (name.length() > 1)
sb.append(name.substring(1));
 
Field f = getField(target, name);
String methodName = sb.toString();
 
if (f != null) {
Method m = null;
 
Class<?> type = f.getType();
try {
 
if (type.isAssignableFrom(source) || checkPrimitives(type, source)) {
m = FindMethod
.getMethod(target, methodName, new Class[] { source });
 
f.setAccessible(true);
} catch (Exception e) {
}
 
return f;
}
if (m == null) {
 
}
Class primitive = getPrimitiveFrom(source);
 
return null;
}
if (primitive != null) {
 
private static final boolean isBlank(Object value) {
try {
 
if (value != null && value instanceof String) {
m = target.getMethod(methodName, new Class[] { primitive });
 
String s = ((String) value).trim();
} catch (Exception e) {
}
 
if (s.length() == 0) return true;
}
}
}
 
return false;
}
if (m != null) {
m.setAccessible(true);
}
 
public static boolean inject(Method m, Object target, Object value, boolean tryToConvert, boolean tryingToConvertBoolean) throws Exception {
return m;
 
Class<?> type = m.getParameterTypes()[0];
 
if (tryingToConvertBoolean) {
 
if (value == null && (type.equals(Boolean.class) || type.equals(boolean.class))) {
 
value = Boolean.FALSE;
 
} else {
 
// if trying to convert boolean, convert or don't do anything...
 
return false;
 
}
}
 
if (value == null
|| (type.isAssignableFrom(value.getClass()) || checkPrimitives(type, value.getClass()) || (tryToConvert && ((isBlank(value) && (value = shouldConvertToNull(value,
type)) == null) || (value = tryToConvert(value, type)) != null)))) {
public static Field findFieldToInject(Class<? extends Object> target,
String name, Class<? extends Object> source) {
 
try {
Field f = getField(target, name);
 
m.invoke(target, new Object[] { value });
if (f != null) {
 
return true;
Class<?> type = f.getType();
 
} catch (Exception e) {
if (type.isAssignableFrom(source) || checkPrimitives(type, source)) {
 
System.err.println("Error injecting by method: " + value + " in " + target + " thru " + m);
f.setAccessible(true);
 
e.printStackTrace();
return f;
}
 
throw e;
}
 
}
return null;
}
 
return false;
private static final boolean isBlank(Object value) {
 
}
if (value != null && value instanceof String) {
 
public static boolean hasDefaultConstructor(Class<? extends Object> klass) {
String s = ((String) value).trim();
 
try {
if (s.length() == 0)
return true;
}
 
return klass.getConstructor((Class[]) null) != null;
 
} catch (Exception e) {
 
return false;
return false;
}
}
 
/*
* This method takes setUsername and returns username.
*
* If we have a prefix, then it returns prefix.username.
*/
private static String adjustName(String name, String prefix) {
public static boolean inject(Method m, Object target, Object value,
Locale loc, boolean tryToConvert, boolean tryingToConvertBoolean)
throws Exception {
 
StringBuilder sb;
Class<?> type = m.getParameterTypes()[0];
 
if (name.length() >= 4 && (name.startsWith("get") || name.startsWith("set"))) {
if (tryingToConvertBoolean) {
 
sb = new StringBuilder(name.length() - 3);
sb.append(name.substring(3, 4).toLowerCase());
if (name.length() > 4) sb.append(name.substring(4, name.length()));
if (value == null && (type.equals(Boolean.class) || type.equals(boolean.class))) {
 
} else if (name.length() >= 3 && name.startsWith("is")) {
value = Boolean.FALSE;
 
sb = new StringBuilder(name.length() - 2);
sb.append(name.substring(2, 3).toLowerCase());
if (name.length() > 3) sb.append(name.substring(3, name.length()));
} else {
 
} else {
// if trying to convert boolean, convert or don't do anything...
 
throw new IllegalArgumentException("Cannot adjust method: " + name);
}
return false;
 
if (prefix != null) {
}
}
 
StringBuffer sb2 = new StringBuffer(128);
if (value == null
|| (type.isAssignableFrom(value.getClass())
|| checkPrimitives(type, value.getClass()) || (tryToConvert && ((isBlank(value) && (value = shouldConvertToNull(
value, type)) == null) || (value = tryToConvert(value,
type, loc)) != null)))) {
 
return sb2.append(prefix).append(PREFIX_SEPARATOR).append(sb.toString()).toString();
try {
 
}
m.invoke(target, new Object[] { value });
 
return sb.toString();
}
return true;
 
/**
* Extract the value of a property of a bean!
*
* @param bean
* the target bean
* @param nameProperty
* the property name
* @return they value as String. The method toString is always called to
* every property!
* @throws Exception
*/
public static String getProperty(Object bean, String nameProperty) throws Exception {
} catch (Exception e) {
 
if (nameProperty == null || nameProperty.equals("")) return null;
System.err.println("Error injecting by method: " + value
+ " in " + target + " thru " + m);
 
String methodName = getter(nameProperty);
e.printStackTrace();
 
Class<? extends Object> clazz = bean.getClass();
Method[] methods = clazz.getMethods();
for (Method method : methods) {
if (method.getName().equals(methodName) && method.getParameterTypes().length == 0) {
Object value = method.invoke(bean, (Object[]) null);
if (value == null) return null;
return value.toString();
}
}
throw e;
 
Field[] fields = clazz.getDeclaredFields();
for (Field field : fields) {
field.setAccessible(true);
if (field.getName().equals(nameProperty)) {
Object value = field.get(bean);
if (value == null) return null;
return value.toString();
}
}
 
return null;
}
 
private static String getter(String name) {
StringBuilder sb = new StringBuilder(name.length() + 3);
 
sb.append("get").append(name.substring(0, 1).toUpperCase());
 
if (name.length() > 1) sb.append(name.substring(1));
return sb.toString();
}
 
public static void beanToMap(Object bean, Map<String, String> map) throws IllegalArgumentException, IllegalAccessException, InvocationTargetException {
if (bean != null) {
 
for (Method method : bean.getClass().getMethods()) {
String name = method.getName();
 
if (name.length() > 3 && name.startsWith("get") && !name.equals("getClass") && method.getParameterTypes().length == 0) {
 
method.setAccessible(true);
Object value = method.invoke(bean, new Object[0]);
map.put(name, value.toString());
}
}
}
}
}
 
public static void getObject(Object target, Container container, boolean tryField, String prefix, boolean tryToConvert, boolean convertBoolean,
boolean allowRecursion) throws Exception {
return false;
 
Class<? extends Object> targetClass = target.getClass();
 
Map<String, Object> setters, fields;
 
// see if we have these in cache...
 
synchronized (settersMaps) {
 
setters = settersMaps.get(targetClass);
 
fields = fieldsMaps.get(targetClass);
 
}
 
// if not in cache, prepare maps for injection...
public static boolean hasDefaultConstructor(Class<? extends Object> klass) {
 
if (setters == null) {
try {
 
setters = new HashMap<String, Object>();
return klass.getConstructor((Class[]) null) != null;
 
fields = null;
} catch (Exception e) {
 
if (tryField) {
 
fields = new HashMap<String, Object>();
 
}
 
prepareForInjection(targetClass, setters, fields);
 
synchronized (settersMaps) {
 
settersMaps.put(targetClass, setters);
 
fieldsMaps.put(targetClass, fields);
 
}
return false;
}
}
 
Iterator<String> iter = setters.keySet().iterator();
/*
* This method takes setUsername and returns username.
*
* If we have a prefix, then it returns prefix.username.
*/
private static String adjustName(String name, String prefix) {
 
while (iter.hasNext()) {
StringBuilder sb;
 
String var = iter.next();
if (name.length() >= 4
&& (name.startsWith("get") || name.startsWith("set"))) {
 
boolean hasValue = container.contains(var);
sb = new StringBuilder(name.length() - 3);
sb.append(name.substring(3, 4).toLowerCase());
if (name.length() > 4)
sb.append(name.substring(4, name.length()));
 
Object value = container.contains(var);
} else if (name.length() >= 3 && name.startsWith("is")) {
 
boolean tryingToConvertBoolean = false;
sb = new StringBuilder(name.length() - 2);
sb.append(name.substring(2, 3).toLowerCase());
if (name.length() > 3)
sb.append(name.substring(3, name.length()));
 
if (value == null && !hasValue) {
 
if (!convertBoolean) {
 
continue;
 
} else {
 
tryingToConvertBoolean = true;
throw new IllegalArgumentException("Cannot adjust method: " + name);
}
 
}
if (prefix != null) {
 
// if (value == null) continue;
StringBuffer sb2 = new StringBuffer(128);
 
Object obj = setters.get(var);
return sb2.append(prefix).append(PREFIX_SEPARATOR).append(
sb.toString()).toString();
 
// we may have a list of overloaded methods...
 
List list = null;
 
Method m = null;
 
if (obj instanceof List) {
 
list = (List) obj;
 
} else {
 
m = (Method) setters.get(var);
 
}
 
if (m != null) {
 
if (!inject(m, target, value, tryToConvert, tryingToConvertBoolean) && allowRecursion) {
 
// i did not inject... how about a VO object for this
// setter?
 
Class<?> type = m.getParameterTypes()[0];
 
if (!type.getName().startsWith("java.") && !type.isPrimitive() && hasDefaultConstructor(type)) {
 
Object param = type.newInstance();
 
InjectionUtils.getObject(param, container, true, prefix, true, true, false); // no
// recursion...
 
inject(m, target, param, false, false);
}
}
 
} else {
return sb.toString();
}
 
Iterator it = list.iterator();
/**
* Extract the value of a property of a bean!
*
* @param bean
* the target bean
* @param nameProperty
* the property name
* @return they value as String. The method toString is always called to
* every property!
* @throws Exception
*/
public static String getProperty(Object bean, String nameProperty)
throws Exception {
 
boolean injected = false;
if (nameProperty == null || nameProperty.equals(""))
return null;
String methodName = getter(nameProperty);
 
while (it.hasNext()) {
 
m = (Method) it.next();
 
if (inject(m, target, value, tryToConvert, tryingToConvertBoolean)) {
 
injected = true;
 
break;
}
Class<? extends Object> clazz = bean.getClass();
Method[] methods = clazz.getMethods();
for (Method method : methods) {
if (method.getName().equals(methodName)
&& method.getParameterTypes().length == 0) {
Object value = method.invoke(bean, (Object[]) null);
if (value == null)
return null;
return value.toString();
}
}
 
if (!injected && allowRecursion) {
 
// i could not inject anything... how about a VO object for
// this setter...
 
it = list.iterator();
 
while (it.hasNext()) {
 
m = (Method) it.next();
 
Class<?> type = m.getParameterTypes()[0];
 
if (!type.getName().startsWith("java.") && !type.isPrimitive() && hasDefaultConstructor(type)) {
 
Object param = type.newInstance();
 
InjectionUtils.getObject(param, container, true, prefix, true, true, false); // no
// recursion...
 
if (inject(m, target, param, false, false)) {
 
break; // done...
}
Field[] fields = clazz.getDeclaredFields();
for (Field field : fields) {
field.setAccessible(true);
if (field.getName().equals(nameProperty)) {
Object value = field.get(bean);
if (value == null)
return null;
return value.toString();
}
}
}
}
 
return null;
}
 
if (fields != null) {
private static String getter(String name) {
StringBuilder sb = new StringBuilder(name.length() + 3);
 
iter = fields.keySet().iterator();
sb.append("get").append(name.substring(0, 1).toUpperCase());
 
while (iter.hasNext()) {
if (name.length() > 1)
sb.append(name.substring(1));
return sb.toString();
}
 
String var = iter.next();
public static void beanToMap(Object bean, Map<String, String> map)
throws IllegalArgumentException, IllegalAccessException,
InvocationTargetException {
if (bean != null) {
 
boolean hasValue = container.contains(var);
for (Method method : bean.getClass().getMethods()) {
String name = method.getName();
 
Object value = container.get(var);
if (name.length() > 3 && name.startsWith("get")
&& !name.equals("getClass")
&& method.getParameterTypes().length == 0) {
 
Field f = (Field) fields.get(var);
 
Class<?> type = f.getType();
 
// If there is no value in the action input, assume false for
// booleans...
// (checkboxes and radio buttons are not send when not
// marked...)
 
if (convertBoolean && value == null && !hasValue) {
 
if (type.equals(Boolean.class) || type.equals(boolean.class)) {
 
value = Boolean.FALSE;
}
 
method.setAccessible(true);
Object value = method.invoke(bean, new Object[0]);
map.put(name, value.toString());
}
}
}
 
if (value == null && !hasValue) continue;
 
// if (value == null) continue;
 
if (value == null
|| (type.isAssignableFrom(value.getClass()) || checkPrimitives(type, value.getClass()) || (tryToConvert && ((isBlank(value) && (value = shouldConvertToNull(
value, type)) == null) || (value = tryToConvert(value, type)) != null)))) {
 
try {
 
f.set(target, value);
 
} catch (Exception e) {
 
System.err.println("Error injecting by field: " + value + " in " + target);
 
e.printStackTrace();
 
throw e;
 
}
}
}
}
}
 
}
/trunk/pom.xml
18,7 → 18,7
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>
<version>4.8.1</version>
<version>3.8.1</version>
<scope>test</scope>
</dependency>
</dependencies>