简体   繁体   中英

Spring data JpaRepository pagination and group by

In my JpaRepository interface I got the following method that works fine:

Page<PermissionRule> findByOrganizationIdAndTypeStringAndObjectReferenceIgnoreCaseContaining(
        Long organizationId, String typeId, String searchTerm, Pageable pageable);

What I need is the same query with a group by object_reference.

This is what I tried doing : EDIT

@Query(value = "SELECT object_reference, dst_type, other FROM permission_rule pr WHERE pr.organization_id = %?1% AND pr.dst_type_id = %?2% AND pr.object_reference LIKE %?3% GROUP BY object_reference", nativeQuery = true)
Page<PermissionRule> getFunds(Long organizationId, String dstTypeId, String searchTerm, Pageable pageable);

but I get the following error

InvalidJpaQueryMethodException: Cannot use native queries with dynamic sorting and/or pagination in method

Also if it helps my entity column that I want to use in GROUP BY is

@Column(name = "object_reference", nullable = false)
private String objectReference;

My question is whether there is an easier way to do it or I still need a custom query (do I need to move the custom query in the Entity maybe or use named query instead?) ?

You usually use a groupBy when you want to aggregate results. Here, you are doing select * instead of aggregation.

@Query("SELECT l.someCol, count(*) as numOfRows from SomeTable l GROUP BY l.someCol")
    Page<Something> findSomething(Pageable pageable);

The Something object can be an interface with getter methods for someCol and numOfRows.

If you're using native query, you need to use countQuery

@Query(value = "SELECT someCol, count(*) as numRows from SomeTable GROUP BY someCol",
            countQuery= "SELECT count(*) FROM (SELECT someCol, count(*) as numRows from SomeTable GROUP BY someCol)",
            nativeQuery=true)
    Page<Something> findSomething(Pageable pageable);

As stated in https://www.techonthenet.com/oracle/group_by.php : "The Oracle GROUP BY clause is used in a SELECT statement to collect data across multiple records and group the results by one or more columns" and has the following syntax:

SELECT expression1, expression2, ... expression_n, aggregate_function (aggregate_expression) FROM tables [WHERE conditions] GROUP BY expression1, expression2, ... expression_n;

In your query is missing an aggregate_function such as SUM, COUNT, MIN, MAX , or AVG .

Ignoring why I need to do a Group By without an aggregate, I found my solution:

@Query("SELECT pr FROM PermissionRule pr WHERE pr.organizationId = ?1 AND pr.type = ?2 GROUP BY objectReference")
Page<PermissionRule> getFunds(Long organizationId, String type, Pageable pageable);

Seems more straight forward than the native_query approach.

Useful link

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM