You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@ofbiz.apache.org by ad...@apache.org on 2012/07/01 22:54:24 UTC
svn commit: r1356024 -
/ofbiz/trunk/framework/entity/src/org/ofbiz/entity/finder/EntityFinderUtil.java
Author: adrianc
Date: Sun Jul 1 20:54:23 2012
New Revision: 1356024
URL: http://svn.apache.org/viewvc?rev=1356024&view=rev
Log:
Some optimizations in EntityFinderUtil.java:
1. Made the Condition implementations immutable and thread-safe.
2. Moved operator lookup from run-time to parse-time.
3. Removed unnecessary calls to UtilValidate.
4. Replaced LinkedList with ArrayList.
5. Optimized code in the ConditionExpr.createCondition method.
Modified:
ofbiz/trunk/framework/entity/src/org/ofbiz/entity/finder/EntityFinderUtil.java
Modified: ofbiz/trunk/framework/entity/src/org/ofbiz/entity/finder/EntityFinderUtil.java
URL: http://svn.apache.org/viewvc/ofbiz/trunk/framework/entity/src/org/ofbiz/entity/finder/EntityFinderUtil.java?rev=1356024&r1=1356023&r2=1356024&view=diff
==============================================================================
--- ofbiz/trunk/framework/entity/src/org/ofbiz/entity/finder/EntityFinderUtil.java (original)
+++ ofbiz/trunk/framework/entity/src/org/ofbiz/entity/finder/EntityFinderUtil.java Sun Jul 1 20:54:23 2012
@@ -21,19 +21,18 @@ package org.ofbiz.entity.finder;
import static org.ofbiz.base.util.UtilGenerics.cast;
import java.io.Serializable;
+import java.util.ArrayList;
import java.util.Collection;
+import java.util.Collections;
+import java.util.HashMap;
import java.util.HashSet;
-import java.util.LinkedList;
import java.util.List;
import java.util.Map;
import java.util.Set;
-import javolution.util.FastMap;
-
import org.ofbiz.base.util.Debug;
import org.ofbiz.base.util.ObjectType;
import org.ofbiz.base.util.StringUtil;
-import org.ofbiz.base.util.UtilFormatOut;
import org.ofbiz.base.util.UtilGenerics;
import org.ofbiz.base.util.UtilValidate;
import org.ofbiz.base.util.UtilXml;
@@ -63,24 +62,24 @@ public class EntityFinderUtil {
Map<FlexibleMapAccessor<Object>, Object> fieldMap = null;
List<? extends Element> fieldMapElementList = UtilXml.childElementList(element, "field-map");
if (fieldMapElementList.size() > 0) {
- fieldMap = FastMap.newInstance();
+ fieldMap = new HashMap<FlexibleMapAccessor<Object>, Object>(fieldMapElementList.size());
for (Element fieldMapElement: fieldMapElementList) {
// set the env-name for each field-name, noting that if no field-name is specified it defaults to the env-name
String fieldName = fieldMapElement.getAttribute("field-name");
String envName = fieldMapElement.getAttribute("from-field");
- if (UtilValidate.isEmpty(envName)) {
+ if (envName.isEmpty()) {
envName = fieldMapElement.getAttribute("env-name");
}
String value = fieldMapElement.getAttribute("value");
- if (UtilValidate.isEmpty(fieldName)) {
+ if (fieldName.isEmpty()) {
// no fieldName, use envName for both
fieldMap.put(FlexibleMapAccessor.getInstance(envName), FlexibleMapAccessor.getInstance(envName));
} else {
- if (UtilValidate.isNotEmpty(value)) {
+ if (!value.isEmpty()) {
fieldMap.put(FlexibleMapAccessor.getInstance(fieldName), FlexibleStringExpander.getInstance(value));
} else {
// at this point we have a fieldName and no value, do we have a envName?
- if (UtilValidate.isNotEmpty(envName)) {
+ if (!envName.isEmpty()) {
fieldMap.put(FlexibleMapAccessor.getInstance(fieldName), FlexibleMapAccessor.getInstance(envName));
} else {
// no envName, use fieldName for both
@@ -116,7 +115,7 @@ public class EntityFinderUtil {
List<FlexibleStringExpander> selectFieldExpanderList = null;
List<? extends Element> selectFieldElementList = UtilXml.childElementList(element, "select-field");
if (selectFieldElementList.size() > 0) {
- selectFieldExpanderList = new LinkedList<FlexibleStringExpander>();
+ selectFieldExpanderList = new ArrayList<FlexibleStringExpander>(selectFieldElementList.size());
for (Element selectFieldElement: selectFieldElementList) {
selectFieldExpanderList.add(FlexibleStringExpander.getInstance(selectFieldElement.getAttribute("field-name")));
}
@@ -138,7 +137,7 @@ public class EntityFinderUtil {
public static List<String> makeOrderByFieldList(List<FlexibleStringExpander> orderByExpanderList, Map<String, Object> context) {
List<String> orderByFields = null;
if (UtilValidate.isNotEmpty(orderByExpanderList)) {
- orderByFields = new LinkedList<String>();
+ orderByFields = new ArrayList<String>(orderByExpanderList.size());
for (FlexibleStringExpander orderByExpander: orderByExpanderList) {
orderByFields.add(orderByExpander.expandString(context));
}
@@ -149,30 +148,37 @@ public class EntityFinderUtil {
public static interface Condition extends Serializable {
public EntityCondition createCondition(Map<String, ? extends Object> context, ModelEntity modelEntity, ModelFieldTypeReader modelFieldTypeReader);
}
+
@SuppressWarnings("serial")
- public static class ConditionExpr implements Condition {
- protected FlexibleStringExpander fieldNameExdr;
- protected FlexibleStringExpander operatorExdr;
- protected FlexibleMapAccessor<Object> envNameAcsr;
- protected FlexibleStringExpander valueExdr;
- protected FlexibleStringExpander ignoreExdr;
- protected boolean ignoreIfNull;
- protected boolean ignoreIfEmpty;
- protected boolean ignoreCase;
+ public static final class ConditionExpr implements Condition {
+ private final String fieldName;
+ private final EntityOperator<?,?,?> operator;
+ private final FlexibleMapAccessor<Object> envNameAcsr;
+ private final FlexibleStringExpander valueExdr;
+ private final FlexibleStringExpander ignoreExdr;
+ private final boolean ignoreIfNull;
+ private final boolean ignoreIfEmpty;
+ private final boolean ignoreCase;
public ConditionExpr(Element conditionExprElement) {
- this.fieldNameExdr = FlexibleStringExpander.getInstance(conditionExprElement.getAttribute("field-name"));
- if (this.fieldNameExdr.isEmpty()) {
- // no "field-name"? try "name"
- this.fieldNameExdr = FlexibleStringExpander.getInstance(conditionExprElement.getAttribute("name"));
- }
-
- this.operatorExdr = FlexibleStringExpander.getInstance(UtilFormatOut.checkEmpty(conditionExprElement.getAttribute("operator"), "equals"));
- if (UtilValidate.isNotEmpty(conditionExprElement.getAttribute("from-field"))) {
- this.envNameAcsr = FlexibleMapAccessor.getInstance(conditionExprElement.getAttribute("from-field"));
- } else {
- this.envNameAcsr = FlexibleMapAccessor.getInstance(conditionExprElement.getAttribute("env-name"));
+ String fieldNameAttribute = conditionExprElement.getAttribute("field-name");
+ if (fieldNameAttribute.isEmpty()) {
+ fieldNameAttribute = conditionExprElement.getAttribute("name");
+ }
+ this.fieldName = fieldNameAttribute;
+ String operatorAttribute = conditionExprElement.getAttribute("operator");
+ if (operatorAttribute.isEmpty()) {
+ operatorAttribute = "equals";
+ }
+ this.operator = EntityOperator.lookup(operatorAttribute);
+ if (this.operator == null) {
+ throw new IllegalArgumentException("Could not find an entity operator for the name: " + operatorAttribute);
+ }
+ String fromFieldAttribute = conditionExprElement.getAttribute("from-field");
+ if (fromFieldAttribute.isEmpty()) {
+ fromFieldAttribute = conditionExprElement.getAttribute("env-name");
}
+ this.envNameAcsr = FlexibleMapAccessor.getInstance(fromFieldAttribute);
this.valueExdr = FlexibleStringExpander.getInstance(conditionExprElement.getAttribute("value"));
this.ignoreIfNull = "true".equals(conditionExprElement.getAttribute("ignore-if-null"));
this.ignoreIfEmpty = "true".equals(conditionExprElement.getAttribute("ignore-if-empty"));
@@ -181,22 +187,19 @@ public class EntityFinderUtil {
}
public EntityCondition createCondition(Map<String, ? extends Object> context, ModelEntity modelEntity, ModelFieldTypeReader modelFieldTypeReader) {
- String fieldName = fieldNameExdr.expandString(context);
-
- Object value = null;
- // start with the environment variable, will override if exists and a value is specified
- if (envNameAcsr != null) {
- value = envNameAcsr.get(context);
+ if ("true".equals(this.ignoreExdr.expandString(context))) {
+ return null;
}
- // no value so far, and a string value is specified, use that
- if (value == null && valueExdr != null) {
- value = valueExdr.expandString(context);
+ if (modelEntity.getField(fieldName) == null) {
+ throw new IllegalArgumentException("Error in Entity Find: could not find field [" + fieldName + "] in entity with name [" + modelEntity.getEntityName() + "]");
}
- String operatorName = operatorExdr.expandString(context);
- EntityOperator<?,?,?> operator = EntityOperator.lookup(operatorName);
- if (operator == null) {
- throw new IllegalArgumentException("Could not find an entity operator for the name: " + operatorName);
+ Object value = envNameAcsr.get(context);
+ if (value == null && !valueExdr.isEmpty()) {
+ value = valueExdr.expandString(context);
+ }
+ if (this.ignoreIfNull && value == null) {
+ return null;
}
// If IN or BETWEEN operator, see if value is a literal list and split it
@@ -208,15 +211,11 @@ public class EntityFinderUtil {
} else if (((String)value).indexOf(",") >= 0) {
delim = ",";
}
- if (UtilValidate.isNotEmpty(delim)) {
+ if (delim != null) {
value = StringUtil.split((String)value, delim);
}
}
- if (modelEntity.getField(fieldName) == null) {
- throw new IllegalArgumentException("Error in Entity Find: could not find field [" + fieldName + "] in entity with name [" + modelEntity.getEntityName() + "]");
- }
-
// don't convert the field to the desired type if this is an IN or BETWEEN operator and we have a Collection
if (!((operator.equals(EntityOperator.IN) || operator.equals(EntityOperator.BETWEEN) || operator.equals(EntityOperator.NOT_IN))
&& value instanceof Collection<?>)) {
@@ -226,17 +225,10 @@ public class EntityFinderUtil {
if (Debug.verboseOn()) Debug.logVerbose("Got value for fieldName [" + fieldName + "]: " + value, module);
- if (this.ignoreIfNull && value == null) {
- return null;
- }
if (this.ignoreIfEmpty && ObjectType.isEmpty(value)) {
return null;
}
- if ("true".equals(this.ignoreExdr.expandString(context))) {
- return null;
- }
-
if (operator == EntityOperator.NOT_EQUAL && value != null) {
// since some databases don't consider nulls in != comparisons, explicitly include them
// this makes more sense logically, but if anyone ever needs it to not behave this way we should add an "or-null" attribute that is true by default
@@ -263,68 +255,72 @@ public class EntityFinderUtil {
}
@SuppressWarnings("serial")
- public static class ConditionList implements Condition {
- List<Condition> conditionList = new LinkedList<Condition>();
- FlexibleStringExpander combineExdr;
+ public static final class ConditionList implements Condition {
+ private final List<Condition> conditionList;
+ private final EntityOperator<?,?,?> operator;
public ConditionList(Element conditionListElement) {
- this.combineExdr = FlexibleStringExpander.getInstance(conditionListElement.getAttribute("combine"));
-
+ String operatorAttribute = conditionListElement.getAttribute("combine");
+ if (operatorAttribute.isEmpty()) {
+ operatorAttribute = "equals";
+ }
+ this.operator = EntityOperator.lookup(operatorAttribute);
+ if (this.operator == null) {
+ throw new IllegalArgumentException("Could not find an entity operator for the name: " + operatorAttribute);
+ }
List<? extends Element> subElements = UtilXml.childElementList(conditionListElement);
- for (Element subElement: subElements) {
- if ("condition-expr".equals(subElement.getNodeName())) {
- conditionList.add(new ConditionExpr(subElement));
- } else if ("condition-list".equals(subElement.getNodeName())) {
- conditionList.add(new ConditionList(subElement));
- } else if ("condition-object".equals(subElement.getNodeName())) {
- conditionList.add(new ConditionObject(subElement));
- } else {
- throw new IllegalArgumentException("Invalid element with name [" + subElement.getNodeName() + "] found under a condition-list element.");
+ if (subElements.isEmpty()) {
+ this.conditionList = null;
+ } else {
+ List<Condition> conditionList = new ArrayList<Condition>(subElements.size());
+ for (Element subElement : subElements) {
+ if ("condition-expr".equals(subElement.getNodeName())) {
+ conditionList.add(new ConditionExpr(subElement));
+ } else if ("condition-list".equals(subElement.getNodeName())) {
+ conditionList.add(new ConditionList(subElement));
+ } else if ("condition-object".equals(subElement.getNodeName())) {
+ conditionList.add(new ConditionObject(subElement));
+ } else {
+ throw new IllegalArgumentException("Invalid element with name [" + subElement.getNodeName() + "] found under a condition-list element.");
+ }
}
+ this.conditionList = Collections.unmodifiableList(conditionList);
}
}
public EntityCondition createCondition(Map<String, ? extends Object> context, ModelEntity modelEntity, ModelFieldTypeReader modelFieldTypeReader) {
- if (this.conditionList.size() == 0) {
+ if (this.conditionList == null) {
return null;
}
if (this.conditionList.size() == 1) {
Condition condition = this.conditionList.get(0);
return condition.createCondition(context, modelEntity, modelFieldTypeReader);
}
-
- List<EntityCondition> entityConditionList = new LinkedList<EntityCondition>();
- for (Condition curCondition: conditionList) {
+ List<EntityCondition> entityConditionList = new ArrayList<EntityCondition>(this.conditionList.size());
+ for (Condition curCondition: this.conditionList) {
EntityCondition econd = curCondition.createCondition(context, modelEntity, modelFieldTypeReader);
if (econd != null) {
entityConditionList.add(econd);
}
}
-
- String operatorName = combineExdr.expandString(context);
- EntityOperator<?,?,?> operator = EntityOperator.lookup(operatorName);
- if (operator == null) {
- throw new IllegalArgumentException("Could not find an entity operator for the name: " + operatorName);
- }
-
return EntityCondition.makeCondition(entityConditionList, UtilGenerics.<EntityJoinOperator>cast(operator));
}
}
+
@SuppressWarnings("serial")
- public static class ConditionObject implements Condition {
- protected FlexibleMapAccessor<Object> fieldNameAcsr;
+ public static final class ConditionObject implements Condition {
+ private final FlexibleMapAccessor<Object> fieldNameAcsr;
public ConditionObject(Element conditionExprElement) {
- this.fieldNameAcsr = FlexibleMapAccessor.getInstance(conditionExprElement.getAttribute("field"));
- if (this.fieldNameAcsr.isEmpty()) {
- // no "field"? try "field-name"
- this.fieldNameAcsr = FlexibleMapAccessor.getInstance(conditionExprElement.getAttribute("field-name"));
+ String fieldNameAttribute = conditionExprElement.getAttribute("field");
+ if (fieldNameAttribute.isEmpty()) {
+ fieldNameAttribute = conditionExprElement.getAttribute("field-name");
}
+ this.fieldNameAcsr = FlexibleMapAccessor.getInstance(fieldNameAttribute);
}
public EntityCondition createCondition(Map<String, ? extends Object> context, ModelEntity modelEntity, ModelFieldTypeReader modelFieldTypeReader) {
- EntityCondition condition = (EntityCondition) fieldNameAcsr.get(context);
- return condition;
+ return (EntityCondition) fieldNameAcsr.get(context);
}
}