Author: vanto
Date: Tue Feb 23 16:44:35 2010
New Revision: 915424
URL: http://svn.apache.org/viewvc?rev=915424&view=rev
Log:
ODE-770: use HQL instead of hibernate's criteria API
Modified:
ode/branches/APACHE_ODE_1.X/dao-hibernate/src/main/java/org/apache/ode/daohib/bpel/BpelDAOConnectionImpl.java
ode/branches/APACHE_ODE_1.X/dao-hibernate/src/main/java/org/apache/ode/daohib/bpel/CriteriaBuilder.java
Modified:
ode/branches/APACHE_ODE_1.X/dao-hibernate/src/main/java/org/apache/ode/daohib/bpel/BpelDAOConnectionImpl.java
URL:
http://svn.apache.org/viewvc/ode/branches/APACHE_ODE_1.X/dao-hibernate/src/main/java/org/apache/ode/daohib/bpel/BpelDAOConnectionImpl.java?rev=915424&r1=915423&r2=915424&view=diff
==============================================================================
---
ode/branches/APACHE_ODE_1.X/dao-hibernate/src/main/java/org/apache/ode/daohib/bpel/BpelDAOConnectionImpl.java
(original)
+++
ode/branches/APACHE_ODE_1.X/dao-hibernate/src/main/java/org/apache/ode/daohib/bpel/BpelDAOConnectionImpl.java
Tue Feb 23 16:44:35 2010
@@ -69,6 +69,7 @@
import org.hibernate.FetchMode;
import org.hibernate.HibernateException;
import org.hibernate.Session;
+import org.hibernate.criterion.DetachedCriteria;
import org.hibernate.criterion.Expression;
import org.hibernate.criterion.Projections;
@@ -191,13 +192,9 @@
@SuppressWarnings("unchecked")
private static List<HProcessInstance> _instanceQueryForList(Session
session, boolean countOnly, InstanceFilter filter) {
- Criteria crit = session.createCriteria(HProcessInstance.class);
CriteriaBuilder cb = new CriteriaBuilder();
- cb.buildCriteria(crit, filter);
- crit.setFetchMode("fault", FetchMode.JOIN);
-
- return crit.list();
+ return cb.buildHQLQuery(session, filter).list();
}
static ProcessInstanceDAO _getInstance(SessionManager sm, Session session,
Long iid) {
Modified:
ode/branches/APACHE_ODE_1.X/dao-hibernate/src/main/java/org/apache/ode/daohib/bpel/CriteriaBuilder.java
URL:
http://svn.apache.org/viewvc/ode/branches/APACHE_ODE_1.X/dao-hibernate/src/main/java/org/apache/ode/daohib/bpel/CriteriaBuilder.java?rev=915424&r1=915423&r2=915424&view=diff
==============================================================================
---
ode/branches/APACHE_ODE_1.X/dao-hibernate/src/main/java/org/apache/ode/daohib/bpel/CriteriaBuilder.java
(original)
+++
ode/branches/APACHE_ODE_1.X/dao-hibernate/src/main/java/org/apache/ode/daohib/bpel/CriteriaBuilder.java
Tue Feb 23 16:44:35 2010
@@ -19,32 +19,240 @@
package org.apache.ode.daohib.bpel;
+import java.sql.Timestamp;
+import java.text.ParseException;
+import java.util.ArrayList;
+import java.util.Date;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+import org.apache.commons.logging.Log;
+import org.apache.commons.logging.LogFactory;
import org.apache.ode.bpel.common.BpelEventFilter;
import org.apache.ode.bpel.common.Filter;
import org.apache.ode.bpel.common.InstanceFilter;
import org.apache.ode.utils.ISO8601DateParser;
import org.apache.ode.utils.RelativeDateParser;
import org.hibernate.Criteria;
+import org.hibernate.Query;
+import org.hibernate.Session;
import org.hibernate.criterion.Disjunction;
import org.hibernate.criterion.Property;
import org.hibernate.criterion.Restrictions;
-import java.text.ParseException;
-import java.util.Date;
-import java.util.List;
-import java.util.Map;
-
/**
* Class used for converting "filter" objects into Hibernate
* {...@link org.hibernate.Criteria} objects.
*/
class CriteriaBuilder {
+ static final Log __log = LogFactory.getLog(CriteriaBuilder.class);
+
+ /**
+ * Build a HQL query from an instance filter.
+ * @param filter filter
+ */
+ Query buildHQLQuery(Session session, InstanceFilter filter) {
+ Map<String, Object> parameters = new HashMap<String, Object>();
+
+ StringBuffer query = new StringBuffer();
+
+ query.append("select pi from HProcessInstance as pi left join fetch
pi.fault ");
+
+ if (filter != null) {
+ // Building each clause
+ ArrayList<String> clauses = new ArrayList<String>();
+
+ // iid filter
+ if ( filter.getIidFilter() != null ) {
+ StringBuffer filters = new StringBuffer();
+ List<String> iids = filter.getIidFilter();
+ for (int m = 0; m < iids.size(); m++) {
+ filters.append(" pi.id = :iid").append(m);
+ parameters.put("iid" + m, iids.get(m));
+ if (m < iids.size() - 1) filters.append(" or");
+ }
+ clauses.add(" (" + filters + ")");
+ }
+
+ // pid filter
+ if (filter.getPidFilter() != null) {
+ StringBuffer filters = new StringBuffer();
+ List<String> pids = filter.getPidFilter();
+ String cmp;
+ if (filter.arePidsNegative()) {
+ cmp = " != ";
+ } else {
+ cmp = " = ";
+ }
+ for (int m = 0; m < pids.size(); m++) {
+ filters.append(" pi.process.id ").append(cmp).append("
:pid").append(m);
+ parameters.put("pid" + m, pids.get(m));
+ if (m < pids.size() - 1) filters.append(" or");
+ }
+ clauses.add(" (" + filters + ")");
+ }
+
+ // name filter
+ if (filter.getNameFilter() != null) {
+ clauses.add(" pi.process.typeName like :pname");
+ parameters.put("pname",
filter.getNameFilter().replaceAll("\\*", "%"));
+ }
+
+ // name space filter
+ if (filter.getNamespaceFilter() != null) {
+ clauses.add(" pi.process.typeNamespace like :pnamespace");
+ parameters.put("pnamespace",
filter.getNamespaceFilter().replaceAll("\\*", "%"));
+ }
+
+ // started filter
+ if (filter.getStartedDateFilter() != null) {
+ for ( String ds : filter.getStartedDateFilter() ) {
+ // named parameters not needed as date is parsed and is
hence not
+ // prone to HQL injections
+ clauses.add(" pi.created " + dateFilter(ds));
+ }
+ }
+
+ // last-active filter
+ if (filter.getLastActiveDateFilter() != null) {
+ for ( String ds : filter.getLastActiveDateFilter() ) {
+ // named parameters not needed as date is parsed and is
hence not
+ // prone to HQL injections
+ clauses.add(" pi.lastActiveTime " + dateFilter(ds));
+ }
+ }
+
+ // status filter
+ if (filter.getStatusFilter() != null) {
+ StringBuffer filters = new StringBuffer();
+ List<Short> states = filter.convertFilterState();
+ for (int m = 0; m < states.size(); m++) {
+ filters.append(" pi.state = :pstate").append(m);
+ parameters.put("pstate" + m, states.get(m));
+ if (m < states.size() - 1) filters.append(" or");
+ }
+ clauses.add(" (" + filters.toString() + ")");
+ }
+
+ // $property filter
+ if (filter.getPropertyValuesFilter() != null) {
+ Map<String,String> props = filter.getPropertyValuesFilter();
+ // join to correlation sets
+ query.append(" inner join pi.correlationSets as cs");
+ int i = 0;
+ for (String propKey : props.keySet()) {
+ i++;
+ // join to props for each prop
+ query.append(" inner join cs.properties as csp"+i);
+ // add clause for prop key and value
+
+ // spaces have to be escaped, might be better handled in
InstanceFilter
+ String value = props.get(propKey).replaceAll(" ", " ");
+ if (propKey.startsWith("{")) {
+ String namespace = propKey.substring(1,
propKey.lastIndexOf("}"));
+ clauses.add(" csp" + i + ".name = :cspname" + i +
+ " and csp" + i + ".namespace = :cspnamespace"
+ i +
+ " and csp" + i + ".value = :cspvalue" + i);
+
+ parameters.put("cspname" + i,
propKey.substring(propKey.lastIndexOf("}") + 1, propKey.length()));
+ parameters.put("cspnamespace" + i, namespace);
+ parameters.put("cspvalue" + i, value);
+ } else {
+ clauses.add(" csp" + i + ".name = :cspname" + i +
+ " and csp" + i + ".value = :cspvalue" + i);
+
+ parameters.put("cspname" + i, propKey);
+ parameters.put("cspvalue" + i, value);
+ }
+ }
+ }
+
+ // order by
+ StringBuffer orderby = new StringBuffer("");
+ if (filter.getOrders() != null) {
+ orderby.append(" order by");
+ List<String> orders = filter.getOrders();
+ for (int m = 0; m < orders.size(); m++) {
+ String field = orders.get(m);
+ String ord = " asc";
+ if (field.startsWith("-")) {
+ ord = " desc";
+ }
+ String fieldName = " pi.id";
+ if (field.endsWith("name")) {
+ fieldName = " pi.process.typeName";
+ }
+ if (field.endsWith("namespace")) {
+ fieldName = " pi.process.typeNamespace";
+ }
+ if ( field.endsWith("version")) {
+ fieldName = " pi.process.version";
+ }
+ if ( field.endsWith("status")) {
+ fieldName = " pi.state";
+ }
+ if ( field.endsWith("started")) {
+ fieldName = " pi.created";
+ }
+ if ( field.endsWith("last-active")) {
+ fieldName = " pi.lastActiveTime";
+ }
+ orderby.append(fieldName + ord);
+ if (m < orders.size() - 1) orderby.append(", ");
+ }
+
+ }
+
+ // Preparing the statement
+ if (clauses.size() > 0) {
+ query.append(" where");
+ for (int m = 0; m < clauses.size(); m++) {
+ query.append(clauses.get(m));
+ if (m < clauses.size() - 1) query.append(" and");
+ }
+ }
+
+ query.append(orderby);
+ }
+
+ if (__log.isDebugEnabled()) {
+ __log.debug(query.toString());
+ }
+
+ Query q = session.createQuery(query.toString());
+
+ for (String p : parameters.keySet()) {
+ q.setParameter(p, parameters.get(p));
+ }
+
+ if (filter.getLimit() != 0) {
+ q.setMaxResults(filter.getLimit());
+ }
+
+ return q;
+ }
+
+ private static String dateFilter(String filter) {
+ String date = Filter.getDateWithoutOp(filter);
+ String op = filter.substring(0,filter.indexOf(date));
+ Date dt = null;
+ try {
+ dt = ISO8601DateParser.parse(date);
+ } catch (ParseException e) {
+ e.printStackTrace();
+ }
+ Timestamp ts = new Timestamp(dt.getTime());
+ return op + " '" + ts.toString() + "'";
+ }
+
+
+
/**
* Build a Hibernate {...@link Criteria} from an instance filter.
* @param crit target (destination) criteria
* @param filter filter
*/
- @SuppressWarnings("unchecked")
void buildCriteria(Criteria crit, InstanceFilter filter) {
Criteria processCrit = crit.createCriteria("process");