Added Streamable.toStreamable() and ….toStreamable(Collector) to allow the creation of a Streamable from streams wither using a default List-based intermediate collector (former) or providing an explicit one (latter).
We now use a presized HashMap and Weak references in BasicPersistentEntity to improve memory and CPU profile and and avoid unmodifiable collection creation in BasicPersistentEntity.iterator(). Refactored ClassTypeInformation.from(…) lambda to method reference and predefined collection size for the cache. Reduced object instantiations during TypeDiscoverer.equals(…) by checking for type variable map emptiness to avoid Map iterator creation in Map.equals(…).
Original pull request: #305.
CustomRepositoryImplementationDetector now works in two differend modes. If initialized with an ImplementationDetectionConfiguration, it will trigger a canonical, cached component scan for implementation types matching the configured name pattern. Individual custom implementation lookups will then select from this initially scanned set of bean definitions to pick the matching implementation class and potentially resolve ambiguities.
Add missing since tags. Extract methods to maintain single abstraction level per method. Move visitDefaultValue from ClassGeneratingPropertyAccessorFactory to BytecodeUtil. Extend Javadoc.
We now support updating of immutable Kotlin data objects by creating new copies through Kotlin's copy method that is generated along with data classes and immutable properties.
data class DataClassKt(val id: String) {
}
data class ExtendedDataClassKt(val id: String, val name: String) {
}
Introduced ProxyUtils.getUserClass(…) that by default is basically a facade for Spring's ClassUtils.getUserClass(…) but allows the registration of ProxyDetector implementations via Spring's SpringFactoriesLoader mechanism.
Moved all existing usages of ClassUtils.getUserClass(…) to ProxyUtils.
MappingContext now exposes a method to detect all property paths pointing to properties matching a given predicate.
Extracted PersistentPropertyPath creation into a dedicated factory class so that it can be tested individually. DefaultPersistentPropertyPath now exposes a ….containsPropertyOfType(…) to detect whether we've already processed a particular type in the path. Also applied a bit of Java 8 and Lombok polish.
InvalidPersistentPropertyPath now collects suggested alternatives to create a better exception message. PersistentEntities now allows to map over a MappingContext and PersistentEntity that a given type is corresponding to. Streamable now exposes an ….isEmpty(). Removed references to equivalent methods implemented in subtypes.
We now inspect Kotlin's Metadata annotation to determine the kind of a Kotlin class.
Previously we used Kotlins internal API to introspect classes. Because this API is not public and can be changed at any time we rely on Kotlins annotations as they are supposed to not change in near future.
Original pull request: #269.
Expanded generics to make sure we can take Functions and Suppliers of sub- and supertypes properly. Added factory method to create a Lazy from a fixed value. Added method to access Optional result. Added methods to allow chaining Lazy instances via ….or(…). Reduced visibility of ….orElseGet(…) as it basically equates to ….or(…).get(Optional)().
More unit tests.
Introduced BeanLookup to easily create a Lazy<T>-based lookup of a unique bean by type on a ListableBeanFactory. This is in support of making it easy for downstream Spring Data modules to consume the EntityPathResolver declared in an ApplicationContext using XML configuration.
QuerydslWebConfiguration now uses a plain ObjectProvider to access the bean defined falling back to our default.
Original pull request: #265.
We now resolve Kotlin interface properties to inspect these for nullability. Kotlin-reflect does not resolve interface property accessors yet so we need to handle this aspect ourselves.
Related ticket: https://youtrack.jetbrains.com/issue/KT-20768.
Original pull request: #254.
We now eagerly resolve a generics declaration chain, which we previously - erroneously - expected GenericTypeResolver to do for us. Simplified TypeVariableTypeInformation implementation. Renamed ParameterizedTypeUnitTests to ParameterizedTypeInformationUnitTests.
We now only inspect regular Kotlin classes with inspection to adapt Kotlin-specific behavior. Multipart-, synthetic and unknown classes are not supported. In such cases we fall back to the JVM reflection mechanism.
Non-regular classes are typically synthetic stubs, lambdas and SAM conversion which do not represent typical domain objects but rather technical bridge code.
Original pull request: #245.
We now validate query method invocations to check method parameters whether they accept null values and reject execution if null values are not supported. We derive nullability support from repository interfaces declared using Kotlin and Spring's NonNullApi/Nullable annotations.
We also check whether a query method can return null. If a query method returns null which isn't supposed to do so, then we throw EmptyResultDataAccessException to prevent null return values.
interface UserRepository extends Repository<User, String> {
List<User> findByLastname(@Nullable String firstname);
@Nullable
User findByFirstnameAndLastname(String firstname, String lastname);
}
interface UserRepository : Repository<User, String> {
fun findByLastname(username: String?): List<User>
fun findByFirstnameAndLastname(firstname: String, lastname: String): User?
}
Original pull request: #241.
We now discover Kotlin constructors and apply parameter defaulting to allow construction of immutable value objects. Constructor discovery uses primary constructors by default and considers PersistenceConstructor annotations.
KotlinClassGeneratingEntityInstantiator can instantiate Kotlin classes with default parameters by resolving the synthetic constructor. Null values translate to parameter defaults.
class Person(val firstname: String = "Walter") {
}
class Address(val street: String, val city: String) {
@PersistenceConstructor
constructor(street: String = "Unknown", city: String = "Unknown", country: String) : this(street, city)
}
Original pull request: #233.
Type specialization - i.e. enrichment of a raw type with a current generic context - is now only done if the current type is not yet resolved completely. This allows wildcarded target references to just fall back to the type to specialize, which will then by definition carry more generics information than the one to be specialized.
Revert the merging of a parent type's type variable map and only apply the locally available declared generics in case of parameterized types. Moved that augmentation into ParameterizedTypeInformation.
Marked all packages with Spring Frameworks @NonNullApi. Added Spring's @Nullable to methods, parameters and fields that take or produce null values. Adapted using code to make sure the IDE can evaluate the null flow properly. Fixed Javadoc in places where an invalid null handling policy was advertised. Strengthened null requirements for types that expose null-instances.
Removed null handling from converters for JodaTime and ThreeTenBP. Introduced factory methods Page.empty() and Page.empty(Pageable). Introduced default methods getRequiredGetter(), …Setter() and …Field() on PersistentProperty to allow non-nullable lookups of members. The same for TypeInformation.getrequiredActualType(), …SuperTypeInformation().
Tweaked PersistentPropertyCreator.addPropertiesForRemainingDescriptors() to filter unsuitable PropertyDescriptors before actually trying to create a Property instance from them as the new stronger nullability requirements would cause exceptions downstream.
Lazy.get() now expects a non-null return value. Clients being able to cope with null need to call ….orElse(…).
Original pull request: #232.
This is an overload for the already existing method taking a plain Iterator so that we only apply the close callback to the Stream in the newly introduced one.
Updated Sonargraph architecture description. Polished imports in domain package to avoid unnecessary imports (mostly due to Javadoc references).
Removed manually declared constructor in ExampleMatcherAccessor in favor of Lombok's @RequiredArgsConstructor. Removed deprecations in type information subsystem. Moved to different way of class loading to avoid null pointer warnings in ReflectionUtils.
All overloaded methods are now available in SPeL expressions. Among methods with identical argument list from different sources in the same extension (extension, root object, aliases) the last one in the order in parens wins. If there is more than one method for an application the following rules are applied: if there is one method with exact matching types in the argument list it is used, otherwise an exception is thrown.
Original pull request: #217.
RevisionRepository now returns Optional for methods that could previously return null. Revision exposes additional methods to lookup required revision numbers and dates. Revisions now implements Streamable and exposes a ….none() factory method to create an empty instance.
AnnotationBasedRevisionMetadata now uses Lazy to lookup the fields with revision annotations. AnnotationDetectionFieldCallback now also uses Optional in places it previously returned null. StreamUtils now exposes factory methods for Collector instances producing unmodifiable List and Set instances.
Related ticket: DATACMNS-867.
Removed the additional methods that reflectively checked for the Stream type and whether a Method instance is a default method. Turned utility classes into interfaces where possible. Make use of Lombok's @UtilityClass where not.
Removed obsolete implementation class in StreamUtils in favor of a lambda.
Streamable now exposes map(…), flatMap(…) and filter(…) to allow easy conversion into new Streamables. Introduced LazyStreamable to back those implementations. Simplified implementation of methods in PartTree to use those new methods.
Changed Page and Slice map(…) method to take a Function over a Converter so that act as specialization of the newly introduced map(…) method.
Make use of lambdas and method references though out the codebase. Remove no longer required generic type parameters.
Additionally remove unused imports and replace single element list initialization with dedicated singletonList.
Use Assertion overloads taking Supplier for dynamic assertion error messages.
Re added PropertyDescriptor collection. Looks like the method got dropped during one of the rebase operations.
Additionally make use of .distinct() name collection in tests as descriptors might appear multiple times for the same property name.