Просмотр исходного кода

Merge branch 'fix/distinct' into 'develop'

人员属于多个组织时会重复显示

See merge request o2oa/o2oa!310
胡起 5 лет назад
Родитель
Сommit
a22a553ed6

+ 102 - 42
o2server/x_base_core_project/src/main/java/com/x/base/core/project/jaxrs/StandardJaxrsAction.java

@@ -16,6 +16,7 @@ import javax.servlet.http.HttpServletRequest;
 
 import org.apache.commons.beanutils.PropertyUtils;
 import org.apache.commons.collections4.map.ListOrderedMap;
+import org.apache.commons.lang3.BooleanUtils;
 import org.apache.commons.lang3.StringUtils;
 
 import com.x.base.core.container.EntityManagerContainer;
@@ -25,6 +26,7 @@ import com.x.base.core.project.bean.WrapCopier;
 import com.x.base.core.project.exception.ExceptionWhen;
 import com.x.base.core.project.gson.GsonPropertyObject;
 import com.x.base.core.project.http.ActionResult;
+import com.x.base.core.project.tools.CollectionTools;
 import com.x.base.core.project.tools.ListTools;
 
 public abstract class StandardJaxrsAction extends AbstractJaxrsAction {
@@ -622,7 +624,7 @@ public abstract class StandardJaxrsAction extends AbstractJaxrsAction {
 			ListOrderedMap<String, Collection<?>> notIns, ListOrderedMap<String, Object> members,
 			ListOrderedMap<String, Object> notMembers, boolean andJoin, String order) throws Exception {
 		EntityManager em = emc.get(cls);
-		String str = "SELECT count(o) FROM " + cls.getCanonicalName() + " o";
+		String str = "SELECT count(distinct o) FROM " + cls.getCanonicalName() + " o";
 		/* 预编译的SQL语句的参数序号,必须由1开始 */
 		Integer index = 1;
 		List<String> ps = new ArrayList<>();
@@ -694,74 +696,132 @@ public abstract class StandardJaxrsAction extends AbstractJaxrsAction {
 		return (Long) query.getSingleResult() + 1;
 	}
 
+	// private <T extends JpaObject> Long count(EntityManagerContainer emc, Class<T>
+	// cls, EqualsTerms equals,
+	// NotEqualsTerms notEquals, LikeTerms likes, InTerms ins, NotInTerms notIns,
+	// MemberTerms members,
+	// NotMemberTerms notMembers, boolean andJoin) throws Exception {
+	// EntityManager em = emc.get(cls);
+	// String str = "SELECT count(distinct o) FROM " + cls.getCanonicalName() + "
+	// o";
+	// /* 预编译的SQL语句的参数序号,必须由1开始 */
+	// Integer index = 1;
+	// List<String> ps = new ArrayList<>();
+	// List<Object> vs = new ArrayList<>();
+	// if (null != equals && (!equals.isEmpty())) {
+	// for (Entry<String, Object> en : equals.entrySet()) {
+	// ps.add("o." + en.getKey() + (" = ?" + index));
+	// vs.add(en.getValue());
+	// index++;
+	// }
+	// }
+	// if (null != notEquals && (!notEquals.isEmpty())) {
+	// for (Entry<String, Object> en : notEquals.entrySet()) {
+	// ps.add("(o." + en.getKey() + (" <> ?" + index) + " or o." + en.getKey() + "
+	// is null)");
+	// vs.add(en.getValue());
+	// index++;
+	// }
+	// }
+	// if (null != likes && (!likes.isEmpty())) {
+	// List<String> ors = new ArrayList<>();
+	// for (Entry<String, Object> en : likes.entrySet()) {
+	// ors.add("o." + en.getKey() + (" Like ?" + index));
+	// vs.add("%" + en.getValue() + "%");
+	// index++;
+	// }
+	// ps.add("(" + StringUtils.join(ors, " or ") + ")");
+	// }
+	// if (null != ins && (!ins.isEmpty())) {
+	// for (Entry<String, Collection<?>> en : ins.entrySet()) {
+	// ps.add("o." + en.getKey() + (" in ?" + index));
+	// vs.add(en.getValue());
+	// index++;
+	// }
+	// }
+	// if (null != notIns && (!notIns.isEmpty())) {
+	// for (Entry<String, Collection<?>> en : notIns.entrySet()) {
+	// ps.add("o." + en.getKey() + (" not in ?" + index));
+	// vs.add(en.getValue());
+	// index++;
+	// }
+	// }
+	// if (null != members && (!members.isEmpty())) {
+	// for (Entry<String, Object> en : members.entrySet()) {
+	// ps.add(("?" + index) + (" member of o." + en.getKey()));
+	// vs.add(en.getValue());
+	// index++;
+	// }
+	// }
+	// if (null != notMembers && (!notMembers.isEmpty())) {
+	// for (Entry<String, Object> en : notMembers.entrySet()) {
+	// ps.add(("?" + index) + (" not member of o." + en.getKey()));
+	// vs.add(en.getValue());
+	// index++;
+	// }
+	// }
+	// if (!ps.isEmpty()) {
+	// str += " where " + StringUtils.join(ps, (andJoin ? " and " : " or "));
+	// }
+	// Query query = em.createQuery(str, cls);
+	// for (int i = 0; i < vs.size(); i++) {
+	// query.setParameter(i + 1, vs.get(i));
+	// }
+	// return (Long) query.getSingleResult();
+	// }
+
 	private <T extends JpaObject> Long count(EntityManagerContainer emc, Class<T> cls, EqualsTerms equals,
 			NotEqualsTerms notEquals, LikeTerms likes, InTerms ins, NotInTerms notIns, MemberTerms members,
 			NotMemberTerms notMembers, boolean andJoin) throws Exception {
 		EntityManager em = emc.get(cls);
-		String str = "SELECT count(o) FROM " + cls.getCanonicalName() + " o";
-		/* 预编译的SQL语句的参数序号,必须由1开始 */
-		Integer index = 1;
-		List<String> ps = new ArrayList<>();
-		List<Object> vs = new ArrayList<>();
+		CriteriaBuilder cb = em.getCriteriaBuilder();
+		CriteriaQuery<Long> cq = cb.createQuery(Long.class);
+		Root<T> root = cq.from(cls);
+		List<Predicate> ps = new ArrayList<>();
 		if (null != equals && (!equals.isEmpty())) {
 			for (Entry<String, Object> en : equals.entrySet()) {
-				ps.add("o." + en.getKey() + (" = ?" + index));
-				vs.add(en.getValue());
-				index++;
+				ps.add(cb.equal(root.get(en.getKey()), en.getValue()));
 			}
 		}
 		if (null != notEquals && (!notEquals.isEmpty())) {
 			for (Entry<String, Object> en : notEquals.entrySet()) {
-				ps.add("(o." + en.getKey() + (" <> ?" + index) + " or o." + en.getKey() + " is null)");
-				vs.add(en.getValue());
-				index++;
+				ps.add(cb.or(cb.isNull(root.get(en.getKey())), cb.notEqual(root.get(en.getKey()), en.getValue())));
 			}
 		}
 		if (null != likes && (!likes.isEmpty())) {
-			List<String> ors = new ArrayList<>();
+			List<Predicate> ors = new ArrayList<>();
 			for (Entry<String, Object> en : likes.entrySet()) {
-				ors.add("o." + en.getKey() + (" Like ?" + index));
-				vs.add("%" + en.getValue() + "%");
-				index++;
+				ors.add(cb.like(root.get(en.getKey()), "%" + en.getValue() + "%"));
 			}
-			ps.add("(" + StringUtils.join(ors, " or ") + ")");
+			ps.add(cb.or(CollectionTools.toArray(ors, Predicate.class)));
 		}
 		if (null != ins && (!ins.isEmpty())) {
 			for (Entry<String, Collection<?>> en : ins.entrySet()) {
-				ps.add("o." + en.getKey() + (" in ?" + index));
-				vs.add(en.getValue());
-				index++;
+				ps.add(root.get(en.getKey()).in(en.getValue()));
 			}
 		}
 		if (null != notIns && (!notIns.isEmpty())) {
 			for (Entry<String, Collection<?>> en : notIns.entrySet()) {
-				ps.add("o." + en.getKey() + (" not in ?" + index));
-				vs.add(en.getValue());
-				index++;
+				ps.add(cb.not(root.get(en.getKey()).in(en.getValue())));
 			}
 		}
 		if (null != members && (!members.isEmpty())) {
 			for (Entry<String, Object> en : members.entrySet()) {
-				ps.add(("?" + index) + (" member of o." + en.getKey()));
-				vs.add(en.getValue());
-				index++;
+				ps.add(cb.isMember(en.getValue(), root.get(en.getKey())));
 			}
 		}
 		if (null != notMembers && (!notMembers.isEmpty())) {
 			for (Entry<String, Object> en : notMembers.entrySet()) {
-				ps.add(("?" + index) + (" not member of o." + en.getKey()));
-				vs.add(en.getValue());
-				index++;
+				ps.add(cb.isNotMember(en.getValue(), root.get(en.getKey())));
 			}
 		}
-		if (!ps.isEmpty()) {
-			str += " where " + StringUtils.join(ps, (andJoin ? " and " : " or "));
-		}
-		Query query = em.createQuery(str, cls);
-		for (int i = 0; i < vs.size(); i++) {
-			query.setParameter(i + 1, vs.get(i));
+		Predicate p = null;
+		if (BooleanUtils.isTrue(andJoin)) {
+			p = cb.and(CollectionTools.toArray(ps, Predicate.class));
+		} else {
+			p = cb.or(CollectionTools.toArray(ps, Predicate.class));
 		}
-		return (Long) query.getSingleResult();
+		return em.createQuery(cq.select(cb.countDistinct(root)).where(p)).getSingleResult();
 	}
 
 	/**
@@ -1061,7 +1121,7 @@ public abstract class StandardJaxrsAction extends AbstractJaxrsAction {
 				selections.add(root.get(field));
 			}
 
-			List<Tuple> os = em.createQuery(cq.multiselect(selections))
+			List<Tuple> os = em.createQuery(cq.multiselect(selections).distinct(true))
 					.setMaxResults(Math.max(Math.min(count, list_max), list_min)).getResultList();
 
 			List<W> ws = new ArrayList<W>();
@@ -1121,7 +1181,7 @@ public abstract class StandardJaxrsAction extends AbstractJaxrsAction {
 				selections.add(root.get(field));
 			}
 
-			List<Tuple> os = em.createQuery(cq.multiselect(selections))
+			List<Tuple> os = em.createQuery(cq.multiselect(selections).distinct(true))
 					.setMaxResults(Math.max(Math.min(count, list_max), list_min)).getResultList();
 
 			List<W> ws = new ArrayList<W>();
@@ -1176,8 +1236,8 @@ public abstract class StandardJaxrsAction extends AbstractJaxrsAction {
 				cq.orderBy(cb.asc(root.get(sequenceField)));
 			}
 
-			List<T> os = em.createQuery(cq.select(root)).setMaxResults(Math.max(Math.min(count, list_max), list_min))
-					.getResultList();
+			List<T> os = em.createQuery(cq.select(root).distinct(true))
+					.setMaxResults(Math.max(Math.min(count, list_max), list_min)).getResultList();
 
 			ActionResult<List<T>> result = new ActionResult<>();
 			result.setData(new ArrayList<T>(os));
@@ -1240,14 +1300,14 @@ public abstract class StandardJaxrsAction extends AbstractJaxrsAction {
 		CriteriaBuilder cb = em.getCriteriaBuilder();
 		CriteriaQuery<Long> cq = cb.createQuery(Long.class);
 		Root<T> root = cq.from(cls);
-		return em.createQuery(cq.select(cb.count(root)).where(predicate)).getSingleResult();
+		return em.createQuery(cq.select(cb.countDistinct(root)).where(predicate)).getSingleResult();
 	}
 
 	/**
 	 * 将request参数值转为json
 	 */
 	public String request2Json(HttpServletRequest request) {
-		Map<String,String> map = new HashMap<>();
+		Map<String, String> map = new HashMap<>();
 		Enumeration paramNames = request.getParameterNames();
 		while (paramNames.hasMoreElements()) {
 			String paramName = (String) paramNames.nextElement();

+ 20 - 0
o2server/x_base_core_project/src/main/java/com/x/base/core/project/tools/CollectionTools.java

@@ -0,0 +1,20 @@
+package com.x.base.core.project.tools;
+
+import java.util.Collection;
+
+import org.apache.commons.collections4.IteratorUtils;
+
+/**
+ * @author Ray
+ */
+public class CollectionTools {
+
+    private CollectionTools() {
+        // nothing
+    }
+
+    public static <T> T[] toArray(Collection<T> col, Class<T> cls) {
+        return IteratorUtils.toArray(col.iterator(), cls);
+    }
+
+}

+ 2 - 3
o2server/x_organization_assemble_express/src/main/java/com/x/organization/assemble/express/jaxrs/person/ActionListWithUnitSubDirectLikeObject.java

@@ -9,8 +9,6 @@ import javax.persistence.criteria.CriteriaQuery;
 import javax.persistence.criteria.Predicate;
 import javax.persistence.criteria.Root;
 
-import org.apache.commons.lang3.StringUtils;
-
 import com.google.gson.JsonElement;
 import com.x.base.core.container.EntityManagerContainer;
 import com.x.base.core.container.factory.EntityManagerContainerFactory;
@@ -22,13 +20,14 @@ import com.x.base.core.project.http.EffectivePerson;
 import com.x.base.core.project.tools.ListTools;
 import com.x.base.core.project.tools.StringTools;
 import com.x.organization.assemble.express.Business;
-import com.x.organization.assemble.express.jaxrs.person.ActionListWithUnitSubDirectObject.Wo;
 import com.x.organization.core.entity.Identity;
 import com.x.organization.core.entity.Identity_;
 import com.x.organization.core.entity.Person;
 import com.x.organization.core.entity.Person_;
 import com.x.organization.core.entity.Unit;
 
+import org.apache.commons.lang3.StringUtils;
+
 import net.sf.ehcache.Element;
 
 class ActionListWithUnitSubDirectLikeObject extends BaseAction {

+ 22 - 2
o2server/x_organization_assemble_express/src/main/java/com/x/organization/assemble/express/jaxrs/role/ActionListWithPerson.java

@@ -9,8 +9,6 @@ import javax.persistence.criteria.CriteriaQuery;
 import javax.persistence.criteria.Predicate;
 import javax.persistence.criteria.Root;
 
-import org.apache.commons.lang3.StringUtils;
-
 import com.google.gson.JsonElement;
 import com.x.base.core.container.EntityManagerContainer;
 import com.x.base.core.container.factory.EntityManagerContainerFactory;
@@ -21,10 +19,14 @@ import com.x.base.core.project.http.ActionResult;
 import com.x.base.core.project.http.EffectivePerson;
 import com.x.base.core.project.tools.ListTools;
 import com.x.organization.assemble.express.Business;
+import com.x.organization.core.entity.Group;
+import com.x.organization.core.entity.Identity;
 import com.x.organization.core.entity.Person;
 import com.x.organization.core.entity.Role;
 import com.x.organization.core.entity.Role_;
 
+import org.apache.commons.lang3.StringUtils;
+
 import net.sf.ehcache.Element;
 
 class ActionListWithPerson extends BaseAction {
@@ -71,11 +73,19 @@ class ActionListWithPerson extends BaseAction {
 		List<Person> os = business.person().pick(wi.getPersonList());
 		List<String> groupIds = new ArrayList<>();
 		List<String> personIds = new ArrayList<>();
+		List<String> unitIds = new ArrayList<>();
 		for (Person person : os) {
 			personIds.add(person.getId());
 			groupIds.addAll(business.group().listSupNestedWithPerson(person.getId()));
 		}
 		groupIds = ListTools.trim(groupIds, true, true);
+		List<Identity> identities = this.identities(business, personIds);
+		for (Identity o : identities) {
+			unitIds.add(o.getUnit());
+		}
+		unitIds = ListTools.trim(unitIds, true, true);
+		groupIds.addAll(this.groupsContainsUnit(business, unitIds));
+		groupIds = ListTools.trim(groupIds, true, true);
 		EntityManager em = business.entityManagerContainer().get(Role.class);
 		CriteriaBuilder cb = em.getCriteriaBuilder();
 		CriteriaQuery<String> cq = cb.createQuery(String.class);
@@ -88,4 +98,14 @@ class ActionListWithPerson extends BaseAction {
 		return wo;
 	}
 
+	private List<Identity> identities(Business business, List<String> personIds) throws Exception {
+		return business.entityManagerContainer().fetchIn(Identity.class,
+				ListTools.toList(Identity.unit_FIELDNAME), Identity.person_FIELDNAME,
+				personIds);
+	}
+
+	private List<String> groupsContainsUnit(Business business, List<String> units) throws Exception {
+		return business.entityManagerContainer().idsIn(Group.class, Group.unitList_FIELDNAME, units);
+	}
+
 }

+ 2 - 3
o2server/x_organization_assemble_express/src/main/webapp/describe/sources/com/x/organization/assemble/express/jaxrs/person/ActionListWithUnitSubDirectLikeObject.java

@@ -9,8 +9,6 @@ import javax.persistence.criteria.CriteriaQuery;
 import javax.persistence.criteria.Predicate;
 import javax.persistence.criteria.Root;
 
-import org.apache.commons.lang3.StringUtils;
-
 import com.google.gson.JsonElement;
 import com.x.base.core.container.EntityManagerContainer;
 import com.x.base.core.container.factory.EntityManagerContainerFactory;
@@ -22,13 +20,14 @@ import com.x.base.core.project.http.EffectivePerson;
 import com.x.base.core.project.tools.ListTools;
 import com.x.base.core.project.tools.StringTools;
 import com.x.organization.assemble.express.Business;
-import com.x.organization.assemble.express.jaxrs.person.ActionListWithUnitSubDirectObject.Wo;
 import com.x.organization.core.entity.Identity;
 import com.x.organization.core.entity.Identity_;
 import com.x.organization.core.entity.Person;
 import com.x.organization.core.entity.Person_;
 import com.x.organization.core.entity.Unit;
 
+import org.apache.commons.lang3.StringUtils;
+
 import net.sf.ehcache.Element;
 
 class ActionListWithUnitSubDirectLikeObject extends BaseAction {

+ 22 - 2
o2server/x_organization_assemble_express/src/main/webapp/describe/sources/com/x/organization/assemble/express/jaxrs/role/ActionListWithPerson.java

@@ -9,8 +9,6 @@ import javax.persistence.criteria.CriteriaQuery;
 import javax.persistence.criteria.Predicate;
 import javax.persistence.criteria.Root;
 
-import org.apache.commons.lang3.StringUtils;
-
 import com.google.gson.JsonElement;
 import com.x.base.core.container.EntityManagerContainer;
 import com.x.base.core.container.factory.EntityManagerContainerFactory;
@@ -21,10 +19,14 @@ import com.x.base.core.project.http.ActionResult;
 import com.x.base.core.project.http.EffectivePerson;
 import com.x.base.core.project.tools.ListTools;
 import com.x.organization.assemble.express.Business;
+import com.x.organization.core.entity.Group;
+import com.x.organization.core.entity.Identity;
 import com.x.organization.core.entity.Person;
 import com.x.organization.core.entity.Role;
 import com.x.organization.core.entity.Role_;
 
+import org.apache.commons.lang3.StringUtils;
+
 import net.sf.ehcache.Element;
 
 class ActionListWithPerson extends BaseAction {
@@ -71,11 +73,19 @@ class ActionListWithPerson extends BaseAction {
 		List<Person> os = business.person().pick(wi.getPersonList());
 		List<String> groupIds = new ArrayList<>();
 		List<String> personIds = new ArrayList<>();
+		List<String> unitIds = new ArrayList<>();
 		for (Person person : os) {
 			personIds.add(person.getId());
 			groupIds.addAll(business.group().listSupNestedWithPerson(person.getId()));
 		}
 		groupIds = ListTools.trim(groupIds, true, true);
+		List<Identity> identities = this.identities(business, personIds);
+		for (Identity o : identities) {
+			unitIds.add(o.getUnit());
+		}
+		unitIds = ListTools.trim(unitIds, true, true);
+		groupIds.addAll(this.groupsContainsUnit(business, unitIds));
+		groupIds = ListTools.trim(groupIds, true, true);
 		EntityManager em = business.entityManagerContainer().get(Role.class);
 		CriteriaBuilder cb = em.getCriteriaBuilder();
 		CriteriaQuery<String> cq = cb.createQuery(String.class);
@@ -88,4 +98,14 @@ class ActionListWithPerson extends BaseAction {
 		return wo;
 	}
 
+	private List<Identity> identities(Business business, List<String> personIds) throws Exception {
+		return business.entityManagerContainer().fetchIn(Identity.class,
+				ListTools.toList(Identity.unit_FIELDNAME), Identity.person_FIELDNAME,
+				personIds);
+	}
+
+	private List<String> groupsContainsUnit(Business business, List<String> units) throws Exception {
+		return business.entityManagerContainer().idsIn(Group.class, Group.unitList_FIELDNAME, units);
+	}
+
 }