UNION to JPA Query

社会主义新天地 提交于 2019-11-26 14:27:34

问题


Is it possible to query "UNION" in JPA and even "Criteria Builder"?

I'm looking for examples, but so far i got no result.

Does anyone have any examples of how to use it?

Or would that be with native sql?


回答1:


SQL supports UNION, but JPA 2.0 JPQL does not. Most unions can be done in terms of joins, but some can not, and some are more difficult to express using joins.

EclipseLink supports UNION.




回答2:


Depending on the case, one could use sub queries, something like:

select e
from Entity e
where e.id in
(
  select e.id
  from Entity2 e2
       join e2.entity e
  where e2.someProperty = 'value'
)
      or e.id in
(
  select e.id
  from Entity3 e3
       join e3.entity e
  where e3.someProperty = 'value2'
)



回答3:


One thing just comes to my mind (searching for the exact same problem):

Perform two different JPA queries on the same entity mapping and simply add the objects of the second result to the list (or set to avoid duplicates) of the first result.

That way you get the same effect as with a UNION, the difference being that you use two SQL statements instead of one. But actually, I would expect that to perform just as good as issueing one UNION statement.




回答4:


write native query (set it true , default its false) - ex.

String findQuery = "select xyz from abc union select abc from def"
@Query(value = findQuery, nativeQuery = true)
//method



回答5:


There is no direct union for JPA, what I did was to build two specifications.

Specification<Task> specification = Specification.where(null);
Specification<Task> specification2 = Specification.where(null;

They belong to a single table but return different values

specification = specification.and((root, criteriaQuery, criteriaBuilder) -> criteriaBuilder.equal(criteriaBuilder.function(MONTH, Integer.class, root.get("deliveryExpirationDate")), month));
        specification2 = specification2.and((root, criteriaQuery, criteriaBuilder) -> criteriaBuilder.lessThan(criteriaBuilder.function(MONTH, Integer.class, root.get("deliveryExpirationDate")), month))
            .and((root, criteriaQuery, criteriaBuilder) -> criteriaBuilder.equal(root.get("enable"), true));

for this example it is a table of tasks that in the first specification I need the tasks of the current month enabled and disabled, and in the second specification I only need the tasks enabled of the previous months.

Specification<Task> specificationFullJoin = Specification.where(specification).or(specification2);

Esto es muy útil para que la lista de tareas devueltas tenga paginación.

taskRepository.findAll(specificationFullJoin, pageable).map(TaskResponse::new); //Here you can continue adding filters, sort or search.

It helps me a lot, I hope it is what they are looking for or that it serves them something.




回答6:


using EntityManager.createNativeQuery(...); It's allow you use UNION




回答7:


You can directly use UNION in your query. The following query returns id of friends from FRIENDSHIP table.

Eg:

TypedQuery<String> queryFriend = em.createQuery("SELECT f.Id FROM Friendship f WHERE f.frStuId = :stuId UNION "
                                 + "SELECT f.frStuId FROM Friendship f WHERE f.FriendId = :stuId", String.class);
queryFriend.setParameter("stuId", stuId);

List<String> futureFriends = queryFriend.getResultList();


来源:https://stackoverflow.com/questions/18958614/union-to-jpa-query

标签
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!