[jboss-svn-commits] JBL Code SVN: r28937 - in labs/jbosstm/trunk/common: tests/com/arjuna/common/tests/simple and 1 other directory.
jboss-svn-commits at lists.jboss.org
jboss-svn-commits at lists.jboss.org
Fri Aug 14 10:48:51 EDT 2009
Author: jhalliday
Date: 2009-08-14 10:48:51 -0400 (Fri, 14 Aug 2009)
New Revision: 28937
Modified:
labs/jbosstm/trunk/common/classes/com/arjuna/common/internal/util/propertyservice/BeanPopulator.java
labs/jbosstm/trunk/common/tests/com/arjuna/common/tests/simple/DummyPropertyManager.java
Log:
Improvements to the propertyfile->bean copy handling. JBTM-596
Modified: labs/jbosstm/trunk/common/classes/com/arjuna/common/internal/util/propertyservice/BeanPopulator.java
===================================================================
--- labs/jbosstm/trunk/common/classes/com/arjuna/common/internal/util/propertyservice/BeanPopulator.java 2009-08-14 14:46:26 UTC (rev 28936)
+++ labs/jbosstm/trunk/common/classes/com/arjuna/common/internal/util/propertyservice/BeanPopulator.java 2009-08-14 14:48:51 UTC (rev 28937)
@@ -22,6 +22,10 @@
import java.lang.reflect.Field;
import java.lang.reflect.Method;
+import java.util.List;
+import java.util.LinkedList;
+import java.util.Enumeration;
+import java.util.Collections;
import com.arjuna.common.util.propertyservice.PropertyManager;
@@ -36,19 +40,28 @@
/**
* Examine the properties of the provided bean and update them to match the values of the corresponding
* properties in the PropertyManager.
- * This will normally be used to configure a freshly created default bean to match the configuration
- * read from a properties file.
+ * This will normally be used at startup to configure a freshly created default bean to match
+ * the configuration read from a properties file.
*
* The algorithm is as follows: for each field in the bean, which must have a getter and setter method
* matching according to the JavaBeans naming conventions, determine the corresponding property key.
*
- * Several key names are tried, with the first match being used: The FQN of the bean followed by the field name,
- * the short name of the bean followed by the field name, and finally the bean classes' PropertyPrefix annotation
- * value followed by the name of the field, the last being except in cases where the field has a FullPropertyName
- * annotation, in which case its value is used instead.
+ * Several key names are tried, with the first match being used:
+ * For scalar properties: The FQN of the bean followed by the field name,
+ * the short name of the bean followed by the field name, and finally the bean classes' PropertyPrefix annotation
+ * value followed by the name of the field, the last being except in cases where the field has a FullPropertyName
+ * annotation, in which case its value is used instead.
+ * For vector (in the math sense - the type is actually normally List) properties, a single property key matched
+ * according to the prior rules will be treated as having a compund vlaue which will be tokenized into list
+ * elements based on whitespace and inserted into the list in token order.
+ * If no such key is found, the value of the field's ConcatenationPrefix annotation
+ * is treated as a name prefix and the list elements are assembled from the values of any properties having
+ * key values starting with the prefix. These are inserted into the list in order of the key's name sort position.
+ *
* This allows for the convention that all properties in a given bean will share
* the same prefix e.g. com.arjuna.ats.arjuna.foo. whilst still allowing for changing of the property
* name in cases where this makes for more readable code.
+ *
* Obtain the value of the property from the PropertyManager and if it's not null, type convert it to match
* the bean's property field type. Obtain the value of the property from the bean and if it's different
* from the value read from the propertyManager, use the setter to update the bean.
@@ -63,10 +76,6 @@
throw new Exception("no PropertyPrefix found on "+bean.getClass().getName());
}
- PropertyPrefix prefixAnnotation = bean.getClass().getAnnotation(PropertyPrefix.class);
-
- String prefix = prefixAnnotation.prefix();
-
for(Field field : bean.getClass().getDeclaredFields()) {
Class type = field.getType();
@@ -87,76 +96,149 @@
getter = bean.getClass().getMethod(getterMethodName, new Class[] {});
}
- //////////////////
+ if(field.isAnnotationPresent(ConcatenationPrefix.class)) {
+ handleGroupProperty(bean, propertyManager, field, setter, getter);
+ } else {
+ handleSimpleProperty(bean, propertyManager, field, setter, getter);
+ }
+ }
+ }
- String propertyFileKey = null;
- String valueFromPropertyManager = null;
+ private static void handleGroupProperty(Object bean, PropertyManager propertyManager, Field field, Method setter, Method getter)
+ throws Exception
+ {
+ List<String> values = new LinkedList<String>();
- if(valueFromPropertyManager == null) {
- propertyFileKey = bean.getClass().getCanonicalName()+"."+field.getName();
- valueFromPropertyManager = propertyManager.getProperty(propertyFileKey);
- }
+ String valueFromPropertyManager = getValueFromPropertyManager(bean, propertyManager, field, bean.getClass().getSimpleName());
- if(valueFromPropertyManager == null) {
- propertyFileKey = bean.getClass().getSimpleName()+"."+field.getName();
- valueFromPropertyManager = propertyManager.getProperty(propertyFileKey);
+ if(valueFromPropertyManager != null)
+ {
+ // it's a single value which needs parsing
+
+ String[] tokens = valueFromPropertyManager.split("\\s+");
+
+ // the order we want them is is the order they appear in the string, so we can just add in sequence:
+ for(String token : tokens) {
+ values.add(token);
}
+ }
+ else
+ {
+ // it's set of values that need gathering together
+ // the order we want them in is the lex sort order of the keys, so we need to buffer and sort them:
- if (valueFromPropertyManager == null) {
- propertyFileKey = prefix+field.getName();
+ List<String> listOfMatchingPropertyNames = new LinkedList<String>();
+ Enumeration propertyNamesEnumeration = propertyManager.propertyNames();
- if(field.isAnnotationPresent(FullPropertyName.class)) {
- FullPropertyName fullPropertyName = field.getAnnotation(FullPropertyName.class);
- propertyFileKey = fullPropertyName.name();
+ if (propertyNamesEnumeration != null)
+ {
+ String prefix = field.getAnnotation(ConcatenationPrefix.class).prefix();
+
+ while (propertyNamesEnumeration.hasMoreElements())
+ {
+ String name = (String) propertyNamesEnumeration.nextElement();
+
+ if (name.startsWith(prefix))
+ {
+ listOfMatchingPropertyNames.add(name);
+ }
}
-
- valueFromPropertyManager = propertyManager.getProperty(propertyFileKey);
}
+ Collections.sort(listOfMatchingPropertyNames);
- if(valueFromPropertyManager != null) {
+ for(String name : listOfMatchingPropertyNames) {
+ String value = propertyManager.getProperty(name);
+ values.add(value);
+ }
+ }
+
+ Object valueFromBean = getter.invoke(bean, new Object[] {});
- Object valueFromBean = getter.invoke(bean, new Object[] {});
+ if(!valueFromBean.equals(values)) {
+ setter.invoke(bean, new Object[] {values});
+ }
+ }
- if(field.getType().equals(Boolean.TYPE)) {
+ private static void handleSimpleProperty(Object bean, PropertyManager propertyManager, Field field, Method setter, Method getter)
+ throws Exception
+ {
+ PropertyPrefix prefixAnnotation = bean.getClass().getAnnotation(PropertyPrefix.class);
+ String prefix = prefixAnnotation.prefix();
- if(!((Boolean)valueFromBean).booleanValue() && isPositive(valueFromPropertyManager)) {
- setter.invoke(bean, new Object[]{ Boolean.TRUE });
- }
+ String valueFromPropertyManager = getValueFromPropertyManager(bean, propertyManager, field, prefix);
- if(((Boolean)valueFromBean).booleanValue() && isNegative(valueFromPropertyManager)) {
- setter.invoke(bean, new Object[] { Boolean.FALSE});
- }
+ if(valueFromPropertyManager != null) {
- } else if(field.getType().equals(String.class)) {
+ Object valueFromBean = getter.invoke(bean, new Object[] {});
- if(!valueFromPropertyManager.equals(valueFromBean)) {
- setter.invoke(bean, new Object[] {valueFromPropertyManager});
- }
+ if(field.getType().equals(Boolean.TYPE)) {
- } else if(field.getType().equals(Long.TYPE)) {
+ if(!((Boolean)valueFromBean).booleanValue() && isPositive(valueFromPropertyManager)) {
+ setter.invoke(bean, new Object[]{ Boolean.TRUE });
+ }
- Long longValue = Long.valueOf(valueFromPropertyManager);
- if(!longValue.equals(valueFromBean)) {
- setter.invoke(bean, new Object[] {longValue});
- }
+ if(((Boolean)valueFromBean).booleanValue() && isNegative(valueFromPropertyManager)) {
+ setter.invoke(bean, new Object[] { Boolean.FALSE});
+ }
- } else if(field.getType().equals(Integer.TYPE)) {
+ } else if(field.getType().equals(String.class)) {
- Integer intValue = Integer.valueOf(valueFromPropertyManager);
- if(!intValue.equals(valueFromBean)) {
- setter.invoke(bean, new Object[] {intValue});
- }
+ if(!valueFromPropertyManager.equals(valueFromBean)) {
+ setter.invoke(bean, new Object[] {valueFromPropertyManager});
+ }
- } else {
+ } else if(field.getType().equals(Long.TYPE)) {
- throw new Exception("unknown field type "+field.getType());
+ Long longValue = Long.valueOf(valueFromPropertyManager);
+ if(!longValue.equals(valueFromBean)) {
+ setter.invoke(bean, new Object[] {longValue});
+ }
+ } else if(field.getType().equals(Integer.TYPE)) {
+
+ Integer intValue = Integer.valueOf(valueFromPropertyManager);
+ if(!intValue.equals(valueFromBean)) {
+ setter.invoke(bean, new Object[] {intValue});
}
+
+ } else {
+
+ throw new Exception("unknown field type "+field.getType());
+
}
}
}
+ private static String getValueFromPropertyManager(Object bean, PropertyManager propertyManager, Field field, String prefix)
+ {
+ String propertyFileKey;
+ String valueFromPropertyManager = null;
+
+ if(valueFromPropertyManager == null) {
+ propertyFileKey = bean.getClass().getCanonicalName()+"."+field.getName();
+ valueFromPropertyManager = propertyManager.getProperty(propertyFileKey);
+ }
+
+ if(valueFromPropertyManager == null) {
+ propertyFileKey = bean.getClass().getSimpleName()+"."+field.getName();
+ valueFromPropertyManager = propertyManager.getProperty(propertyFileKey);
+ }
+
+ if (valueFromPropertyManager == null) {
+ propertyFileKey = prefix+field.getName();
+
+ if(field.isAnnotationPresent(FullPropertyName.class)) {
+ FullPropertyName fullPropertyName = field.getAnnotation(FullPropertyName.class);
+ propertyFileKey = fullPropertyName.name();
+ }
+
+ valueFromPropertyManager = propertyManager.getProperty(propertyFileKey);
+ }
+
+ return valueFromPropertyManager;
+ }
+
private static String capitalizeFirstLetter(String string) {
return (string.length()>0) ? (Character.toUpperCase(string.charAt(0))+string.substring(1)) : string;
}
Modified: labs/jbosstm/trunk/common/tests/com/arjuna/common/tests/simple/DummyPropertyManager.java
===================================================================
--- labs/jbosstm/trunk/common/tests/com/arjuna/common/tests/simple/DummyPropertyManager.java 2009-08-14 14:46:26 UTC (rev 28936)
+++ labs/jbosstm/trunk/common/tests/com/arjuna/common/tests/simple/DummyPropertyManager.java 2009-08-14 14:48:51 UTC (rev 28937)
@@ -25,11 +25,9 @@
import com.arjuna.common.util.exceptions.LoadPropertiesException;
import com.arjuna.common.util.exceptions.SavePropertiesException;
import com.arjuna.common.util.exceptions.ManagementPluginException;
+import com.arjuna.common.internal.util.propertyservice.ConcatenationPrefix;
-import java.util.Set;
-import java.util.HashSet;
-import java.util.Properties;
-import java.util.Enumeration;
+import java.util.*;
import java.lang.reflect.Field;
import java.io.IOException;
@@ -57,8 +55,20 @@
return keys;
}
+ public void addConcatenationKeys(Class environmentBean) {
+
+ for(Field field : environmentBean.getDeclaredFields()) {
+ if(field.isAnnotationPresent(ConcatenationPrefix.class)) {
+ String prefix = field.getAnnotation(ConcatenationPrefix.class).prefix();
+ concatenationKeys.add(prefix);
+ System.out.println("addConcat : "+prefix);
+ }
+ }
+ }
+
public Set<String> usedKeys = new HashSet<String>();
Properties properties = null;
+ public Set<String> concatenationKeys = new HashSet<String>();
public DummyPropertyManager(Properties properties) {
this.properties = properties;
@@ -66,6 +76,13 @@
public String getProperty(String key)
{
+ for(String prefix : concatenationKeys) {
+ if(key.startsWith(prefix) && !usedKeys.contains(prefix)) {
+ usedKeys.add(prefix);
+ break;
+ }
+ }
+
usedKeys.add(key);
if(properties != null) {
@@ -102,7 +119,12 @@
public Enumeration propertyNames()
{
- throw new RuntimeException("this is not expected to be called during the test");
+ Vector<String> names = new Vector<String>();
+ for(String prefix : concatenationKeys) {
+ names.add(prefix+"_one");
+ names.add(prefix+"_two");
+ }
+ return names.elements();
}
public void load(String s, String s1) throws IOException, ClassNotFoundException, LoadPropertiesException
More information about the jboss-svn-commits
mailing list