RepositoryFactoryBeanSupport now takes the repository interface as a constructor argument instead of as a setter. This makes sure that the container induced type prediction for factory beans actually wires the interface *before* it calls getObjectType() on the instance. This allows us to remove the extra infrastructure we had in place to predict the bean types and autowiring will just work out of the box.
Adapted infrastructure code accordingly, removed obsolete infrastructure code and adapted test cases accordingly.
The interceptor discovers whether a transaction was running before the call entered the repository proxy and exposes that fact via ….isSurroundingTransactionActive() for donwstream usage.
Related ticket: DATAJPA-1023.
The nullable wrapper types now expose whether they're a single value type or a multi value type. This is necessary as Javaslang's Option implements Iterable (something we previously checked for to detect a collection query) and the custom collections potentially being usable within other wrapper types (e.g. Future<Seq<User>>).
Javaslang's collection and map types can now be used on repository query methods and get adapted similarly to nullable wrapper types (like JDK's Optional). Also made TypeInformation infrastructure aware of the map type so that a value type lookup gets handle correctly.
We now support downcasts (e.g. user.as(QSpecialUser.class).…) expressions in Querydsl web binding. We do so by skipping the introduced intermediate step in the path when calculating the dot path.
Refactored the internals of the binding to now work based on a PathInformation implementation for which either a Querydsl Path or a Spring Data PropertyPath can be used. This allows us to reuse the paths of predefined bindings.
A bit of Lombok cleanup in internal implementations.
Previously a null value was added to the list of associations if it was handed to BasicaPersistentEntity.addAssociation(…). We now drop those null values and log a warning as it usually indicates a MappingContext implementation identifying a property as association but subsequently failing to look it up.
Both the configuration code looking up Spring Data specific Jackson modules as well as the code detecting whether we have multiple Spring Data modules on the classpath used component scanning. That can have quite significant impact on startup times.
This commit replaces the classpath scanning with the use of SpringFactoriesLoader that now requires modules that want to extend the behavior of Spring Data's web configuration or indicate a repository implementation being present by shipping a file called META-INF/spring.factories. Spring Data relies on the following keys:
- org.springframework.data.web.config.SpringDataJacksonModules - list the Spring configuration classes that will expose additional Jackson modules that are supposed to be registered for Spring Data's Jackson web support
- org.springframework.data.repository.core.support.RepositoryFactorySupport - list the Spring Data repository factory implementation class that implements repository support for your module. The general detection and configuration mechanism for user repositories is not affected by this. Currently Spring Data only uses the pure number of different entries for that key to switch into strict configuration mode in case we find more than one entry.
We now publish events for all methods named "save" on the repository. Fundamentally, that's in place to capture calls to CrudRepository.save(Iterable entities), too.
Some minor refactorings to the internal setup of EventPublishingMethodInterceptor. More JavaDoc.
Introduced @DomainEvents usable on a method of an aggregate root. The method will be invoked when the aggregate is passed to a repository to save and its returned value or values will be exposed via an ApplicationEventListener.
Also, the aggregate can expose a method annotated with @AfterDomainEventPublication which will be invoked once all events have been published.
We now try to look up a target class method based on concrete name and parameter type before falling back on the more expensive type matches. This also eliminates the possibility of invalid method matches as described in the ticket.
We now no longer attempt query creation for static methods declared on a repository interface. This allows static method usage inside of repository interfaces.
interface PersonRepository extends CrudRepository<Person, String> {
static String createId() {
// …
}
default Person findPerson() {
return findOne(createId());
}
}
PageableHandlerMethodArgumentResolver.isFallbackPageable() now correctly guards against the fallback Pageable being null, a situation that's explicitly deemed valid in setFallbackPageable(…).
This commit changes some ArrayList initializations to use an initial capacity and avoids the unnecessary fetch of the return type of a method in Parameter.isDynamicProjectionParameter().
Original pull request: #180.
The special case of an Iterable parameter doesn't have to be handled explicitly anymore so that we can simplify the type match check in DefaultRepositoryInformation.
Related ticket: DATACMNS-912.
Previously, ClassGeneratingPropertyAccessorFactory uses boxed types for primitive type setters. This threw NoSuchMethodExceptions and caused ExceptionInInitializerError as the generated class could not be initialized. We now use the appropriate argument type to look up setters.
Also, we now only generate accessor usage if the property is configured to use property access in the first place.
Original pull request: #178.
QueryExecutionResultHandler now explicitly handles null values for query methods returning Maps by returning an empty Map. This can be the case if a query is supposed to produce a Map (a single result) but doesn't actually yield any results at all.
We now correctly check the bounds of generic methods if we deal with a type variable found as method parameter. Introduced different code paths for type and method level generics so that the latter is explicitly checking all bounds available.
After the Spring 5 build profile has been activated properly in Spring Data build [0], the test cases for RepositoryPopulators failed as there was only an explicit detection of Spring 4 to point the test to the right resource file. Removed the guard now as all supported versions can now use the same file.
Adapt to the stricter contract in Spring 5's MethodParameter in unit test for QuerydsPredicateArgumentResolver.
[0] 31df5de907
The proxies created for projections now defensively mask getDecoratedClass(), a method declared on DecoratingProxy, an interface that JDK proxies on Spring 4.3 will implement.
The introduced method allows creating new Order instances for a different property ensuring all other aspects (ignore case, null handling) are retained.
Introduced dedicated RevisionSort property that allows to define the sort order independent of the revision property to be used.
Introduced methods to find out whether a Sort is descending or ascending to avoid having to refer to the enum.
We now support exists projections in derived queries by parsing the exists keyword and expose it via PartTree.isExistsProjection().
Original pull request: #171.
Previously, calls to ParameterizedTypeInformation.getMapValueType() caused an infinite recursion when invoked on a type information that was not a map type. This lead to a StackOverflowError.
We now call the super method doGetMapValueType() instead of calling the entry super method getMapValueType() and return by that null in case the map value type is not resolvable.
Original pull request: #176.
We now provide equals(…) and hashCode() methods for GenericPropertyMatcher, PropertySpecifier and PropertySpecifiers so that they can be compared and used in sets.
Original pull request: #175.