You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
Copy file name to clipboardExpand all lines: src/main/asciidoc/repositories.adoc
+82Lines changed: 82 additions & 0 deletions
Original file line number
Diff line number
Diff line change
@@ -225,6 +225,88 @@ In the prior example, you defined a common base interface for all your domain re
225
225
226
226
NOTE: The intermediate repository interface is annotated with `@NoRepositoryBean`. Make sure you add that annotation to all repository interfaces for which Spring Data should not create instances at runtime.
227
227
228
+
[[repositories.collections-and-iterables]]
229
+
=== Repository Methods Returning Collections or Iterables
230
+
Query methods that return multiple results can use standard Java `Iterable`, `List`, `Set`.
231
+
Beyond that we support returning Spring Data's `Streamable`, a custom extension of `Iterable`, as well as collection types provided by http://www.vavr.io/[Vavr].
`Streamable` can be used as alternative to `Iterable` or any collection type.
236
+
It provides convenience methods to access a non-parallel `Stream` (missing from `Iterable`), the ability to directly `….filter(…)` and `….map(…)` over the elements and concatenate the `Streamable` to others:
Providing dedicated wrapper types for collections is a commonly used pattern to provide API on a query execution result that returns multiple elements.
256
+
Usually these types are used by invoking a repository method returning a collection-like type and creating an instance of the wrapper type manually.
257
+
That additional step can be avoided as Spring Data allows to use these wrapper types as query method return types if they meet the following criterias:
258
+
259
+
. The type implements `Streamable`.
260
+
. The type exposes either a constructor or a static factory method named `of(…)` or `valueOf(…)` taking `Streamable` as argument.
261
+
262
+
A sample use case looks as follows:
263
+
264
+
====
265
+
[source, java]
266
+
----
267
+
class Product { <1>
268
+
MonetaryAmount getPrice() { … }
269
+
}
270
+
271
+
@RequiredArgConstructor(staticName = "of")
272
+
class Products implements Streamable<Product> { <2>
<1> A `Product` entity that exposes API to access the product's price.
288
+
<2> A wrapper type for a `Streamable<Product>` that can be constructed via `Products.of(…)` (factory method created via the Lombok annotation).
289
+
<3> The wrapper type exposes additional API calculating new values on the `Streamable<Product>`.
290
+
<4> That wrapper type can be used as query method return type directly. No need to return `Stremable<Product>` and manually wrap it in the repository client.
291
+
====
292
+
293
+
[[repositories.collections-and-iterables.vavr]]
294
+
==== Support for Vavr Collections
295
+
296
+
http://www.vavr.io/[Vavr] is a library to embrace functional programming concepts in Java.
297
+
It ships with a custom set of collection types that can be used as query method return types.
The types in the first column (or subtypes thereof) can be used as quer method return types and will get the types in the second column used as implementation type depending on the Java type of the actual query result (thrid column).
308
+
Alternatively, `Traversable` (Vavr the `Iterable` equivalent) can be declared and we derive the implementation class from the actual return value, i.e. a `java.util.List` will be turned into a Vavr `List`/`Seq`, a `java.util.Set` becomes a Vavr `LinkedHashSet`/`Set` etc.
Copy file name to clipboardExpand all lines: src/main/asciidoc/repository-query-return-types-reference.adoc
+3Lines changed: 3 additions & 0 deletions
Original file line number
Diff line number
Diff line change
@@ -21,6 +21,9 @@ NOTE: Geospatial types (such as `GeoResult`, `GeoResults`, and `GeoPage`) are av
21
21
|`Optional<T>`|A Java 8 or Guava `Optional`. Expects the query method to return one result at most. If no result is found, `Optional.empty()` or `Optional.absent()` is returned. More than one result triggers an `IncorrectResultSizeDataAccessException`.
22
22
|`Option<T>`|Either a Scala or Vavr `Option` type. Semantically the same behavior as Java 8's `Optional`, described earlier.
23
23
|`Stream<T>`|A Java 8 `Stream`.
24
+
|`Streamable<T>`|A convenience extension of `Iterable` that directy exposes methods to stream, map and filter results, concatenate them etc.
25
+
|Types that implement `Streamable` and take a `Streamable` constructor or factory method argument|Types that expose a constructor or `….of(…)`/`….valueOf(…)` factory method taking a `Streamable` as argument. See <<repositories.collections-and-iterables.streamable-wrapper>> for details.
26
+
|Vavr `Seq`, `List`, `Map`, `Set`|Vavr collection types. See <<repositories.collections-and-iterables.vavr>> for details.
24
27
|`Future<T>`|A `Future`. Expects a method to be annotated with `@Async` and requires Spring's asynchronous method execution capability to be enabled.
25
28
|`CompletableFuture<T>`|A Java 8 `CompletableFuture`. Expects a method to be annotated with `@Async` and requires Spring's asynchronous method execution capability to be enabled.
26
29
|`ListenableFuture`|A `org.springframework.util.concurrent.ListenableFuture`. Expects a method to be annotated with `@Async` and requires Spring's asynchronous method execution capability to be enabled.
0 commit comments