Skip to content
Merged
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
80 changes: 77 additions & 3 deletions java/working-with-cql/query-api.md
Original file line number Diff line number Diff line change
Expand Up @@ -621,7 +621,22 @@ Select.from("bookshop.Books")
b.get("title").startsWith("Wuth")));
```

### Grouping

### Aggregating Data { #aggregating }

You can aggregate data in two ways:

- **Aggregate the current entity:** Use [aggregate functions](#aggregation-functions) like `sum` in the columns clause of your `Select` statement, usually together with [groupBy](#group-by), to summarize or group data.

- **Aggregate associated entities:** Use dedicated aggregation methods to calculate values over to-many associations directly in your queries. See [Aggregating over Associations](#aggregating-associations).


#### Aggregation Functions { #aggregation-functions }

Use [aggregation functions](/guides/databases#aggregate-functions) to calculate minimums, maximums, totals, averages, and counts of values. You can use them in *columns* of `Select` statements to include the aggregated values in the result set, or in the [having](#having) clause to filter based on aggregated values.


#### Grouping { #grouping }

The Query Builder API offers a way to group the results into summarized rows (in most cases these are aggregate functions) and apply certain criteria on it.

Expand All @@ -635,7 +650,7 @@ Let's assume the following dataset for our examples:
|103 |Hugo |
|104 |Smith |

#### Group By
##### Group By { #group-by }

The `groupBy` clause groups by one or more elements and usually involves aggregate [functions](query-api#scalar-functions), such as `count`, `countDistinct`, `sum`, `max`, `avg`, and so on. It returns one row for each group.

Expand All @@ -658,7 +673,7 @@ If we execute the query on our dataset, we get the following result:
|Hugo |1 |


#### Having
##### Having { #having }

To filter the [grouped](#group-by) result, `having` is used. Both, `having` and `where`, filter the result before `group by` is applied and can be used in the same query.

Expand All @@ -678,6 +693,65 @@ If we execute the query on our dataset, we get the following result:
|Smith |3 |


#### Aggregating over Associations <Beta /> { #aggregating-associations }

Use the aggregation methods `min`, `max`, `sum`, and `count` to calculate minimums, maximums, totals, and counts of values of associated entities directly in your CQL queries. You can use these aggregation methods in *columns* to include the aggregated values in the result set, or in the *where* clause to filter the result set based on aggregated values.

::: tip
Use [infix filters](/cds/cql#with-infix-filters) to aggregate only a subset of a (to-many) association.
:::

##### min

Find the minimum value of an element in a collection.

```java
Select.from(ORDERS).columns(
o -> o.id(),
o -> o.items()
.filter(i -> i.amount().gt(0)) // optional filter
.min(i -> i.amount()).as("minAmount")
);
```

This query selects each order’s id and the minimum item amount greater than 0 as "minAmount".

##### max

Find the maximum value of an element in a collection.

```java
Select.from(ORDERS)
.where(o -> o.items().max(i -> i.amount()).gt(100));
```

This query selects all orders where the maximum item amount is greater than 100.

##### sum

Calculate the total of a numeric element across related entities.

```java
Select.from(ORDERS).columns(
o -> o.id(),
o -> o.items().sum(i -> i.amount().times(i.price())).as("orderTotal")
);
```

This query selects each order's id and the total order amount (sum of amount times price) as "orderTotal".

##### count

Count non-null values of an element in a collection.

```java
Select.from(ORDERS)
.where(o -> o.items().count(i -> i.discount()).gt(0));
```

This query selects all orders where at least one item has a discount.


### Ordering and Pagination

The Query Builder API allows to specify the sort order of query results. The _sort specification_ governs, according to which elements the result is sorted, and which sort order (ascending or descending) is applied.
Expand Down