Drop `@CollectionClassificationType`;
Drop `@CollectionSemantics`; Drop `@CollectionSemanticsRegistration(s)`; Add `@CollectionTypeRegistration(s)`; Rename `@CustomType` to `@Type`; User Guide and Migration Guide changes
This commit is contained in:
parent
b8d26f829e
commit
448d678fb5
|
@ -32,6 +32,8 @@ Hibernate supports using the following integrations as managed beans:
|
|||
* `org.hibernate.type.descriptor.jdbc.JdbcType`
|
||||
* `org.hibernate.type.descriptor.java.BasicJavaType`
|
||||
* `org.hibernate.type.descriptor.java.MutabilityPlan`
|
||||
* `org.hibernate.usertype.UserType`
|
||||
* `org.hibernate.usertype.UserCollectionType`
|
||||
* `org.hibernate.metamodel.EmbeddableInstantiator`
|
||||
* `org.hibernate.envers.RevisionListener`
|
||||
* `org.hibernate.id.IdentifierGenerator`{fn-cdi-availability}
|
||||
|
|
|
@ -1532,17 +1532,17 @@ See <<basic-type-contributor>> for an alternative to `@JavaTypeRegistration` and
|
|||
[[basic-mapping-custom]]
|
||||
==== Custom type mapping
|
||||
|
||||
Another approach is to supply the implementation of the `org.hibernate.usertype.UserType` contract using `@CustomType`.
|
||||
Another approach is to supply the implementation of the `org.hibernate.usertype.UserType` contract using `@Type`.
|
||||
|
||||
There are also corresponding, specialized forms of `@CustomType` for specific model parts:
|
||||
There are also corresponding, specialized forms of `@Type` for specific model parts:
|
||||
|
||||
* When mapping a Map, `@CustomType` describes the Map value while `@MapKeyCustomType` describe the Map key
|
||||
* When mapping a List or array, `@CustomType` describes the elements while `@ListIndexCustomType` describes the index
|
||||
* When mapping an id-bag, `@CustomType` describes the elements while `@CollectionIdCustomType` describes the collection-id
|
||||
* For other collection mappings, `@CustomType` describes the elements
|
||||
* For discriminated association mappings (`@Any` and `@ManyToAny`), `@CustomType` describes the discriminator value
|
||||
* When mapping a Map, `@Type` describes the Map value while `@MapKeyCustomType` describe the Map key
|
||||
* When mapping a List or array, `@Type` describes the elements while `@ListIndexCustomType` describes the index
|
||||
* When mapping an id-bag, `@Type` describes the elements while `@CollectionIdCustomType` describes the collection-id
|
||||
* For other collection mappings, `@Type` describes the elements
|
||||
* For discriminated association mappings (`@Any` and `@ManyToAny`), `@Type` describes the discriminator value
|
||||
|
||||
`@UserType` allows for more complex mapping concerns; but, <<basic-jpa-convert,AttributeConverter> and
|
||||
`@Type` allows for more complex mapping concerns; but, <<basic-jpa-convert,AttributeConverter> and
|
||||
<<basic-mapping-composition>> should generally be preferred as simpler solutions
|
||||
|
||||
[[basic-nationalized]]
|
||||
|
|
|
@ -237,7 +237,7 @@ Some apps map BAG collections using `java.util.List` instead. Hibernate provide
|
|||
lists as bags. First an explicit annotation
|
||||
|
||||
[[collection-bag-list-ex]]
|
||||
.List as BAG
|
||||
.@Bag
|
||||
====
|
||||
[source, JAVA, indent=0]
|
||||
----
|
||||
|
@ -245,11 +245,11 @@ include::{classificationTestsDir}/bag/EntityWithBagAsList.java[tags=collections-
|
|||
----
|
||||
====
|
||||
|
||||
Specifically, the usage of `@CollectionClassificationType(BAG)` forces the interpretation to
|
||||
BAG. See <<collection-classification-ann>> for details on using `@CollectionClassificationType`.
|
||||
Specifically, the usage of `@Bag` forces the classification as BAG. Even though the `names` attribute is defined
|
||||
as `List`, Hibernate will treat it using the BAG semantics.
|
||||
|
||||
Additionally, as discussed in <<collection-list>>, the `hibernate.mapping.default_list_semantics` setting
|
||||
is available to have Hibernate interpret a `List` with no `@OrderColumn` as a BAG.
|
||||
is available to have Hibernate interpret a `List` with no `@OrderColumn` and no `@ListIndexBase` as a BAG.
|
||||
|
||||
|
||||
An ID_BAG is similar to a BAG, except that it maps a generated, per-row identifier into the collection
|
||||
|
@ -380,118 +380,16 @@ Id:: the identifier for an ID_BAG
|
|||
// todo (6.0) - finish
|
||||
|
||||
|
||||
[[collection-semantics-influence]]
|
||||
==== Influencing CollectionSemantics
|
||||
|
||||
Hibernate provides multiple ways to influence the `CollectionSemantics used to
|
||||
map any particular plural attribute:
|
||||
|
||||
1. <<collection-classification-ann, @CollectionClassificationType>>
|
||||
2. <<collection-semantics-ann, @CollectionSemantics>>
|
||||
3. <<collection-type-ann>>
|
||||
|
||||
|
||||
|
||||
[[collection-classification-ann]]
|
||||
===== @CollectionClassificationType
|
||||
|
||||
`@CollectionClassificationType` allows directly telling Hibernate which semantics to use
|
||||
through its classification.
|
||||
|
||||
For example, as discussed in <<collection-bag>>, Hibernate will map a `java.util.Collection`
|
||||
using BAG semantics by default.
|
||||
|
||||
As seen in <<collection-bag-list-ex>>, we can use the `@CollectionClassificationType`
|
||||
annotation to request it handled using a different semantic - there LIST.
|
||||
|
||||
In fact, we can use this technique with any of the classifications as long
|
||||
as the attribute's declared type on the domain model is assignable from the type
|
||||
implied by the semantic associated with the classification. The most common case where
|
||||
this would be useful is when exposing a plural attribute using `java.util.Collection` but
|
||||
telling Hibernate to use a semantic other than BAG. E.g., to use SET semantics for a
|
||||
`java.util.Collection`
|
||||
|
||||
|
||||
[[collection-bag-set-ex]]
|
||||
.Collection as SET
|
||||
====
|
||||
[source, JAVA, indent=0]
|
||||
----
|
||||
include::{classificationTestsDir}/explicit/EntityWithExplicitSetClassification.java[tags=collections-bag-set-ex]
|
||||
----
|
||||
====
|
||||
|
||||
|
||||
[[collection-semantics-ann]]
|
||||
===== @CollectionSemantics
|
||||
|
||||
Applications can also use the `@CollectionSemantics` annotation to specify a custom
|
||||
link:{javadoc-base}/org/hibernate/collection/spi/CollectionSemantics.html[`org.hibernate.collection.spi.CollectionSemantics`]
|
||||
implementation to use for the plural attribute.
|
||||
|
||||
As an example, consider a requirement for a collection with the semantics of a "unique list" - a
|
||||
cross between the ordered-ness of a `List` and the uniqueness of a `Set`. First the entity:
|
||||
|
||||
|
||||
[[collection-semantics-ann-ex]]
|
||||
.@CollectionSemantics
|
||||
====
|
||||
[source, JAVA, indent=0]
|
||||
----
|
||||
include::{coreCollectionTestsDir}/semantics/TheEntityWithUniqueList.java[tags=collections-custom-semantics-ex]
|
||||
----
|
||||
====
|
||||
|
||||
The mapping specifies that a custom `UniqueListSemantic` should be used as the `CollectionSemantics` for the
|
||||
`strings` attribute.
|
||||
|
||||
|
||||
[[collection-semantics-ann-impl-ex]]
|
||||
.@CollectionSemantics
|
||||
====
|
||||
[source, JAVA, indent=0]
|
||||
----
|
||||
include::{coreCollectionTestsDir}/semantics/UniqueListSemantic.java[tags=collections-custom-semantics-ex]
|
||||
----
|
||||
====
|
||||
|
||||
`UniqueListSemantic` defines the actual semantics of what a unique list is and how Hibernate should handle it.
|
||||
|
||||
See the `CollectionSemantics` link:{javadoc-base}/org/hibernate/collection/spi/CollectionSemantics.html[javadoc] for
|
||||
details.
|
||||
|
||||
|
||||
[[collection-semantics-ann-wrapper-ex]]
|
||||
.PersistentCollection
|
||||
====
|
||||
[source, JAVA, indent=0]
|
||||
----
|
||||
include::{coreCollectionTestsDir}/semantics/UniqueListWrapper.java[tags=collections-custom-semantics-ex]
|
||||
----
|
||||
====
|
||||
|
||||
Most custom `CollectionSemantics` will need their own `PersistentCollection` implementation.
|
||||
`UniqueListWrapper` is the `PersistentCollection` implementation for the "unique list" semantic.
|
||||
See <<collection-wrapper>> for more details.
|
||||
|
||||
|
||||
For cases where an application wants to apply the same custom semantic to all
|
||||
plural attributes of a given classification, Hibernate also provides the
|
||||
`@CollectionSemanticsRegistration`:
|
||||
|
||||
// todo (6.0) - example of using `@CollectionSemanticsRegistration`
|
||||
|
||||
|
||||
[[collection-type-ann]]
|
||||
===== @CollectionType
|
||||
==== @CollectionType
|
||||
|
||||
The `@CollectionType` annotation provides the ability to use a custom
|
||||
link:{javadoc-base}/org/hibernate/usertype/UserCollectionType.html[`UserCollectionType`]
|
||||
implementation.
|
||||
implementation to influence how the collection for a plural attribute behaves.
|
||||
|
||||
Let's revisit the requirement of needing a unique list that was used
|
||||
in <<collection-semantics-ann>> and see how to implement the same behavior using
|
||||
`UserCollectionType`.
|
||||
As an example, consider a requirement for a collection with the semantics of a "unique list" - a
|
||||
cross between the ordered-ness of a `List` and the uniqueness of a `Set`. First the entity:
|
||||
|
||||
|
||||
[[collection-type-ann-ex]]
|
||||
|
@ -499,7 +397,7 @@ in <<collection-semantics-ann>> and see how to implement the same behavior using
|
|||
====
|
||||
[source, JAVA, indent=0]
|
||||
----
|
||||
include::{coreCollectionTestsDir}/semantics/AnotherEntityWithUniqueList.java[tags=collections-custom-type-ex]
|
||||
include::{coreCollectionTestsDir}/semantics/TheEntityWithUniqueList.java[tags=ex-collections-custom-type-model]
|
||||
----
|
||||
====
|
||||
|
||||
|
@ -514,6 +412,30 @@ include::{coreCollectionTestsDir}/semantics/UniqueListType.java[tags=collections
|
|||
----
|
||||
====
|
||||
|
||||
Most custom `UserCollectionType` implementations will want their own `PersistentCollection` implementation.
|
||||
|
||||
[[collection-type-usertype-wrapper-ex]]
|
||||
.UniqueListWrapper
|
||||
====
|
||||
[source, JAVA, indent=0]
|
||||
----
|
||||
include::{coreCollectionTestsDir}/semantics/UniqueListWrapper.java[tags=collections-custom-semantics-ex]
|
||||
----
|
||||
====
|
||||
|
||||
`UniqueListWrapper` is the `PersistentCollection` implementation for the "unique list" semantic. See <<collection-wrapper>> for more details.
|
||||
|
||||
|
||||
For cases where an application wants to apply the same custom type to all
|
||||
plural attributes of a given classification, Hibernate also provides the
|
||||
`@CollectionTypeRegistration`:
|
||||
|
||||
// todo (6.0) - example of using `@CollectionTypeRegistration`
|
||||
|
||||
|
||||
[[collection-type-reg-ann]]
|
||||
==== @CollectionTypeRegistration
|
||||
|
||||
|
||||
|
||||
[[collection-wrapper]]
|
||||
|
|
|
@ -15,11 +15,21 @@ import java.util.Queue;
|
|||
import org.hibernate.HibernateException;
|
||||
import org.hibernate.collection.spi.PersistentCollection;
|
||||
import org.hibernate.engine.spi.SharedSessionContractImplementor;
|
||||
import org.hibernate.metamodel.CollectionClassification;
|
||||
import org.hibernate.persister.collection.CollectionPersister;
|
||||
import org.hibernate.usertype.UserCollectionType;
|
||||
|
||||
//tag::collections-custom-collection-mapping-example[]
|
||||
public class QueueType implements UserCollectionType {
|
||||
@Override
|
||||
public CollectionClassification getClassification() {
|
||||
return CollectionClassification.BAG;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Class<?> getCollectionClass() {
|
||||
return Queue.class;
|
||||
}
|
||||
|
||||
@Override
|
||||
public PersistentCollection instantiate(
|
||||
|
|
|
@ -6,7 +6,7 @@
|
|||
*/
|
||||
package org.hibernate.userguide.mapping.basic;
|
||||
|
||||
import org.hibernate.annotations.CustomType;
|
||||
import org.hibernate.annotations.Type;
|
||||
import org.hibernate.orm.test.jpa.BaseEntityManagerFunctionalTestCase;
|
||||
|
||||
import org.junit.Test;
|
||||
|
@ -48,7 +48,7 @@ public class EnumerationCustomTypeTest extends BaseEntityManagerFunctionalTestCa
|
|||
|
||||
private String name;
|
||||
|
||||
@CustomType(org.hibernate.userguide.mapping.basic.GenderType.class)
|
||||
@Type(org.hibernate.userguide.mapping.basic.GenderType.class)
|
||||
public Gender gender;
|
||||
|
||||
//Getters and setters are omitted for brevity
|
||||
|
|
|
@ -9,7 +9,7 @@ package org.hibernate.userguide.mapping.basic;
|
|||
import jakarta.persistence.Entity;
|
||||
import jakarta.persistence.Id;
|
||||
|
||||
import org.hibernate.annotations.CustomType;
|
||||
import org.hibernate.annotations.Type;
|
||||
import org.hibernate.annotations.Parameter;
|
||||
import org.hibernate.orm.test.jpa.BaseEntityManagerFunctionalTestCase;
|
||||
import org.hibernate.usertype.UserTypeLegacyBridge;
|
||||
|
@ -46,13 +46,13 @@ public class ExplicitTypeTest extends BaseEntityManagerFunctionalTestCase {
|
|||
|
||||
private String sku;
|
||||
|
||||
@CustomType(
|
||||
@Type(
|
||||
value = UserTypeLegacyBridge.class,
|
||||
parameters = @Parameter(name = UserTypeLegacyBridge.TYPE_NAME_PARAM_KEY, value = "nstring")
|
||||
)
|
||||
private String name;
|
||||
|
||||
@CustomType(
|
||||
@Type(
|
||||
value = UserTypeLegacyBridge.class,
|
||||
parameters = @Parameter(name = UserTypeLegacyBridge.TYPE_NAME_PARAM_KEY, value = "materialized_nclob")
|
||||
)
|
||||
|
|
|
@ -8,7 +8,7 @@ package org.hibernate.userguide.mapping.basic.bitset;
|
|||
|
||||
import java.util.BitSet;
|
||||
|
||||
import org.hibernate.annotations.CustomType;
|
||||
import org.hibernate.annotations.Type;
|
||||
|
||||
import org.hibernate.testing.junit4.BaseCoreFunctionalTestCase;
|
||||
import org.junit.Test;
|
||||
|
@ -107,7 +107,7 @@ public class BitSetUserTypeTest extends BaseCoreFunctionalTestCase {
|
|||
@Id
|
||||
private Integer id;
|
||||
|
||||
@CustomType(BitSetUserType.class)
|
||||
@Type(BitSetUserType.class)
|
||||
@Column(name = "bitset_col")
|
||||
private BitSet bitSet;
|
||||
|
||||
|
|
|
@ -14,14 +14,15 @@ import static java.lang.annotation.ElementType.METHOD;
|
|||
import static java.lang.annotation.RetentionPolicy.RUNTIME;
|
||||
|
||||
/**
|
||||
* Specifies a custom {@link org.hibernate.collection.spi.CollectionSemantics}
|
||||
* Can be used to map a {@link java.util.List}-valued attribute using
|
||||
* {@link org.hibernate.metamodel.CollectionClassification#BAG} semantics.
|
||||
*
|
||||
* @since 6.0
|
||||
* @apiNote Ignored if either {@link jakarta.persistence.OrderColumn} or
|
||||
* {@link ListIndexBase} is used.
|
||||
*
|
||||
* @author Steve Ebersole
|
||||
*/
|
||||
@java.lang.annotation.Target({METHOD, FIELD, ANNOTATION_TYPE})
|
||||
@Retention(RUNTIME)
|
||||
public @interface CollectionSemantics {
|
||||
Class<? extends org.hibernate.collection.spi.CollectionSemantics> value();
|
||||
public @interface Bag {
|
||||
}
|
|
@ -1,27 +0,0 @@
|
|||
/*
|
||||
* Hibernate, Relational Persistence for Idiomatic Java
|
||||
*
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later
|
||||
* See the lgpl.txt file in the root directory or http://www.gnu.org/licenses/lgpl-2.1.html
|
||||
*/
|
||||
package org.hibernate.annotations;
|
||||
|
||||
import java.lang.annotation.Retention;
|
||||
|
||||
import org.hibernate.metamodel.CollectionClassification;
|
||||
|
||||
import static java.lang.annotation.ElementType.ANNOTATION_TYPE;
|
||||
import static java.lang.annotation.ElementType.FIELD;
|
||||
import static java.lang.annotation.ElementType.METHOD;
|
||||
import static java.lang.annotation.RetentionPolicy.RUNTIME;
|
||||
|
||||
/**
|
||||
* @since 6.0
|
||||
*
|
||||
* @author Steve Ebersole
|
||||
*/
|
||||
@java.lang.annotation.Target({METHOD, FIELD, ANNOTATION_TYPE})
|
||||
@Retention(RUNTIME)
|
||||
public @interface CollectionClassificationType {
|
||||
CollectionClassification value();
|
||||
}
|
|
@ -15,7 +15,7 @@ import static java.lang.annotation.ElementType.METHOD;
|
|||
import static java.lang.annotation.RetentionPolicy.RUNTIME;
|
||||
|
||||
/**
|
||||
* Form of {@link CustomType} for describing the id of an id-bag mapping
|
||||
* Form of {@link Type} for describing the id of an id-bag mapping
|
||||
*
|
||||
* @since 6.0
|
||||
*/
|
||||
|
@ -26,7 +26,7 @@ public @interface CollectionIdCustomType {
|
|||
/**
|
||||
* The custom type implementor class
|
||||
*
|
||||
* @see CustomType#value
|
||||
* @see Type#value
|
||||
*/
|
||||
Class<? extends UserType<?>> value();
|
||||
|
||||
|
@ -37,7 +37,7 @@ public @interface CollectionIdCustomType {
|
|||
* The type should implement {@link org.hibernate.usertype.ParameterizedType}
|
||||
* to receive the parameters
|
||||
*
|
||||
* @see CustomType#parameters
|
||||
* @see Type#parameters
|
||||
*/
|
||||
Parameter[] parameters() default {};
|
||||
}
|
||||
|
|
|
@ -1,45 +0,0 @@
|
|||
/*
|
||||
* Hibernate, Relational Persistence for Idiomatic Java
|
||||
*
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later
|
||||
* See the lgpl.txt file in the root directory or http://www.gnu.org/licenses/lgpl-2.1.html
|
||||
*/
|
||||
package org.hibernate.annotations;
|
||||
|
||||
import java.lang.annotation.Repeatable;
|
||||
import java.lang.annotation.Retention;
|
||||
|
||||
import org.hibernate.metamodel.CollectionClassification;
|
||||
|
||||
import static java.lang.annotation.ElementType.ANNOTATION_TYPE;
|
||||
import static java.lang.annotation.ElementType.FIELD;
|
||||
import static java.lang.annotation.ElementType.METHOD;
|
||||
import static java.lang.annotation.RetentionPolicy.RUNTIME;
|
||||
|
||||
/**
|
||||
* Allows to register a {@link org.hibernate.collection.spi.CollectionSemantics}
|
||||
* to use as the default for the specified classification of collection.
|
||||
*
|
||||
* @see CollectionClassificationType
|
||||
* @see CollectionSemantics
|
||||
* @see org.hibernate.collection.spi.CollectionSemantics
|
||||
*
|
||||
* @since 6.0
|
||||
*
|
||||
* @author Steve Ebersole
|
||||
*/
|
||||
@java.lang.annotation.Target({METHOD, FIELD, ANNOTATION_TYPE})
|
||||
@Retention(RUNTIME)
|
||||
@Repeatable( CollectionSemanticsRegistrations.class )
|
||||
public @interface CollectionSemanticsRegistration {
|
||||
/**
|
||||
* The collection classification for which the supplied semantic applies
|
||||
*/
|
||||
CollectionClassification classification();
|
||||
|
||||
/**
|
||||
* The semantic to apply. Will be applied to all collections of the given
|
||||
* classification which do not define an explicit {@link org.hibernate.collection.spi.CollectionSemantics}
|
||||
*/
|
||||
Class<? extends org.hibernate.collection.spi.CollectionSemantics<?,?>> semantics();
|
||||
}
|
|
@ -29,18 +29,6 @@ public @interface CollectionType {
|
|||
*/
|
||||
Class<? extends UserCollectionType> type();
|
||||
|
||||
/**
|
||||
* Specifies the class to use the semantics of.
|
||||
*
|
||||
* For example, specifying {@link java.util.Set} will use Set semantics.
|
||||
*
|
||||
* When not specified, will be inferred from the interfaces on the property
|
||||
* as long as it extends a standard {@link java.util.Collection} or {@link java.util.Map}.
|
||||
*
|
||||
* @return the class to use the semantics of.
|
||||
*/
|
||||
Class<?> semantics() default void.class;
|
||||
|
||||
/**
|
||||
* Specifies configuration information for the type. Note that if the named type is a
|
||||
* {@link org.hibernate.usertype.UserCollectionType}, it must also implement
|
||||
|
|
|
@ -0,0 +1,53 @@
|
|||
/*
|
||||
* Hibernate, Relational Persistence for Idiomatic Java
|
||||
*
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later
|
||||
* See the lgpl.txt file in the root directory or http://www.gnu.org/licenses/lgpl-2.1.html
|
||||
*/
|
||||
package org.hibernate.annotations;
|
||||
|
||||
import java.lang.annotation.Repeatable;
|
||||
import java.lang.annotation.Retention;
|
||||
|
||||
import org.hibernate.metamodel.CollectionClassification;
|
||||
import org.hibernate.usertype.UserCollectionType;
|
||||
|
||||
import static java.lang.annotation.ElementType.ANNOTATION_TYPE;
|
||||
import static java.lang.annotation.ElementType.FIELD;
|
||||
import static java.lang.annotation.ElementType.METHOD;
|
||||
import static java.lang.annotation.ElementType.PACKAGE;
|
||||
import static java.lang.annotation.ElementType.TYPE;
|
||||
import static java.lang.annotation.RetentionPolicy.RUNTIME;
|
||||
|
||||
/**
|
||||
* Allows to register a {@link org.hibernate.usertype.UserCollectionType}
|
||||
* to use as the default for the specified classification of collection.
|
||||
*
|
||||
* @see CollectionType
|
||||
*
|
||||
* @since 6.0
|
||||
*
|
||||
* @author Steve Ebersole
|
||||
*/
|
||||
@java.lang.annotation.Target({TYPE, PACKAGE, ANNOTATION_TYPE})
|
||||
@Retention(RUNTIME)
|
||||
@Repeatable( CollectionTypeRegistrations.class )
|
||||
public @interface CollectionTypeRegistration {
|
||||
/**
|
||||
* The collection classification for which the supplied type applies
|
||||
*/
|
||||
CollectionClassification classification();
|
||||
|
||||
/**
|
||||
* Specifies the UserCollectionType to use when we encounter
|
||||
* a plural attribute classified as {@link #classification()}
|
||||
*/
|
||||
Class<? extends UserCollectionType> type();
|
||||
|
||||
/**
|
||||
* Specifies configuration information for the type. Note that if the named type is a
|
||||
* {@link org.hibernate.usertype.UserCollectionType}, it must also implement
|
||||
* {@link org.hibernate.usertype.ParameterizedType} in order to receive these values.
|
||||
*/
|
||||
Parameter[] parameters() default {};
|
||||
}
|
|
@ -11,20 +11,21 @@ import java.lang.annotation.Retention;
|
|||
import static java.lang.annotation.ElementType.ANNOTATION_TYPE;
|
||||
import static java.lang.annotation.ElementType.FIELD;
|
||||
import static java.lang.annotation.ElementType.METHOD;
|
||||
import static java.lang.annotation.ElementType.TYPE;
|
||||
import static java.lang.annotation.RetentionPolicy.RUNTIME;
|
||||
|
||||
/**
|
||||
* Repeatable container for {@link CollectionSemanticsRegistration}
|
||||
* Repeatable container for {@link CollectionTypeRegistration}
|
||||
*
|
||||
* @since 6.0
|
||||
*
|
||||
* @author Steve Ebersole
|
||||
*/
|
||||
@java.lang.annotation.Target({METHOD, FIELD, ANNOTATION_TYPE})
|
||||
@java.lang.annotation.Target({TYPE, ANNOTATION_TYPE})
|
||||
@Retention(RUNTIME)
|
||||
public @interface CollectionSemanticsRegistrations {
|
||||
public @interface CollectionTypeRegistrations {
|
||||
/**
|
||||
* The individual CollectionSemanticsRegistrations
|
||||
* The individual CollectionTypeRegistration
|
||||
*/
|
||||
CollectionSemanticsRegistration[] value();
|
||||
CollectionTypeRegistration[] value();
|
||||
}
|
|
@ -9,7 +9,7 @@ package org.hibernate.annotations;
|
|||
import org.hibernate.usertype.UserType;
|
||||
|
||||
/**
|
||||
* Form of {@link CustomType} for use with map-keys
|
||||
* Form of {@link Type} for use with map-keys
|
||||
*
|
||||
* @since 6.0
|
||||
*/
|
||||
|
@ -17,14 +17,14 @@ public @interface MapKeyCustomType {
|
|||
/**
|
||||
* The custom type implementor class
|
||||
*
|
||||
* @see CustomType#value
|
||||
* @see Type#value
|
||||
*/
|
||||
Class<? extends UserType<?>> value();
|
||||
|
||||
/**
|
||||
* Parameters for the custom type
|
||||
*
|
||||
* @see CustomType#parameters
|
||||
* @see Type#parameters
|
||||
*/
|
||||
Parameter[] parameters() default {};
|
||||
}
|
||||
|
|
|
@ -22,7 +22,7 @@ import static java.lang.annotation.RetentionPolicy.RUNTIME;
|
|||
*/
|
||||
@java.lang.annotation.Target({METHOD, FIELD})
|
||||
@Retention(RUNTIME)
|
||||
public @interface CustomType {
|
||||
public @interface Type {
|
||||
|
||||
/**
|
||||
* The custom type implementor class
|
|
@ -31,7 +31,7 @@
|
|||
* </li>
|
||||
* <li>
|
||||
* Contracted via the {@link org.hibernate.usertype.UserType} interface and specified using
|
||||
* {@link org.hibernate.annotations.CustomType}.
|
||||
* {@link org.hibernate.annotations.Type}.
|
||||
* As with the compositional approach, there are model-part specific annotations for specifying
|
||||
* custom-types as well.
|
||||
* </li>
|
||||
|
|
|
@ -15,6 +15,7 @@ import java.util.Iterator;
|
|||
import java.util.List;
|
||||
import java.util.Locale;
|
||||
import java.util.Map;
|
||||
import java.util.Properties;
|
||||
import java.util.Set;
|
||||
import java.util.UUID;
|
||||
import java.util.concurrent.ConcurrentHashMap;
|
||||
|
@ -27,6 +28,8 @@ import org.hibernate.DuplicateMappingException;
|
|||
import org.hibernate.HibernateException;
|
||||
import org.hibernate.MappingException;
|
||||
import org.hibernate.SessionFactory;
|
||||
import org.hibernate.annotations.CollectionTypeRegistration;
|
||||
import org.hibernate.annotations.Parameter;
|
||||
import org.hibernate.annotations.common.reflection.XClass;
|
||||
import org.hibernate.boot.CacheRegionDefinition;
|
||||
import org.hibernate.boot.SessionFactoryBuilder;
|
||||
|
@ -54,6 +57,7 @@ import org.hibernate.boot.query.NamedProcedureCallDefinition;
|
|||
import org.hibernate.boot.query.NamedResultSetMappingDescriptor;
|
||||
import org.hibernate.boot.spi.BootstrapContext;
|
||||
import org.hibernate.boot.spi.InFlightMetadataCollector;
|
||||
import org.hibernate.boot.spi.InFlightMetadataCollector.CollectionTypeRegistrationDescriptor;
|
||||
import org.hibernate.boot.spi.MetadataBuildingContext;
|
||||
import org.hibernate.boot.spi.MetadataBuildingOptions;
|
||||
import org.hibernate.boot.spi.NaturalIdUniqueKeyBinder;
|
||||
|
@ -95,12 +99,14 @@ import org.hibernate.mapping.RootClass;
|
|||
import org.hibernate.mapping.SimpleValue;
|
||||
import org.hibernate.mapping.Table;
|
||||
import org.hibernate.mapping.UniqueKey;
|
||||
import org.hibernate.metamodel.CollectionClassification;
|
||||
import org.hibernate.metamodel.EmbeddableInstantiator;
|
||||
import org.hibernate.query.named.NamedObjectRepository;
|
||||
import org.hibernate.query.sqm.function.SqmFunctionDescriptor;
|
||||
import org.hibernate.type.descriptor.java.JavaType;
|
||||
import org.hibernate.type.descriptor.jdbc.JdbcType;
|
||||
import org.hibernate.type.spi.TypeConfiguration;
|
||||
import org.hibernate.usertype.UserCollectionType;
|
||||
|
||||
import jakarta.persistence.AttributeConverter;
|
||||
import jakarta.persistence.Embeddable;
|
||||
|
@ -407,6 +413,48 @@ public class InFlightMetadataCollectorImpl implements InFlightMetadataCollector
|
|||
return registeredInstantiators.get( embeddableType );
|
||||
}
|
||||
|
||||
private Map<CollectionClassification, CollectionTypeRegistrationDescriptor> collectionTypeRegistrations;
|
||||
|
||||
|
||||
@Override
|
||||
public void addCollectionTypeRegistration(CollectionTypeRegistration registrationAnnotation) {
|
||||
addCollectionTypeRegistration(
|
||||
registrationAnnotation.classification(),
|
||||
toDescriptor( registrationAnnotation )
|
||||
);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void addCollectionTypeRegistration(CollectionClassification classification, CollectionTypeRegistrationDescriptor descriptor) {
|
||||
if ( collectionTypeRegistrations == null ) {
|
||||
collectionTypeRegistrations = new HashMap<>();
|
||||
}
|
||||
collectionTypeRegistrations.put( classification, descriptor );
|
||||
}
|
||||
|
||||
@Override
|
||||
public CollectionTypeRegistrationDescriptor findCollectionTypeRegistration(CollectionClassification classification) {
|
||||
if ( collectionTypeRegistrations == null ) {
|
||||
return null;
|
||||
}
|
||||
|
||||
return collectionTypeRegistrations.get( classification );
|
||||
}
|
||||
|
||||
private CollectionTypeRegistrationDescriptor toDescriptor(CollectionTypeRegistration registrationAnnotation) {
|
||||
final Properties parameters;
|
||||
if ( registrationAnnotation.parameters().length > 0 ) {
|
||||
parameters = new Properties();
|
||||
for ( Parameter parameter : registrationAnnotation.parameters() ) {
|
||||
parameters.put( parameter.name(), parameter.value() );
|
||||
}
|
||||
}
|
||||
else {
|
||||
parameters = null;
|
||||
}
|
||||
return new CollectionTypeRegistrationDescriptor( registrationAnnotation.type(), parameters );
|
||||
}
|
||||
|
||||
|
||||
// ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
||||
// attribute converters
|
||||
|
|
|
@ -10,11 +10,13 @@ import java.io.Serializable;
|
|||
import java.util.List;
|
||||
import java.util.Locale;
|
||||
import java.util.Map;
|
||||
import java.util.Properties;
|
||||
import java.util.function.Function;
|
||||
|
||||
import org.hibernate.DuplicateMappingException;
|
||||
import org.hibernate.HibernateException;
|
||||
import org.hibernate.MappingException;
|
||||
import org.hibernate.annotations.CollectionTypeRegistration;
|
||||
import org.hibernate.annotations.common.reflection.XClass;
|
||||
import org.hibernate.boot.internal.ClassmateContext;
|
||||
import org.hibernate.boot.internal.NamedProcedureCallDefinitionImpl;
|
||||
|
@ -49,9 +51,11 @@ import org.hibernate.mapping.Join;
|
|||
import org.hibernate.mapping.MappedSuperclass;
|
||||
import org.hibernate.mapping.PersistentClass;
|
||||
import org.hibernate.mapping.Table;
|
||||
import org.hibernate.metamodel.CollectionClassification;
|
||||
import org.hibernate.metamodel.EmbeddableInstantiator;
|
||||
import org.hibernate.type.descriptor.java.JavaType;
|
||||
import org.hibernate.type.descriptor.jdbc.JdbcType;
|
||||
import org.hibernate.usertype.UserCollectionType;
|
||||
|
||||
import jakarta.persistence.AttributeConverter;
|
||||
|
||||
|
@ -323,6 +327,10 @@ public interface InFlightMetadataCollector extends Mapping, MetadataImplementor
|
|||
void registerEmbeddableInstantiator(Class<?> embeddableType, Class<? extends EmbeddableInstantiator> instantiator);
|
||||
Class<? extends EmbeddableInstantiator> findRegisteredEmbeddableInstantiator(Class<?> embeddableType);
|
||||
|
||||
void addCollectionTypeRegistration(CollectionTypeRegistration registrationAnnotation);
|
||||
void addCollectionTypeRegistration(CollectionClassification classification, CollectionTypeRegistrationDescriptor descriptor);
|
||||
CollectionTypeRegistrationDescriptor findCollectionTypeRegistration(CollectionClassification classification);
|
||||
|
||||
interface DelayedPropertyReferenceHandler extends Serializable {
|
||||
void process(InFlightMetadataCollector metadataCollector);
|
||||
}
|
||||
|
@ -371,4 +379,23 @@ public interface InFlightMetadataCollector extends Mapping, MetadataImplementor
|
|||
Table primaryTable,
|
||||
EntityTableXref superEntityTableXref);
|
||||
Map<String,Join> getJoins(String entityName);
|
||||
|
||||
|
||||
class CollectionTypeRegistrationDescriptor {
|
||||
private final Class<? extends UserCollectionType> implementation;
|
||||
private final Properties parameters;
|
||||
|
||||
public CollectionTypeRegistrationDescriptor(Class<? extends UserCollectionType> implementation, Properties parameters) {
|
||||
this.implementation = implementation;
|
||||
this.parameters = parameters;
|
||||
}
|
||||
|
||||
public Class<? extends UserCollectionType> getImplementation() {
|
||||
return implementation;
|
||||
}
|
||||
|
||||
public Properties getParameters() {
|
||||
return parameters;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -19,7 +19,6 @@ import java.util.Iterator;
|
|||
import java.util.List;
|
||||
import java.util.Locale;
|
||||
import java.util.Map;
|
||||
import java.util.Properties;
|
||||
import java.util.Set;
|
||||
|
||||
import org.hibernate.AnnotationException;
|
||||
|
@ -33,6 +32,8 @@ import org.hibernate.annotations.Cascade;
|
|||
import org.hibernate.annotations.CascadeType;
|
||||
import org.hibernate.annotations.Check;
|
||||
import org.hibernate.annotations.CollectionId;
|
||||
import org.hibernate.annotations.CollectionTypeRegistration;
|
||||
import org.hibernate.annotations.CollectionTypeRegistrations;
|
||||
import org.hibernate.annotations.Columns;
|
||||
import org.hibernate.annotations.Comment;
|
||||
import org.hibernate.annotations.DiscriminatorFormula;
|
||||
|
@ -873,16 +874,18 @@ public final class AnnotationBinder {
|
|||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private static Properties extractProperties(Parameter[] parameters) {
|
||||
final Properties properties = new Properties();
|
||||
if ( parameters.length > 0 ) {
|
||||
for ( int i = 0; i < parameters.length; i++ ) {
|
||||
properties.setProperty( parameters[i].name(), parameters[i].value() );
|
||||
final CollectionTypeRegistration singleRegistration = annotatedElement.getAnnotation( CollectionTypeRegistration.class );
|
||||
if ( singleRegistration != null ) {
|
||||
context.getMetadataCollector().addCollectionTypeRegistration( singleRegistration );
|
||||
}
|
||||
|
||||
final CollectionTypeRegistrations multiRegistration = annotatedElement.getAnnotation( CollectionTypeRegistrations.class );
|
||||
if ( multiRegistration != null ) {
|
||||
for ( CollectionTypeRegistration registration : multiRegistration.value() ) {
|
||||
context.getMetadataCollector().addCollectionTypeRegistration( registration );
|
||||
}
|
||||
}
|
||||
return properties;
|
||||
}
|
||||
|
||||
private static void handleSqlTypeDescriptorRegistration(
|
||||
|
|
|
@ -19,7 +19,7 @@ import java.util.Map;
|
|||
import java.util.TreeMap;
|
||||
|
||||
import org.hibernate.AnnotationException;
|
||||
import org.hibernate.annotations.CustomType;
|
||||
import org.hibernate.annotations.Type;
|
||||
import org.hibernate.annotations.JavaType;
|
||||
import org.hibernate.annotations.ManyToAny;
|
||||
import org.hibernate.annotations.Target;
|
||||
|
@ -385,7 +385,7 @@ class PropertyContainer {
|
|||
else if ( p.isAnnotationPresent( Basic.class ) ) {
|
||||
return true;
|
||||
}
|
||||
else if ( p.isAnnotationPresent( CustomType.class ) ) {
|
||||
else if ( p.isAnnotationPresent( Type.class ) ) {
|
||||
return true;
|
||||
}
|
||||
else if ( p.isAnnotationPresent( JavaType.class ) ) {
|
||||
|
|
|
@ -6,11 +6,15 @@
|
|||
*/
|
||||
package org.hibernate.cfg.annotations;
|
||||
|
||||
import java.util.function.Supplier;
|
||||
|
||||
import org.hibernate.boot.spi.MetadataBuildingContext;
|
||||
import org.hibernate.mapping.Array;
|
||||
import org.hibernate.mapping.Collection;
|
||||
import org.hibernate.mapping.PersistentClass;
|
||||
import org.hibernate.mapping.SemanticsResolver;
|
||||
import org.hibernate.resource.beans.spi.ManagedBean;
|
||||
import org.hibernate.usertype.UserCollectionType;
|
||||
|
||||
/**
|
||||
* Bind an Array
|
||||
|
@ -18,11 +22,11 @@ import org.hibernate.mapping.SemanticsResolver;
|
|||
* @author Anthony Patricio
|
||||
*/
|
||||
public class ArrayBinder extends ListBinder {
|
||||
public ArrayBinder(SemanticsResolver semanticsResolver, MetadataBuildingContext buildingContext) {
|
||||
super( semanticsResolver, buildingContext );
|
||||
public ArrayBinder(Supplier<ManagedBean<? extends UserCollectionType>> customTypeBeanResolver, MetadataBuildingContext buildingContext) {
|
||||
super( customTypeBeanResolver, buildingContext );
|
||||
}
|
||||
|
||||
protected Collection createCollection(PersistentClass owner) {
|
||||
return new Array( getSemanticsResolver(), owner, getBuildingContext() );
|
||||
return new Array( getCustomTypeBeanResolver(), owner, getBuildingContext() );
|
||||
}
|
||||
}
|
||||
|
|
|
@ -6,10 +6,14 @@
|
|||
*/
|
||||
package org.hibernate.cfg.annotations;
|
||||
|
||||
import java.util.function.Supplier;
|
||||
|
||||
import org.hibernate.boot.spi.MetadataBuildingContext;
|
||||
import org.hibernate.mapping.Collection;
|
||||
import org.hibernate.mapping.PersistentClass;
|
||||
import org.hibernate.mapping.SemanticsResolver;
|
||||
import org.hibernate.resource.beans.spi.ManagedBean;
|
||||
import org.hibernate.usertype.UserCollectionType;
|
||||
|
||||
/**
|
||||
* Bind a bag.
|
||||
|
@ -17,11 +21,11 @@ import org.hibernate.mapping.SemanticsResolver;
|
|||
* @author Matthew Inger
|
||||
*/
|
||||
public class BagBinder extends CollectionBinder {
|
||||
public BagBinder(SemanticsResolver semanticsResolver, MetadataBuildingContext context) {
|
||||
super( semanticsResolver, false, context );
|
||||
public BagBinder(Supplier<ManagedBean<? extends UserCollectionType>> customTypeBeanResolver, MetadataBuildingContext context) {
|
||||
super( customTypeBeanResolver, false, context );
|
||||
}
|
||||
|
||||
protected Collection createCollection(PersistentClass owner) {
|
||||
return new org.hibernate.mapping.Bag( getSemanticsResolver(), owner, getBuildingContext() );
|
||||
return new org.hibernate.mapping.Bag( getCustomTypeBeanResolver(), owner, getBuildingContext() );
|
||||
}
|
||||
}
|
||||
|
|
|
@ -31,7 +31,7 @@ import org.hibernate.annotations.CollectionIdJavaType;
|
|||
import org.hibernate.annotations.CollectionIdJdbcType;
|
||||
import org.hibernate.annotations.CollectionIdJdbcTypeCode;
|
||||
import org.hibernate.annotations.CollectionIdMutability;
|
||||
import org.hibernate.annotations.CustomType;
|
||||
import org.hibernate.annotations.Type;
|
||||
import org.hibernate.annotations.Immutable;
|
||||
import org.hibernate.annotations.JdbcTypeCode;
|
||||
import org.hibernate.annotations.ListIndexJavaType;
|
||||
|
@ -1434,7 +1434,7 @@ public class BasicValueBinder<T> implements JdbcTypeDescriptorIndicators {
|
|||
|
||||
@Override
|
||||
public Class<? extends UserType<?>> customType(XProperty xProperty) {
|
||||
final CustomType customType = findAnnotation( xProperty, CustomType.class );
|
||||
final Type customType = findAnnotation( xProperty, Type.class );
|
||||
if ( customType == null ) {
|
||||
return null;
|
||||
}
|
||||
|
@ -1444,7 +1444,7 @@ public class BasicValueBinder<T> implements JdbcTypeDescriptorIndicators {
|
|||
|
||||
@Override
|
||||
public Parameter[] customTypeParameters(XProperty xProperty) {
|
||||
final CustomType customType = findAnnotation( xProperty, CustomType.class );
|
||||
final Type customType = findAnnotation( xProperty, Type.class );
|
||||
if ( customType == null ) {
|
||||
return null;
|
||||
}
|
||||
|
|
|
@ -13,19 +13,19 @@ import java.util.List;
|
|||
import java.util.Locale;
|
||||
import java.util.Map;
|
||||
import java.util.Properties;
|
||||
import java.util.function.Supplier;
|
||||
|
||||
import org.hibernate.AnnotationException;
|
||||
import org.hibernate.AssertionFailure;
|
||||
import org.hibernate.FetchMode;
|
||||
import org.hibernate.MappingException;
|
||||
import org.hibernate.annotations.Bag;
|
||||
import org.hibernate.annotations.BatchSize;
|
||||
import org.hibernate.annotations.Cache;
|
||||
import org.hibernate.annotations.CollectionClassificationType;
|
||||
import org.hibernate.annotations.CollectionId;
|
||||
import org.hibernate.annotations.CollectionIdJavaType;
|
||||
import org.hibernate.annotations.CollectionIdJdbcType;
|
||||
import org.hibernate.annotations.CollectionIdJdbcTypeCode;
|
||||
import org.hibernate.annotations.CollectionSemantics;
|
||||
import org.hibernate.annotations.CollectionType;
|
||||
import org.hibernate.annotations.Fetch;
|
||||
import org.hibernate.annotations.Filter;
|
||||
|
@ -60,19 +60,22 @@ import org.hibernate.annotations.Where;
|
|||
import org.hibernate.annotations.WhereJoinTable;
|
||||
import org.hibernate.annotations.common.reflection.XClass;
|
||||
import org.hibernate.annotations.common.reflection.XProperty;
|
||||
import org.hibernate.boot.BootLogging;
|
||||
import org.hibernate.boot.model.IdentifierGeneratorDefinition;
|
||||
import org.hibernate.boot.model.TypeDefinition;
|
||||
import org.hibernate.boot.registry.StandardServiceRegistry;
|
||||
import org.hibernate.boot.spi.InFlightMetadataCollector;
|
||||
import org.hibernate.boot.spi.InFlightMetadataCollector.CollectionTypeRegistrationDescriptor;
|
||||
import org.hibernate.boot.spi.MetadataBuildingContext;
|
||||
import org.hibernate.cfg.AccessType;
|
||||
import org.hibernate.cfg.AnnotatedClassType;
|
||||
import org.hibernate.cfg.AnnotatedColumn;
|
||||
import org.hibernate.cfg.AnnotatedJoinColumn;
|
||||
import org.hibernate.cfg.AnnotationBinder;
|
||||
import org.hibernate.cfg.AvailableSettings;
|
||||
import org.hibernate.cfg.BinderHelper;
|
||||
import org.hibernate.cfg.CollectionPropertyHolder;
|
||||
import org.hibernate.cfg.CollectionSecondPass;
|
||||
import org.hibernate.cfg.AnnotatedColumn;
|
||||
import org.hibernate.cfg.AnnotatedJoinColumn;
|
||||
import org.hibernate.cfg.IndexColumn;
|
||||
import org.hibernate.cfg.InheritanceState;
|
||||
import org.hibernate.cfg.PropertyData;
|
||||
|
@ -81,11 +84,11 @@ import org.hibernate.cfg.PropertyHolderBuilder;
|
|||
import org.hibernate.cfg.PropertyInferredData;
|
||||
import org.hibernate.cfg.PropertyPreloadedData;
|
||||
import org.hibernate.cfg.SecondPass;
|
||||
import org.hibernate.collection.internal.CustomCollectionTypeSemantics;
|
||||
import org.hibernate.engine.config.spi.ConfigurationService;
|
||||
import org.hibernate.engine.spi.ExecuteUpdateResultCheckStyle;
|
||||
import org.hibernate.internal.CoreMessageLogger;
|
||||
import org.hibernate.internal.util.StringHelper;
|
||||
import org.hibernate.internal.util.collections.CollectionHelper;
|
||||
import org.hibernate.internal.util.config.ConfigurationHelper;
|
||||
import org.hibernate.mapping.Any;
|
||||
import org.hibernate.mapping.Backref;
|
||||
|
@ -99,13 +102,14 @@ import org.hibernate.mapping.ManyToOne;
|
|||
import org.hibernate.mapping.PersistentClass;
|
||||
import org.hibernate.mapping.Property;
|
||||
import org.hibernate.mapping.Selectable;
|
||||
import org.hibernate.mapping.SemanticsResolver;
|
||||
import org.hibernate.mapping.SimpleValue;
|
||||
import org.hibernate.mapping.Table;
|
||||
import org.hibernate.metamodel.CollectionClassification;
|
||||
import org.hibernate.metamodel.EmbeddableInstantiator;
|
||||
import org.hibernate.resource.beans.spi.ManagedBean;
|
||||
import org.hibernate.resource.beans.spi.ManagedBeanRegistry;
|
||||
import org.hibernate.usertype.ParameterizedType;
|
||||
import org.hibernate.usertype.UserCollectionType;
|
||||
|
||||
import org.jboss.logging.Logger;
|
||||
|
||||
|
@ -150,7 +154,7 @@ public abstract class CollectionBinder {
|
|||
);
|
||||
|
||||
private final MetadataBuildingContext buildingContext;
|
||||
private final SemanticsResolver semanticsResolver;
|
||||
private final Supplier<ManagedBean<? extends UserCollectionType>> customTypeBeanResolver;
|
||||
private final boolean isSortedCollection;
|
||||
|
||||
protected Collection collection;
|
||||
|
@ -194,8 +198,11 @@ public abstract class CollectionBinder {
|
|||
private String explicitType;
|
||||
private final Properties explicitTypeParameters = new Properties();
|
||||
|
||||
protected CollectionBinder(SemanticsResolver semanticsResolver, boolean isSortedCollection, MetadataBuildingContext buildingContext) {
|
||||
this.semanticsResolver = semanticsResolver;
|
||||
protected CollectionBinder(
|
||||
Supplier<ManagedBean<? extends UserCollectionType>> customTypeBeanResolver,
|
||||
boolean isSortedCollection,
|
||||
MetadataBuildingContext buildingContext) {
|
||||
this.customTypeBeanResolver = customTypeBeanResolver;
|
||||
this.isSortedCollection = isSortedCollection;
|
||||
this.buildingContext = buildingContext;
|
||||
}
|
||||
|
@ -204,8 +211,8 @@ public abstract class CollectionBinder {
|
|||
return buildingContext;
|
||||
}
|
||||
|
||||
protected SemanticsResolver getSemanticsResolver() {
|
||||
return semanticsResolver;
|
||||
public Supplier<ManagedBean<? extends UserCollectionType>> getCustomTypeBeanResolver() {
|
||||
return customTypeBeanResolver;
|
||||
}
|
||||
|
||||
public boolean isMap() {
|
||||
|
@ -286,15 +293,20 @@ public abstract class CollectionBinder {
|
|||
final CollectionBinder binder;
|
||||
if ( typeAnnotation != null ) {
|
||||
binder = createBinderFromCustomTypeAnnotation( property, typeAnnotation, buildingContext );
|
||||
|
||||
// todo (6.0) - technically, these should no longer be needed
|
||||
binder.explicitType = typeAnnotation.type().getName();
|
||||
for ( Parameter param : typeAnnotation.parameters() ) {
|
||||
binder.explicitTypeParameters.setProperty( param.name(), param.value() );
|
||||
}
|
||||
}
|
||||
else {
|
||||
final CollectionSemantics customSemantics = property.getAnnotation( CollectionSemantics.class );
|
||||
if ( customSemantics != null ) {
|
||||
binder = createBinderFromCustomSemantics( customSemantics, property, buildingContext );
|
||||
final CollectionClassification classification = determineCollectionClassification( property, buildingContext );
|
||||
final CollectionTypeRegistrationDescriptor typeRegistration = buildingContext
|
||||
.getMetadataCollector()
|
||||
.findCollectionTypeRegistration( classification );
|
||||
if ( typeRegistration != null ) {
|
||||
binder = createBinderFromTypeRegistration( property, classification, typeRegistration, buildingContext );
|
||||
}
|
||||
else {
|
||||
binder = createBinderFromProperty( property, buildingContext );
|
||||
|
@ -306,74 +318,164 @@ public abstract class CollectionBinder {
|
|||
return binder;
|
||||
}
|
||||
|
||||
private static CollectionBinder createBinderFromCustomSemantics(
|
||||
CollectionSemantics customSemantics,
|
||||
private static CollectionBinder createBinderFromTypeRegistration(
|
||||
XProperty property,
|
||||
CollectionClassification classification,
|
||||
CollectionTypeRegistrationDescriptor typeRegistration,
|
||||
MetadataBuildingContext buildingContext) {
|
||||
final ManagedBeanRegistry beanRegistry = buildingContext.getBootstrapContext()
|
||||
.getServiceRegistry()
|
||||
.getService( ManagedBeanRegistry.class );
|
||||
final ManagedBean<? extends org.hibernate.collection.spi.CollectionSemantics> semanticsBean = beanRegistry.getBean( customSemantics.value() );
|
||||
final org.hibernate.collection.spi.CollectionSemantics semantics = semanticsBean.getBeanInstance();
|
||||
return createBinder(
|
||||
property,
|
||||
semantics.getCollectionClassification(),
|
||||
(type) -> semantics,
|
||||
() -> createCustomType(
|
||||
property.getDeclaringClass().getName() + "#" + property.getName(),
|
||||
typeRegistration.getImplementation(),
|
||||
typeRegistration.getParameters(),
|
||||
buildingContext
|
||||
),
|
||||
classification,
|
||||
buildingContext
|
||||
);
|
||||
}
|
||||
|
||||
private static ManagedBean<? extends UserCollectionType> createCustomType(
|
||||
String role,
|
||||
Class<? extends UserCollectionType> implementation,
|
||||
Properties parameters,
|
||||
MetadataBuildingContext buildingContext) {
|
||||
final StandardServiceRegistry serviceRegistry = buildingContext.getBuildingOptions().getServiceRegistry();
|
||||
final ManagedBeanRegistry beanRegistry = serviceRegistry.getService( ManagedBeanRegistry.class );
|
||||
if ( CollectionHelper.isNotEmpty( parameters ) ) {
|
||||
return beanRegistry.getBean( implementation );
|
||||
}
|
||||
else {
|
||||
// defined parameters...
|
||||
if ( ParameterizedType.class.isAssignableFrom( implementation ) ) {
|
||||
// because there are config parameters and the type is configurable, we need
|
||||
// a separate bean instance which means uniquely naming it
|
||||
final ManagedBean<? extends UserCollectionType> typeBean = beanRegistry.getBean( role, implementation );
|
||||
final UserCollectionType type = typeBean.getBeanInstance();
|
||||
( (ParameterizedType) type ).setParameterValues( parameters );
|
||||
return typeBean;
|
||||
}
|
||||
else {
|
||||
// log a "warning"
|
||||
BootLogging.LOGGER.debugf(
|
||||
"Custom collection-type (`%s`) assigned to attribute (`%s`) does not implement `%s`, but its `@CollectionType` defined parameters",
|
||||
implementation.getName(),
|
||||
role,
|
||||
ParameterizedType.class.getName()
|
||||
);
|
||||
|
||||
// but still return the bean - we can again use the no-config bean instance
|
||||
return beanRegistry.getBean( implementation );
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private static CollectionBinder createBinderFromProperty(
|
||||
XProperty property,
|
||||
MetadataBuildingContext buildingContext) {
|
||||
final CollectionClassification classification = determineCollectionClassification( property, null, buildingContext );
|
||||
return createBinder( property, classification, null, buildingContext );
|
||||
final CollectionClassification classification = determineCollectionClassification( property, buildingContext );
|
||||
return createBinder( property, null, classification, buildingContext );
|
||||
}
|
||||
|
||||
private static CollectionBinder createBinderFromCustomTypeAnnotation(
|
||||
XProperty property,
|
||||
CollectionType typeAnnotation,
|
||||
MetadataBuildingContext buildingContext) {
|
||||
final CollectionClassification classification = determineCollectionClassification( property, typeAnnotation, buildingContext );
|
||||
final SemanticsResolver semanticsResolver = (collectionType) -> new CustomCollectionTypeSemantics<>( collectionType, classification );
|
||||
return createBinder( property, classification, semanticsResolver, buildingContext );
|
||||
determineSemanticJavaType( property );
|
||||
|
||||
final ManagedBean<? extends UserCollectionType> customTypeBean = resolveCustomType( property, typeAnnotation, buildingContext );
|
||||
return createBinder(
|
||||
property,
|
||||
() -> customTypeBean,
|
||||
customTypeBean.getBeanInstance().getClassification(),
|
||||
buildingContext
|
||||
);
|
||||
}
|
||||
|
||||
public static ManagedBean<? extends UserCollectionType> resolveCustomType(
|
||||
XProperty property,
|
||||
CollectionType typeAnnotation,
|
||||
MetadataBuildingContext buildingContext) {
|
||||
final ManagedBeanRegistry beanRegistry = buildingContext.getBootstrapContext()
|
||||
.getServiceRegistry()
|
||||
.getService( ManagedBeanRegistry.class );
|
||||
|
||||
final Class<? extends UserCollectionType> typeImpl = typeAnnotation.type();
|
||||
if ( typeAnnotation.parameters().length == 0 ) {
|
||||
// no parameters - we can re-use a no-config bean instance
|
||||
return beanRegistry.getBean( typeImpl );
|
||||
}
|
||||
else {
|
||||
// defined parameters...
|
||||
final String attributeKey = property.getDeclaringClass().getName() + "#" + property.getName();
|
||||
|
||||
if ( ParameterizedType.class.isAssignableFrom( typeImpl ) ) {
|
||||
// because there are config parameters and the type is configurable, we need
|
||||
// a separate bean instance which means uniquely naming it
|
||||
final ManagedBean<? extends UserCollectionType> typeBean = beanRegistry.getBean( attributeKey, typeImpl );
|
||||
final UserCollectionType type = typeBean.getBeanInstance();
|
||||
( (ParameterizedType) type ).setParameterValues( extractParameters( typeAnnotation ) );
|
||||
return typeBean;
|
||||
}
|
||||
else {
|
||||
// log a "warning"
|
||||
BootLogging.LOGGER.debugf(
|
||||
"Custom collection-type (`%s`) assigned to attribute (`%s`) does not implement `%s`, but its `@CollectionType` defined parameters",
|
||||
typeImpl.getName(),
|
||||
attributeKey,
|
||||
ParameterizedType.class.getName()
|
||||
);
|
||||
|
||||
// but still return the bean - we can again use the no-config bean instance
|
||||
return beanRegistry.getBean( typeImpl );
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private static Properties extractParameters(CollectionType typeAnnotation) {
|
||||
final Parameter[] parameterAnnotations = typeAnnotation.parameters();
|
||||
final Properties configParams = new Properties( parameterAnnotations.length );
|
||||
for ( Parameter parameterAnnotation : parameterAnnotations ) {
|
||||
configParams.put( parameterAnnotation.name(), parameterAnnotation.value() );
|
||||
}
|
||||
return configParams;
|
||||
}
|
||||
|
||||
private static CollectionBinder createBinder(
|
||||
XProperty property,
|
||||
Supplier<ManagedBean<? extends UserCollectionType>> customTypeBeanAccess,
|
||||
CollectionClassification classification,
|
||||
SemanticsResolver semanticsResolver,
|
||||
MetadataBuildingContext buildingContext) {
|
||||
|
||||
switch ( classification ) {
|
||||
case ARRAY: {
|
||||
if ( property.getElementClass().isPrimitive() ) {
|
||||
return new PrimitiveArrayBinder( semanticsResolver, buildingContext );
|
||||
return new PrimitiveArrayBinder( customTypeBeanAccess, buildingContext );
|
||||
}
|
||||
return new ArrayBinder( semanticsResolver, buildingContext );
|
||||
return new ArrayBinder( customTypeBeanAccess, buildingContext );
|
||||
}
|
||||
case BAG: {
|
||||
return new BagBinder( semanticsResolver, buildingContext );
|
||||
return new BagBinder( customTypeBeanAccess, buildingContext );
|
||||
}
|
||||
case ID_BAG: {
|
||||
return new IdBagBinder( semanticsResolver, buildingContext );
|
||||
return new IdBagBinder( customTypeBeanAccess, buildingContext );
|
||||
}
|
||||
case LIST: {
|
||||
return new ListBinder( semanticsResolver, buildingContext );
|
||||
return new ListBinder( customTypeBeanAccess, buildingContext );
|
||||
}
|
||||
case MAP:
|
||||
case ORDERED_MAP: {
|
||||
return new MapBinder( semanticsResolver, false, buildingContext );
|
||||
return new MapBinder( customTypeBeanAccess, false, buildingContext );
|
||||
}
|
||||
case SORTED_MAP: {
|
||||
return new MapBinder( semanticsResolver, true, buildingContext );
|
||||
return new MapBinder( customTypeBeanAccess, true, buildingContext );
|
||||
}
|
||||
case SET:
|
||||
case ORDERED_SET: {
|
||||
return new SetBinder( semanticsResolver, false, buildingContext );
|
||||
return new SetBinder( customTypeBeanAccess, false, buildingContext );
|
||||
}
|
||||
case SORTED_SET: {
|
||||
return new SetBinder( semanticsResolver, true, buildingContext );
|
||||
return new SetBinder( customTypeBeanAccess, true, buildingContext );
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -392,23 +494,32 @@ public abstract class CollectionBinder {
|
|||
|
||||
private static CollectionClassification determineCollectionClassification(
|
||||
XProperty property,
|
||||
CollectionType typeAnnotation,
|
||||
MetadataBuildingContext buildingContext) {
|
||||
final CollectionClassificationType classificationTypeAnnotation = property.getAnnotation( CollectionClassificationType.class );
|
||||
|
||||
if ( property.isArray() ) {
|
||||
if ( classificationTypeAnnotation != null ) {
|
||||
throw new AnnotationException( "Arrays should not be annotated with `@" + CollectionClassificationType.class.getName() + "`" );
|
||||
}
|
||||
return CollectionClassification.ARRAY;
|
||||
}
|
||||
|
||||
if ( classificationTypeAnnotation != null ) {
|
||||
return classificationTypeAnnotation.value();
|
||||
final Bag bagAnnotation = HCANNHelper.findAnnotation( property, Bag.class );
|
||||
if ( bagAnnotation != null ) {
|
||||
final Class<?> collectionJavaType = property.getCollectionClass();
|
||||
if ( java.util.List.class.equals( collectionJavaType ) || java.util.Collection.class.equals( collectionJavaType ) ) {
|
||||
return CollectionClassification.BAG;
|
||||
}
|
||||
throw new MappingException(
|
||||
String.format(
|
||||
Locale.ROOT,
|
||||
"@Bag annotation encountered on an attribute `%s#%s` of type `%s`; only `%s` and `%s` are supported",
|
||||
property.getDeclaringClass().getName(),
|
||||
property.getName(),
|
||||
collectionJavaType.getName(),
|
||||
java.util.List.class.getName(),
|
||||
java.util.Collection.class.getName()
|
||||
)
|
||||
);
|
||||
}
|
||||
|
||||
return determineCollectionClassification(
|
||||
determineSemanticJavaType( property, typeAnnotation ),
|
||||
determineSemanticJavaType( property ),
|
||||
property,
|
||||
buildingContext
|
||||
);
|
||||
|
@ -466,14 +577,7 @@ public abstract class CollectionBinder {
|
|||
}
|
||||
}
|
||||
|
||||
private static Class<?> determineSemanticJavaType(XProperty property, CollectionType typeAnnotation) {
|
||||
if ( typeAnnotation != null ) {
|
||||
final Class<?> requestedSemanticsJavaType = typeAnnotation.semantics();
|
||||
if ( requestedSemanticsJavaType != null && requestedSemanticsJavaType != void.class ) {
|
||||
return inferCollectionClassFromSubclass( requestedSemanticsJavaType );
|
||||
}
|
||||
}
|
||||
|
||||
private static Class<?> determineSemanticJavaType(XProperty property) {
|
||||
final Class<?> returnedJavaType = property.getCollectionClass();
|
||||
if ( returnedJavaType == null ) {
|
||||
throw new AnnotationException(
|
||||
|
|
|
@ -8,6 +8,7 @@ package org.hibernate.cfg.annotations;
|
|||
|
||||
import java.util.Collections;
|
||||
import java.util.Map;
|
||||
import java.util.function.Supplier;
|
||||
|
||||
import org.hibernate.MappingException;
|
||||
import org.hibernate.annotations.CollectionId;
|
||||
|
@ -24,10 +25,13 @@ import org.hibernate.cfg.SecondPass;
|
|||
import org.hibernate.cfg.WrappedInferredData;
|
||||
import org.hibernate.mapping.BasicValue;
|
||||
import org.hibernate.mapping.Collection;
|
||||
import org.hibernate.mapping.IdentifierBag;
|
||||
import org.hibernate.mapping.IdentifierCollection;
|
||||
import org.hibernate.mapping.PersistentClass;
|
||||
import org.hibernate.mapping.SemanticsResolver;
|
||||
import org.hibernate.mapping.Table;
|
||||
import org.hibernate.resource.beans.spi.ManagedBean;
|
||||
import org.hibernate.usertype.UserCollectionType;
|
||||
|
||||
import jakarta.persistence.Column;
|
||||
|
||||
|
@ -35,12 +39,12 @@ import jakarta.persistence.Column;
|
|||
* @author Emmanuel Bernard
|
||||
*/
|
||||
public class IdBagBinder extends BagBinder {
|
||||
public IdBagBinder(SemanticsResolver semanticsResolver, MetadataBuildingContext buildingContext) {
|
||||
super( semanticsResolver, buildingContext );
|
||||
public IdBagBinder(Supplier<ManagedBean<? extends UserCollectionType>> customTypeBeanResolver, MetadataBuildingContext buildingContext) {
|
||||
super( customTypeBeanResolver, buildingContext );
|
||||
}
|
||||
|
||||
protected Collection createCollection(PersistentClass owner) {
|
||||
return new org.hibernate.mapping.IdentifierBag( getSemanticsResolver(), owner, getBuildingContext() );
|
||||
return new IdentifierBag( getCustomTypeBeanResolver(), owner, getBuildingContext() );
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
|
@ -7,6 +7,7 @@
|
|||
package org.hibernate.cfg.annotations;
|
||||
|
||||
import java.util.Map;
|
||||
import java.util.function.Supplier;
|
||||
|
||||
import org.hibernate.MappingException;
|
||||
import org.hibernate.annotations.OrderBy;
|
||||
|
@ -28,6 +29,8 @@ import org.hibernate.mapping.OneToMany;
|
|||
import org.hibernate.mapping.PersistentClass;
|
||||
import org.hibernate.mapping.SemanticsResolver;
|
||||
import org.hibernate.mapping.SimpleValue;
|
||||
import org.hibernate.resource.beans.spi.ManagedBean;
|
||||
import org.hibernate.usertype.UserCollectionType;
|
||||
|
||||
import org.jboss.logging.Logger;
|
||||
|
||||
|
@ -41,13 +44,13 @@ import org.jboss.logging.Logger;
|
|||
public class ListBinder extends CollectionBinder {
|
||||
private static final CoreMessageLogger LOG = Logger.getMessageLogger( CoreMessageLogger.class, ListBinder.class.getName() );
|
||||
|
||||
public ListBinder(SemanticsResolver semanticsResolver, MetadataBuildingContext buildingContext) {
|
||||
super( semanticsResolver, false, buildingContext );
|
||||
public ListBinder(Supplier<ManagedBean<? extends UserCollectionType>> customTypeBeanResolver, MetadataBuildingContext buildingContext) {
|
||||
super( customTypeBeanResolver, false, buildingContext );
|
||||
}
|
||||
|
||||
@Override
|
||||
protected Collection createCollection(PersistentClass owner) {
|
||||
return new List( getSemanticsResolver(), owner, getBuildingContext() );
|
||||
return new List( getCustomTypeBeanResolver(), owner, getBuildingContext() );
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
|
@ -9,6 +9,7 @@ package org.hibernate.cfg.annotations;
|
|||
import java.util.HashMap;
|
||||
import java.util.Iterator;
|
||||
import java.util.Map;
|
||||
import java.util.function.Supplier;
|
||||
|
||||
import org.hibernate.AnnotationException;
|
||||
import org.hibernate.AssertionFailure;
|
||||
|
@ -48,6 +49,8 @@ import org.hibernate.mapping.SemanticsResolver;
|
|||
import org.hibernate.mapping.SimpleValue;
|
||||
import org.hibernate.mapping.Table;
|
||||
import org.hibernate.mapping.Value;
|
||||
import org.hibernate.resource.beans.spi.ManagedBean;
|
||||
import org.hibernate.usertype.UserCollectionType;
|
||||
|
||||
import jakarta.persistence.AttributeOverride;
|
||||
import jakarta.persistence.AttributeOverrides;
|
||||
|
@ -64,8 +67,8 @@ import jakarta.persistence.MapKeyJoinColumns;
|
|||
* @author Emmanuel Bernard
|
||||
*/
|
||||
public class MapBinder extends CollectionBinder {
|
||||
public MapBinder(SemanticsResolver semanticsResolver, boolean sorted, MetadataBuildingContext buildingContext) {
|
||||
super( semanticsResolver, sorted, buildingContext );
|
||||
public MapBinder(Supplier<ManagedBean<? extends UserCollectionType>> customTypeBeanResolver, boolean sorted, MetadataBuildingContext buildingContext) {
|
||||
super( customTypeBeanResolver, sorted, buildingContext );
|
||||
}
|
||||
|
||||
public boolean isMap() {
|
||||
|
@ -73,7 +76,7 @@ public class MapBinder extends CollectionBinder {
|
|||
}
|
||||
|
||||
protected Collection createCollection(PersistentClass owner) {
|
||||
return new org.hibernate.mapping.Map( getSemanticsResolver(), owner, getBuildingContext() );
|
||||
return new org.hibernate.mapping.Map( getCustomTypeBeanResolver(), owner, getBuildingContext() );
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
|
@ -6,22 +6,25 @@
|
|||
*/
|
||||
package org.hibernate.cfg.annotations;
|
||||
|
||||
import java.util.function.Supplier;
|
||||
|
||||
import org.hibernate.boot.spi.MetadataBuildingContext;
|
||||
import org.hibernate.mapping.Collection;
|
||||
import org.hibernate.mapping.PersistentClass;
|
||||
import org.hibernate.mapping.PrimitiveArray;
|
||||
import org.hibernate.mapping.SemanticsResolver;
|
||||
import org.hibernate.resource.beans.spi.ManagedBean;
|
||||
import org.hibernate.usertype.UserCollectionType;
|
||||
|
||||
/**
|
||||
* @author Emmanuel Bernard
|
||||
*/
|
||||
public class PrimitiveArrayBinder extends ArrayBinder {
|
||||
public PrimitiveArrayBinder(SemanticsResolver semanticsResolver, MetadataBuildingContext buildingContext) {
|
||||
super( semanticsResolver, buildingContext );
|
||||
public PrimitiveArrayBinder(Supplier<ManagedBean<? extends UserCollectionType>> customTypeBeanResolver, MetadataBuildingContext buildingContext) {
|
||||
super( customTypeBeanResolver, buildingContext );
|
||||
}
|
||||
|
||||
@Override
|
||||
protected Collection createCollection(PersistentClass owner) {
|
||||
return new PrimitiveArray( getSemanticsResolver(), owner, getBuildingContext() );
|
||||
return new PrimitiveArray( getCustomTypeBeanResolver(), owner, getBuildingContext() );
|
||||
}
|
||||
}
|
||||
|
|
|
@ -6,11 +6,15 @@
|
|||
*/
|
||||
package org.hibernate.cfg.annotations;
|
||||
|
||||
import java.util.function.Supplier;
|
||||
|
||||
import org.hibernate.annotations.OrderBy;
|
||||
import org.hibernate.boot.spi.MetadataBuildingContext;
|
||||
import org.hibernate.mapping.Collection;
|
||||
import org.hibernate.mapping.PersistentClass;
|
||||
import org.hibernate.mapping.SemanticsResolver;
|
||||
import org.hibernate.resource.beans.spi.ManagedBean;
|
||||
import org.hibernate.usertype.UserCollectionType;
|
||||
|
||||
/**
|
||||
* Bind a set.
|
||||
|
@ -18,13 +22,13 @@ import org.hibernate.mapping.SemanticsResolver;
|
|||
* @author Matthew Inger
|
||||
*/
|
||||
public class SetBinder extends CollectionBinder {
|
||||
public SetBinder(SemanticsResolver semanticsResolver, boolean sorted, MetadataBuildingContext buildingContext) {
|
||||
super( semanticsResolver, sorted, buildingContext );
|
||||
public SetBinder(Supplier<ManagedBean<? extends UserCollectionType>> customTypeBeanResolver, boolean sorted, MetadataBuildingContext buildingContext) {
|
||||
super( customTypeBeanResolver, sorted, buildingContext );
|
||||
}
|
||||
|
||||
@Override
|
||||
protected Collection createCollection(PersistentClass persistentClass) {
|
||||
return new org.hibernate.mapping.Set( getSemanticsResolver(), persistentClass, getBuildingContext() );
|
||||
return new org.hibernate.mapping.Set( getCustomTypeBeanResolver(), persistentClass, getBuildingContext() );
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
|
@ -30,16 +30,18 @@ import org.hibernate.type.CollectionType;
|
|||
*/
|
||||
public class CustomCollectionTypeSemantics<CE, E> implements CollectionSemantics<CE, E> {
|
||||
private final CollectionType collectionType;
|
||||
private final CollectionClassification classification;
|
||||
|
||||
public CustomCollectionTypeSemantics(CollectionType collectionType, CollectionClassification classification) {
|
||||
public CustomCollectionTypeSemantics(CollectionType collectionType) {
|
||||
this.collectionType = collectionType;
|
||||
this.classification = classification;
|
||||
}
|
||||
|
||||
public CollectionType getCollectionType() {
|
||||
return collectionType;
|
||||
}
|
||||
|
||||
@Override
|
||||
public CollectionClassification getCollectionClassification() {
|
||||
return classification;
|
||||
return collectionType.getCollectionClassification();
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -77,7 +79,7 @@ public class CustomCollectionTypeSemantics<CE, E> implements CollectionSemantics
|
|||
return InitializerProducerBuilder.createCollectionTypeWrapperInitializerProducer(
|
||||
navigablePath,
|
||||
attributeMapping,
|
||||
classification,
|
||||
getCollectionClassification(),
|
||||
fetchParent,
|
||||
selected,
|
||||
indexFetch,
|
||||
|
|
|
@ -6,33 +6,39 @@
|
|||
*/
|
||||
package org.hibernate.collection.spi;
|
||||
|
||||
import java.util.function.Consumer;
|
||||
|
||||
import org.hibernate.Incubating;
|
||||
import org.hibernate.LockMode;
|
||||
import org.hibernate.metamodel.mapping.PluralAttributeMapping;
|
||||
import org.hibernate.query.NavigablePath;
|
||||
import org.hibernate.sql.ast.tree.from.TableGroup;
|
||||
import org.hibernate.sql.results.graph.AssemblerCreationState;
|
||||
import org.hibernate.sql.results.graph.collection.CollectionInitializer;
|
||||
import org.hibernate.sql.results.graph.DomainResultAssembler;
|
||||
import org.hibernate.sql.results.graph.FetchParentAccess;
|
||||
import org.hibernate.sql.results.graph.Initializer;
|
||||
import org.hibernate.sql.results.graph.collection.CollectionInitializer;
|
||||
|
||||
/**
|
||||
* Functional contract to create a CollectionInitializer
|
||||
*
|
||||
* @author Steve Ebersole
|
||||
*
|
||||
* @since 6.0
|
||||
*/
|
||||
@Incubating
|
||||
@FunctionalInterface
|
||||
public interface CollectionInitializerProducer {
|
||||
/**
|
||||
* todo (6.0) : clean this contract up!
|
||||
* Create an initializer for `attribute` relative to `navigablePath`.
|
||||
*
|
||||
* `parentAccess` may be null to indicate that the initializer is for
|
||||
* a {@link org.hibernate.sql.results.graph.DomainResult} rather than
|
||||
* a {@link org.hibernate.sql.results.graph.Fetch}
|
||||
*
|
||||
* `collectionKeyAssembler` and `collectionValueKeyAssembler` allow
|
||||
* creating {@link org.hibernate.sql.results.graph.DomainResult} for
|
||||
* either side of the collection foreign-key
|
||||
*/
|
||||
CollectionInitializer produceInitializer(
|
||||
NavigablePath navigablePath,
|
||||
PluralAttributeMapping attributeMapping,
|
||||
PluralAttributeMapping attribute,
|
||||
FetchParentAccess parentAccess,
|
||||
LockMode lockMode,
|
||||
DomainResultAssembler<?> collectionKeyAssembler,
|
||||
|
|
|
@ -27,6 +27,8 @@ import org.hibernate.sql.results.graph.FetchParent;
|
|||
*
|
||||
* @author Steve Ebersole
|
||||
* @author Gavin King
|
||||
*
|
||||
* @since 6.0
|
||||
*/
|
||||
@Incubating
|
||||
public interface CollectionSemantics<CE, E> {
|
||||
|
|
|
@ -500,7 +500,7 @@ public class PersistentBag<E> extends AbstractPersistentCollection<E> implements
|
|||
|
||||
@Override
|
||||
public Object getIndex(Object entry, int i, CollectionPersister persister) {
|
||||
throw new UnsupportedOperationException( "Bags don't have indexes" );
|
||||
throw new UnsupportedOperationException( "Bags don't have indexes : " + persister.getRole() );
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
|
@ -6,7 +6,7 @@
|
|||
*/
|
||||
package org.hibernate.mapping;
|
||||
|
||||
import java.util.function.Function;
|
||||
import java.util.function.Supplier;
|
||||
|
||||
import org.hibernate.MappingException;
|
||||
import org.hibernate.boot.registry.classloading.spi.ClassLoaderService;
|
||||
|
@ -14,10 +14,12 @@ import org.hibernate.boot.registry.classloading.spi.ClassLoadingException;
|
|||
import org.hibernate.boot.spi.MetadataBuildingContext;
|
||||
import org.hibernate.collection.internal.StandardArraySemantics;
|
||||
import org.hibernate.collection.spi.CollectionSemantics;
|
||||
import org.hibernate.resource.beans.spi.ManagedBean;
|
||||
import org.hibernate.type.ArrayType;
|
||||
import org.hibernate.type.BasicType;
|
||||
import org.hibernate.type.CollectionType;
|
||||
import org.hibernate.type.descriptor.java.spi.PrimitiveJavaType;
|
||||
import org.hibernate.usertype.UserCollectionType;
|
||||
|
||||
/**
|
||||
* An array mapping has a primary key consisting of the key columns + index column.
|
||||
|
@ -31,8 +33,8 @@ public class Array extends List {
|
|||
super( buildingContext, owner );
|
||||
}
|
||||
|
||||
public Array(SemanticsResolver semanticsResolver, PersistentClass owner, MetadataBuildingContext buildingContext) {
|
||||
super( semanticsResolver, owner, buildingContext );
|
||||
public Array(Supplier<ManagedBean<? extends UserCollectionType>> customTypeBeanResolver, PersistentClass owner, MetadataBuildingContext buildingContext) {
|
||||
super( customTypeBeanResolver, owner, buildingContext );
|
||||
}
|
||||
|
||||
public Class<?> getElementClass() throws MappingException {
|
||||
|
|
|
@ -7,12 +7,15 @@
|
|||
package org.hibernate.mapping;
|
||||
|
||||
import java.util.function.Function;
|
||||
import java.util.function.Supplier;
|
||||
|
||||
import org.hibernate.boot.spi.MetadataBuildingContext;
|
||||
import org.hibernate.collection.internal.StandardBagSemantics;
|
||||
import org.hibernate.collection.spi.CollectionSemantics;
|
||||
import org.hibernate.resource.beans.spi.ManagedBean;
|
||||
import org.hibernate.type.BagType;
|
||||
import org.hibernate.type.CollectionType;
|
||||
import org.hibernate.usertype.UserCollectionType;
|
||||
|
||||
/**
|
||||
* A bag permits duplicates, so it has no primary key
|
||||
|
@ -30,8 +33,8 @@ public class Bag extends Collection {
|
|||
/**
|
||||
* Annotation binding
|
||||
*/
|
||||
public Bag(SemanticsResolver semanticsResolver, PersistentClass owner, MetadataBuildingContext buildingContext) {
|
||||
super( semanticsResolver, owner, buildingContext );
|
||||
public Bag(Supplier<ManagedBean<? extends UserCollectionType>> customTypeBeanResolver, PersistentClass owner, MetadataBuildingContext buildingContext) {
|
||||
super( customTypeBeanResolver, owner, buildingContext );
|
||||
}
|
||||
|
||||
public CollectionType getDefaultCollectionType() {
|
||||
|
|
|
@ -14,8 +14,7 @@ import java.util.Iterator;
|
|||
import java.util.List;
|
||||
import java.util.Objects;
|
||||
import java.util.Properties;
|
||||
import java.util.SortedMap;
|
||||
import java.util.SortedSet;
|
||||
import java.util.function.Supplier;
|
||||
|
||||
import org.hibernate.FetchMode;
|
||||
import org.hibernate.MappingException;
|
||||
|
@ -29,12 +28,14 @@ import org.hibernate.engine.spi.Mapping;
|
|||
import org.hibernate.internal.FilterConfiguration;
|
||||
import org.hibernate.internal.util.StringHelper;
|
||||
import org.hibernate.internal.util.collections.ArrayHelper;
|
||||
import org.hibernate.metamodel.CollectionClassification;
|
||||
import org.hibernate.persister.collection.CollectionPersister;
|
||||
import org.hibernate.resource.beans.spi.ManagedBean;
|
||||
import org.hibernate.service.ServiceRegistry;
|
||||
import org.hibernate.type.CollectionType;
|
||||
import org.hibernate.type.CustomCollectionType;
|
||||
import org.hibernate.type.Type;
|
||||
import org.hibernate.type.spi.TypeConfiguration;
|
||||
import org.hibernate.usertype.UserCollectionType;
|
||||
|
||||
/**
|
||||
* Mapping for a collection. Subclasses specialize to particular collection styles.
|
||||
|
@ -77,7 +78,10 @@ public abstract class Collection implements Fetchable, Value, Filterable {
|
|||
|
||||
private String typeName;
|
||||
private Properties typeParameters;
|
||||
private SemanticsResolver customSemanticsResolver;
|
||||
private Supplier<ManagedBean<? extends UserCollectionType>> customTypeBeanResolver;
|
||||
private CollectionType cachedCollectionType;
|
||||
private CollectionSemantics<?,?> cachedCollectionSemantics;
|
||||
|
||||
private Class<? extends CollectionPersister> collectionPersisterClass;
|
||||
|
||||
private final List<FilterConfiguration> filters = new ArrayList<>();
|
||||
|
@ -110,8 +114,11 @@ public abstract class Collection implements Fetchable, Value, Filterable {
|
|||
/**
|
||||
* Annotation binding
|
||||
*/
|
||||
protected Collection(SemanticsResolver customSemanticsResolver, PersistentClass owner, MetadataBuildingContext buildingContext) {
|
||||
this.customSemanticsResolver = customSemanticsResolver;
|
||||
protected Collection(
|
||||
Supplier<ManagedBean<? extends UserCollectionType>> customTypeBeanResolver,
|
||||
PersistentClass owner,
|
||||
MetadataBuildingContext buildingContext) {
|
||||
this.customTypeBeanResolver = customTypeBeanResolver;
|
||||
this.owner = owner;
|
||||
this.buildingContext = buildingContext;
|
||||
}
|
||||
|
@ -409,8 +416,6 @@ public abstract class Collection implements Fetchable, Value, Filterable {
|
|||
return getCollectionType();
|
||||
}
|
||||
|
||||
private CollectionSemantics<?,?> cachedCollectionSemantics;
|
||||
|
||||
@SuppressWarnings("rawtypes")
|
||||
public CollectionSemantics getCollectionSemantics() {
|
||||
if ( cachedCollectionSemantics == null ) {
|
||||
|
@ -422,8 +427,32 @@ public abstract class Collection implements Fetchable, Value, Filterable {
|
|||
|
||||
private CollectionSemantics<?, ?> resolveCollectionSemantics() {
|
||||
final CollectionType collectionType;
|
||||
if ( typeName == null ) {
|
||||
collectionType = null;
|
||||
if ( cachedCollectionType == null ) {
|
||||
collectionType = resolveCollectionType();
|
||||
cachedCollectionType = collectionType;
|
||||
}
|
||||
else {
|
||||
collectionType = cachedCollectionType;
|
||||
}
|
||||
|
||||
return new CustomCollectionTypeSemantics<>( collectionType );
|
||||
}
|
||||
|
||||
private CollectionType resolveCollectionType() {
|
||||
final CollectionType collectionType;
|
||||
if ( cachedCollectionType != null ) {
|
||||
collectionType = cachedCollectionType;
|
||||
}
|
||||
else if ( customTypeBeanResolver != null ) {
|
||||
collectionType = new CustomCollectionType(
|
||||
customTypeBeanResolver.get(),
|
||||
role,
|
||||
referencedPropertyName,
|
||||
getMetadata().getTypeConfiguration()
|
||||
);
|
||||
}
|
||||
else if ( typeName == null ) {
|
||||
collectionType = getDefaultCollectionType();
|
||||
}
|
||||
else {
|
||||
collectionType = MappingHelper.customCollection(
|
||||
|
@ -434,50 +463,7 @@ public abstract class Collection implements Fetchable, Value, Filterable {
|
|||
getMetadata()
|
||||
);
|
||||
}
|
||||
|
||||
if ( customSemanticsResolver != null ) {
|
||||
return customSemanticsResolver.resolve( collectionType );
|
||||
}
|
||||
|
||||
if ( collectionType == null ) {
|
||||
return getDefaultCollectionSemantics();
|
||||
}
|
||||
|
||||
final Class<?> semanticJavaType = collectionType.getReturnedClass();
|
||||
final CollectionClassification classification;
|
||||
|
||||
if ( semanticJavaType.isArray() ) {
|
||||
classification = CollectionClassification.ARRAY;
|
||||
}
|
||||
else if ( List.class.isAssignableFrom( semanticJavaType ) ) {
|
||||
classification = CollectionClassification.LIST;
|
||||
}
|
||||
else if ( SortedSet.class.isAssignableFrom( semanticJavaType ) ) {
|
||||
classification = CollectionClassification.SORTED_SET;
|
||||
}
|
||||
else if ( Set.class.isAssignableFrom( semanticJavaType ) ) {
|
||||
classification = CollectionClassification.SET;
|
||||
}
|
||||
else if ( SortedMap.class.isAssignableFrom( semanticJavaType ) ) {
|
||||
classification = CollectionClassification.SORTED_MAP;
|
||||
}
|
||||
else if ( Map.class.isAssignableFrom( semanticJavaType ) ) {
|
||||
classification = CollectionClassification.MAP;
|
||||
}
|
||||
else if ( Collection.class.isAssignableFrom( semanticJavaType ) ) {
|
||||
if ( isIdentified() ) {
|
||||
classification = CollectionClassification.ID_BAG;
|
||||
}
|
||||
else {
|
||||
classification = CollectionClassification.BAG;
|
||||
}
|
||||
}
|
||||
else {
|
||||
throw new IllegalArgumentException( "Unexpected collection-semantics Java type : " + semanticJavaType );
|
||||
}
|
||||
|
||||
return new CustomCollectionTypeSemantics<>( collectionType, classification );
|
||||
|
||||
return collectionType;
|
||||
}
|
||||
|
||||
public CollectionSemantics<?,?> getDefaultCollectionSemantics() {
|
||||
|
@ -488,13 +474,10 @@ public abstract class Collection implements Fetchable, Value, Filterable {
|
|||
}
|
||||
|
||||
public CollectionType getCollectionType() {
|
||||
// todo (6.0) : hook in CollectionSemantics
|
||||
if ( typeName == null ) {
|
||||
return getDefaultCollectionType();
|
||||
}
|
||||
else {
|
||||
return MappingHelper.customCollection( typeName, typeParameters, role, referencedPropertyName, getMetadata() );
|
||||
if ( cachedCollectionType == null ) {
|
||||
cachedCollectionType = resolveCollectionType();
|
||||
}
|
||||
return cachedCollectionType;
|
||||
}
|
||||
|
||||
public boolean isNullable() {
|
||||
|
|
|
@ -6,11 +6,15 @@
|
|||
*/
|
||||
package org.hibernate.mapping;
|
||||
|
||||
import java.util.function.Supplier;
|
||||
|
||||
import org.hibernate.boot.spi.MetadataBuildingContext;
|
||||
import org.hibernate.collection.internal.StandardIdentifierBagSemantics;
|
||||
import org.hibernate.collection.spi.CollectionSemantics;
|
||||
import org.hibernate.resource.beans.spi.ManagedBean;
|
||||
import org.hibernate.type.CollectionType;
|
||||
import org.hibernate.type.IdentifierBagType;
|
||||
import org.hibernate.usertype.UserCollectionType;
|
||||
|
||||
/**
|
||||
* An {@code IdentifierBag} has a primary key consisting of
|
||||
|
@ -28,8 +32,8 @@ public class IdentifierBag extends IdentifierCollection {
|
|||
/**
|
||||
* annotation binding
|
||||
*/
|
||||
public IdentifierBag(SemanticsResolver semanticsResolver, PersistentClass owner, MetadataBuildingContext buildingContext) {
|
||||
super( semanticsResolver, owner, buildingContext );
|
||||
public IdentifierBag(Supplier<ManagedBean<? extends UserCollectionType>> customTypeBeanResolver, PersistentClass owner, MetadataBuildingContext buildingContext) {
|
||||
super( customTypeBeanResolver, owner, buildingContext );
|
||||
}
|
||||
|
||||
public CollectionType getDefaultCollectionType() {
|
||||
|
|
|
@ -6,10 +6,13 @@
|
|||
*/
|
||||
package org.hibernate.mapping;
|
||||
|
||||
import java.util.function.Supplier;
|
||||
|
||||
import org.hibernate.MappingException;
|
||||
import org.hibernate.boot.spi.MetadataBuildingContext;
|
||||
import org.hibernate.collection.spi.CollectionSemantics;
|
||||
import org.hibernate.engine.spi.Mapping;
|
||||
import org.hibernate.resource.beans.spi.ManagedBean;
|
||||
import org.hibernate.usertype.UserCollectionType;
|
||||
|
||||
/**
|
||||
* A collection with a synthetic "identifier" column
|
||||
|
@ -24,8 +27,8 @@ public abstract class IdentifierCollection extends Collection {
|
|||
super( buildingContext, owner );
|
||||
}
|
||||
|
||||
public IdentifierCollection(SemanticsResolver semanticsResolver, PersistentClass owner, MetadataBuildingContext buildingContext) {
|
||||
super( semanticsResolver, owner, buildingContext );
|
||||
public IdentifierCollection(Supplier<ManagedBean<? extends UserCollectionType>> customTypeBeanResolver, PersistentClass owner, MetadataBuildingContext buildingContext) {
|
||||
super( customTypeBeanResolver, owner, buildingContext );
|
||||
}
|
||||
|
||||
public KeyValue getIdentifier() {
|
||||
|
|
|
@ -7,13 +7,13 @@
|
|||
package org.hibernate.mapping;
|
||||
|
||||
import java.util.Iterator;
|
||||
import java.util.function.Function;
|
||||
import java.util.function.Supplier;
|
||||
|
||||
import org.hibernate.MappingException;
|
||||
import org.hibernate.boot.spi.MetadataBuildingContext;
|
||||
import org.hibernate.collection.spi.CollectionSemantics;
|
||||
import org.hibernate.engine.spi.Mapping;
|
||||
import org.hibernate.type.CollectionType;
|
||||
import org.hibernate.resource.beans.spi.ManagedBean;
|
||||
import org.hibernate.usertype.UserCollectionType;
|
||||
|
||||
/**
|
||||
* Indexed collections include Lists, Maps, arrays and
|
||||
|
@ -30,8 +30,8 @@ public abstract class IndexedCollection extends Collection {
|
|||
super( buildingContext, owner );
|
||||
}
|
||||
|
||||
public IndexedCollection(SemanticsResolver semanticsResolver, PersistentClass owner, MetadataBuildingContext buildingContext) {
|
||||
super( semanticsResolver, owner, buildingContext );
|
||||
public IndexedCollection(Supplier<ManagedBean<? extends UserCollectionType>> customTypeBeanResolver, PersistentClass owner, MetadataBuildingContext buildingContext) {
|
||||
super( customTypeBeanResolver, owner, buildingContext );
|
||||
}
|
||||
|
||||
public Value getIndex() {
|
||||
|
|
|
@ -6,14 +6,16 @@
|
|||
*/
|
||||
package org.hibernate.mapping;
|
||||
|
||||
import java.util.function.Function;
|
||||
import java.util.function.Supplier;
|
||||
|
||||
import org.hibernate.MappingException;
|
||||
import org.hibernate.boot.spi.MetadataBuildingContext;
|
||||
import org.hibernate.collection.internal.StandardListSemantics;
|
||||
import org.hibernate.collection.spi.CollectionSemantics;
|
||||
import org.hibernate.resource.beans.spi.ManagedBean;
|
||||
import org.hibernate.type.CollectionType;
|
||||
import org.hibernate.type.ListType;
|
||||
import org.hibernate.usertype.UserCollectionType;
|
||||
|
||||
/**
|
||||
* A list mapping has a primary key consisting of the key columns + index column.
|
||||
|
@ -34,8 +36,8 @@ public class List extends IndexedCollection {
|
|||
/**
|
||||
* annotation binding
|
||||
*/
|
||||
public List(SemanticsResolver semanticsResolver, PersistentClass owner, MetadataBuildingContext buildingContext) {
|
||||
super( semanticsResolver, owner, buildingContext );
|
||||
public List(Supplier<ManagedBean<? extends UserCollectionType>> customTypeBeanResolver, PersistentClass owner, MetadataBuildingContext buildingContext) {
|
||||
super( customTypeBeanResolver, owner, buildingContext );
|
||||
}
|
||||
|
||||
public boolean isList() {
|
||||
|
|
|
@ -6,16 +6,20 @@
|
|||
*/
|
||||
package org.hibernate.mapping;
|
||||
|
||||
import java.util.function.Supplier;
|
||||
|
||||
import org.hibernate.MappingException;
|
||||
import org.hibernate.boot.spi.MetadataBuildingContext;
|
||||
import org.hibernate.collection.internal.StandardMapSemantics;
|
||||
import org.hibernate.collection.internal.StandardOrderedMapSemantics;
|
||||
import org.hibernate.collection.internal.StandardSortedMapSemantics;
|
||||
import org.hibernate.collection.spi.CollectionSemantics;
|
||||
import org.hibernate.resource.beans.spi.ManagedBean;
|
||||
import org.hibernate.type.CollectionType;
|
||||
import org.hibernate.type.MapType;
|
||||
import org.hibernate.type.OrderedMapType;
|
||||
import org.hibernate.type.SortedMapType;
|
||||
import org.hibernate.usertype.UserCollectionType;
|
||||
|
||||
/**
|
||||
* A map has a primary key consisting of
|
||||
|
@ -29,8 +33,8 @@ public class Map extends IndexedCollection {
|
|||
super( buildingContext, owner );
|
||||
}
|
||||
|
||||
public Map(SemanticsResolver semanticsResolver, PersistentClass owner, MetadataBuildingContext buildingContext) {
|
||||
super( semanticsResolver, owner, buildingContext );
|
||||
public Map(Supplier<ManagedBean<? extends UserCollectionType>> customTypeBeanResolver, PersistentClass owner, MetadataBuildingContext buildingContext) {
|
||||
super( customTypeBeanResolver, owner, buildingContext );
|
||||
}
|
||||
|
||||
public boolean isMap() {
|
||||
|
|
|
@ -6,18 +6,17 @@
|
|||
*/
|
||||
package org.hibernate.mapping;
|
||||
|
||||
import java.util.Locale;
|
||||
import java.util.Map;
|
||||
import java.util.Properties;
|
||||
import java.util.function.Supplier;
|
||||
|
||||
import org.hibernate.Internal;
|
||||
import org.hibernate.MappingException;
|
||||
import org.hibernate.boot.registry.classloading.spi.ClassLoaderService;
|
||||
import org.hibernate.boot.registry.classloading.spi.ClassLoadingException;
|
||||
import org.hibernate.boot.spi.MetadataBuildingContext;
|
||||
import org.hibernate.boot.spi.MetadataImplementor;
|
||||
import org.hibernate.metamodel.mapping.MappingModelCreationLogger;
|
||||
import org.hibernate.resource.beans.spi.ManagedBean;
|
||||
import org.hibernate.resource.beans.spi.ManagedBeanRegistry;
|
||||
import org.hibernate.type.AnyType;
|
||||
import org.hibernate.type.CollectionType;
|
||||
import org.hibernate.type.CustomCollectionType;
|
||||
|
@ -47,20 +46,23 @@ public final class MappingHelper {
|
|||
String propertyRef,
|
||||
MetadataImplementor metadata) {
|
||||
final ClassLoaderService cls = metadata.getMetadataBuildingOptions().getServiceRegistry().getService( ClassLoaderService.class );
|
||||
final Class<? extends UserCollectionType> typeImpl = cls.classForName( typeName );
|
||||
|
||||
try {
|
||||
final Class<? extends UserCollectionType> typeClass = cls.classForName( typeName );
|
||||
final ManagedBeanRegistry beanRegistry = metadata
|
||||
.getMetadataBuildingOptions()
|
||||
.getServiceRegistry()
|
||||
.getService( ManagedBeanRegistry.class );
|
||||
|
||||
CustomCollectionType result = new CustomCollectionType( typeClass, role, propertyRef, metadata.getTypeConfiguration() );
|
||||
if ( typeParameters != null ) {
|
||||
injectParameters( result.getUserType(), typeParameters );
|
||||
}
|
||||
|
||||
return result;
|
||||
final ManagedBean<? extends UserCollectionType> customTypeBean;
|
||||
if ( typeParameters == null ) {
|
||||
customTypeBean = beanRegistry.getBean( typeImpl );
|
||||
}
|
||||
catch (ClassLoadingException e) {
|
||||
throw new MappingException( "user collection type class not found: " + typeName, e );
|
||||
else {
|
||||
customTypeBean = beanRegistry.getBean( role, typeImpl );
|
||||
injectParameters( customTypeBean.getBeanInstance(), typeParameters );
|
||||
}
|
||||
|
||||
return new CustomCollectionType( customTypeBean, role, propertyRef, metadata.getTypeConfiguration() );
|
||||
}
|
||||
|
||||
public static void injectParameters(Object type, Properties parameters) {
|
||||
|
|
|
@ -6,9 +6,13 @@
|
|||
*/
|
||||
package org.hibernate.mapping;
|
||||
|
||||
import java.util.function.Supplier;
|
||||
|
||||
import org.hibernate.boot.spi.MetadataBuildingContext;
|
||||
import org.hibernate.collection.internal.StandardArraySemantics;
|
||||
import org.hibernate.collection.spi.CollectionSemantics;
|
||||
import org.hibernate.resource.beans.spi.ManagedBean;
|
||||
import org.hibernate.usertype.UserCollectionType;
|
||||
|
||||
/**
|
||||
* A primitive array has a primary key consisting of the key columns + index column.
|
||||
|
@ -18,8 +22,8 @@ public class PrimitiveArray extends Array {
|
|||
super( buildingContext, owner );
|
||||
}
|
||||
|
||||
public PrimitiveArray(SemanticsResolver semanticsResolver, PersistentClass owner, MetadataBuildingContext buildingContext) {
|
||||
super( semanticsResolver, owner, buildingContext );
|
||||
public PrimitiveArray(Supplier<ManagedBean<? extends UserCollectionType>> customTypeBeanResolver, PersistentClass owner, MetadataBuildingContext buildingContext) {
|
||||
super( customTypeBeanResolver, owner, buildingContext );
|
||||
}
|
||||
|
||||
public boolean isPrimitiveArray() {
|
||||
|
|
|
@ -7,6 +7,7 @@
|
|||
package org.hibernate.mapping;
|
||||
|
||||
import java.util.Iterator;
|
||||
import java.util.function.Supplier;
|
||||
|
||||
import org.hibernate.MappingException;
|
||||
import org.hibernate.boot.spi.MetadataBuildingContext;
|
||||
|
@ -15,10 +16,12 @@ import org.hibernate.collection.internal.StandardSetSemantics;
|
|||
import org.hibernate.collection.internal.StandardSortedSetSemantics;
|
||||
import org.hibernate.collection.spi.CollectionSemantics;
|
||||
import org.hibernate.engine.spi.Mapping;
|
||||
import org.hibernate.resource.beans.spi.ManagedBean;
|
||||
import org.hibernate.type.CollectionType;
|
||||
import org.hibernate.type.OrderedSetType;
|
||||
import org.hibernate.type.SetType;
|
||||
import org.hibernate.type.SortedSetType;
|
||||
import org.hibernate.usertype.UserCollectionType;
|
||||
|
||||
/**
|
||||
* A set with no nullable element columns. It will have a primary key
|
||||
|
@ -36,8 +39,8 @@ public class Set extends Collection {
|
|||
/**
|
||||
* Used by annotation binding
|
||||
*/
|
||||
public Set(SemanticsResolver semanticsResolver, PersistentClass persistentClass, MetadataBuildingContext buildingContext) {
|
||||
super( semanticsResolver, persistentClass, buildingContext );
|
||||
public Set(Supplier<ManagedBean<? extends UserCollectionType>> customTypeBeanResolver, PersistentClass persistentClass, MetadataBuildingContext buildingContext) {
|
||||
super( customTypeBeanResolver, persistentClass, buildingContext );
|
||||
}
|
||||
|
||||
public void validate(Mapping mapping) throws MappingException {
|
||||
|
|
|
@ -56,6 +56,9 @@ public enum CollectionClassification {
|
|||
* A sorted {@link #SET} using either natural sorting of the elements or a
|
||||
* specified {@link java.util.Comparator}. Represented
|
||||
* as {@link java.util.SortedSet} or {@link java.util.Set}
|
||||
*
|
||||
* @see org.hibernate.annotations.SortNatural
|
||||
* @see org.hibernate.annotations.SortComparator
|
||||
*/
|
||||
SORTED_SET( PluralAttribute.CollectionType.SET ),
|
||||
|
||||
|
@ -64,6 +67,9 @@ public enum CollectionClassification {
|
|||
* as the collection is loaded. Does not maintain ordering
|
||||
* while in memory if the contents change. Represented
|
||||
* as {@link java.util.Set}.
|
||||
*
|
||||
* @see jakarta.persistence.OrderBy
|
||||
* @see org.hibernate.annotations.OrderBy
|
||||
*/
|
||||
ORDERED_SET( PluralAttribute.CollectionType.SET ),
|
||||
|
||||
|
@ -76,6 +82,9 @@ public enum CollectionClassification {
|
|||
* A sorted {@link #MAP} using either natural sorting of the keys or a
|
||||
* specified {@link java.util.Comparator}. Represented
|
||||
* as {@link java.util.SortedMap} or {@link java.util.Map}
|
||||
*
|
||||
* @see org.hibernate.annotations.SortNatural
|
||||
* @see org.hibernate.annotations.SortComparator
|
||||
*/
|
||||
SORTED_MAP( PluralAttribute.CollectionType.MAP ),
|
||||
|
||||
|
@ -84,6 +93,9 @@ public enum CollectionClassification {
|
|||
* as the collection is loaded. Does not maintain ordering
|
||||
* while in memory if the contents change. Represented
|
||||
* as {@link java.util.Map}.
|
||||
*
|
||||
* @see jakarta.persistence.OrderBy
|
||||
* @see org.hibernate.annotations.OrderBy
|
||||
*/
|
||||
ORDERED_MAP( PluralAttribute.CollectionType.MAP );
|
||||
|
||||
|
|
|
@ -7,7 +7,6 @@
|
|||
package org.hibernate.query.internal;
|
||||
|
||||
import java.lang.reflect.ParameterizedType;
|
||||
import java.lang.reflect.Type;
|
||||
import java.util.function.Consumer;
|
||||
|
||||
import org.hibernate.boot.model.convert.internal.ConverterHelper;
|
||||
|
@ -118,7 +117,7 @@ public class ResultMementoBasicStandard implements ResultMementoBasic {
|
|||
}
|
||||
else if ( UserType.class.isAssignableFrom( registeredJtd.getJavaTypeClass() ) ) {
|
||||
final ManagedBean<UserType<?>> userTypeBean = (ManagedBean) beanRegistry.getBean( registeredJtd.getJavaTypeClass() );
|
||||
// todo (6.0) : is this the best approach? or should we keep a Class<? extends UserType> -> CustomType mapping somewhere?
|
||||
// todo (6.0) : is this the best approach? or should we keep a Class<? extends UserType> -> @Type mapping somewhere?
|
||||
explicitType = new CustomType<>( (UserType<Object>) userTypeBean.getBeanInstance(), typeConfiguration );
|
||||
explicitJavaTypeDescriptor = explicitType.getJavaTypeDescriptor();
|
||||
}
|
||||
|
@ -135,8 +134,8 @@ public class ResultMementoBasicStandard implements ResultMementoBasic {
|
|||
private BasicJavaType<?> determineDomainJavaType(
|
||||
ParameterizedType parameterizedType,
|
||||
JavaTypeRegistry jtdRegistry) {
|
||||
final Type[] typeParameters = parameterizedType.getActualTypeArguments();
|
||||
final Type domainTypeType = typeParameters[ 0 ];
|
||||
final java.lang.reflect.Type[] typeParameters = parameterizedType.getActualTypeArguments();
|
||||
final java.lang.reflect.Type domainTypeType = typeParameters[ 0 ];
|
||||
final Class<?> domainClass = (Class<?>) domainTypeType;
|
||||
|
||||
return (BasicJavaType<?>) jtdRegistry.getDescriptor( domainClass );
|
||||
|
@ -145,7 +144,7 @@ public class ResultMementoBasicStandard implements ResultMementoBasic {
|
|||
private BasicValuedMapping resolveUnderlyingMapping(
|
||||
ParameterizedType parameterizedType,
|
||||
TypeConfiguration typeConfiguration) {
|
||||
final Type[] typeParameters = parameterizedType.getActualTypeArguments();
|
||||
final java.lang.reflect.Type[] typeParameters = parameterizedType.getActualTypeArguments();
|
||||
return typeConfiguration.standardBasicTypeForJavaType( (Class) typeParameters[ 1 ] );
|
||||
}
|
||||
|
||||
|
|
|
@ -20,6 +20,7 @@ import org.hibernate.collection.spi.PersistentArrayHolder;
|
|||
import org.hibernate.collection.spi.PersistentCollection;
|
||||
import org.hibernate.engine.spi.SessionFactoryImplementor;
|
||||
import org.hibernate.engine.spi.SharedSessionContractImplementor;
|
||||
import org.hibernate.metamodel.CollectionClassification;
|
||||
import org.hibernate.persister.collection.CollectionPersister;
|
||||
import org.hibernate.type.spi.TypeConfiguration;
|
||||
|
||||
|
@ -43,6 +44,11 @@ public class ArrayType extends CollectionType {
|
|||
return arrayClass;
|
||||
}
|
||||
|
||||
@Override
|
||||
public CollectionClassification getCollectionClassification() {
|
||||
return CollectionClassification.ARRAY;
|
||||
}
|
||||
|
||||
@Override
|
||||
public PersistentCollection instantiate(SharedSessionContractImplementor session, CollectionPersister persister, Object key)
|
||||
throws HibernateException {
|
||||
|
|
|
@ -13,6 +13,7 @@ import org.hibernate.HibernateException;
|
|||
import org.hibernate.collection.spi.PersistentBag;
|
||||
import org.hibernate.collection.spi.PersistentCollection;
|
||||
import org.hibernate.engine.spi.SharedSessionContractImplementor;
|
||||
import org.hibernate.metamodel.CollectionClassification;
|
||||
import org.hibernate.persister.collection.CollectionPersister;
|
||||
import org.hibernate.type.spi.TypeConfiguration;
|
||||
|
||||
|
@ -23,9 +24,8 @@ public class BagType extends CollectionType {
|
|||
}
|
||||
|
||||
@Override
|
||||
public PersistentCollection instantiate(SharedSessionContractImplementor session, CollectionPersister persister, Object key)
|
||||
throws HibernateException {
|
||||
return new PersistentBag( session );
|
||||
public CollectionClassification getCollectionClassification() {
|
||||
return CollectionClassification.BAG;
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -33,6 +33,12 @@ public class BagType extends CollectionType {
|
|||
return Collection.class;
|
||||
}
|
||||
|
||||
@Override
|
||||
public PersistentCollection instantiate(SharedSessionContractImplementor session, CollectionPersister persister, Object key)
|
||||
throws HibernateException {
|
||||
return new PersistentBag( session );
|
||||
}
|
||||
|
||||
@Override
|
||||
public PersistentCollection wrap(SharedSessionContractImplementor session, Object collection) {
|
||||
return new PersistentBag( session, (Collection) collection );
|
||||
|
|
|
@ -37,6 +37,7 @@ import org.hibernate.internal.CoreMessageLogger;
|
|||
import org.hibernate.internal.util.MarkerObject;
|
||||
import org.hibernate.internal.util.collections.ArrayHelper;
|
||||
import org.hibernate.internal.util.collections.CollectionHelper;
|
||||
import org.hibernate.metamodel.CollectionClassification;
|
||||
import org.hibernate.persister.collection.CollectionPersister;
|
||||
import org.hibernate.persister.collection.QueryableCollection;
|
||||
import org.hibernate.persister.entity.EntityPersister;
|
||||
|
@ -74,6 +75,8 @@ public abstract class CollectionType extends AbstractType implements Association
|
|||
this.foreignKeyPropertyName = foreignKeyPropertyName;
|
||||
}
|
||||
|
||||
public abstract CollectionClassification getCollectionClassification();
|
||||
|
||||
public String getRole() {
|
||||
return role;
|
||||
}
|
||||
|
|
|
@ -10,11 +10,12 @@ import java.util.Iterator;
|
|||
import java.util.Map;
|
||||
|
||||
import org.hibernate.HibernateException;
|
||||
import org.hibernate.MappingException;
|
||||
import org.hibernate.collection.spi.PersistentCollection;
|
||||
import org.hibernate.engine.spi.SessionFactoryImplementor;
|
||||
import org.hibernate.engine.spi.SharedSessionContractImplementor;
|
||||
import org.hibernate.metamodel.CollectionClassification;
|
||||
import org.hibernate.persister.collection.CollectionPersister;
|
||||
import org.hibernate.resource.beans.spi.ManagedBean;
|
||||
import org.hibernate.type.spi.TypeConfiguration;
|
||||
import org.hibernate.usertype.LoggableUserType;
|
||||
import org.hibernate.usertype.UserCollectionType;
|
||||
|
@ -32,30 +33,24 @@ public class CustomCollectionType extends CollectionType {
|
|||
private final boolean customLogging;
|
||||
|
||||
public CustomCollectionType(
|
||||
Class<? extends UserCollectionType> userTypeClass,
|
||||
ManagedBean<? extends UserCollectionType> userTypeBean,
|
||||
String role,
|
||||
String foreignKeyPropertyName,
|
||||
TypeConfiguration typeConfiguration) {
|
||||
super( typeConfiguration, role, foreignKeyPropertyName );
|
||||
|
||||
if ( !UserCollectionType.class.isAssignableFrom( userTypeClass ) ) {
|
||||
throw new MappingException( "Custom type does not implement UserCollectionType: " + userTypeClass.getName() );
|
||||
}
|
||||
|
||||
userType = createUserCollectionType( userTypeClass );
|
||||
userType = userTypeBean.getBeanInstance();
|
||||
customLogging = userType instanceof LoggableUserType;
|
||||
}
|
||||
|
||||
private static UserCollectionType createUserCollectionType(Class<? extends UserCollectionType> userTypeClass) {
|
||||
try {
|
||||
return userTypeClass.newInstance();
|
||||
}
|
||||
catch (InstantiationException ie) {
|
||||
throw new MappingException( "Cannot instantiate custom type: " + userTypeClass.getName() );
|
||||
}
|
||||
catch (IllegalAccessException iae) {
|
||||
throw new MappingException( "IllegalAccessException trying to instantiate custom type: " + userTypeClass.getName() );
|
||||
}
|
||||
@Override
|
||||
public Class getReturnedClass() {
|
||||
return userType.instantiate( -1 ).getClass();
|
||||
}
|
||||
|
||||
@Override
|
||||
public CollectionClassification getCollectionClassification() {
|
||||
return userType.getClassification();
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -69,11 +64,6 @@ public class CustomCollectionType extends CollectionType {
|
|||
return userType.wrap( session, collection );
|
||||
}
|
||||
|
||||
@Override
|
||||
public Class getReturnedClass() {
|
||||
return userType.instantiate( -1 ).getClass();
|
||||
}
|
||||
|
||||
@Override
|
||||
public Object instantiate(int anticipatedType) {
|
||||
return userType.instantiate( anticipatedType );
|
||||
|
|
|
@ -12,6 +12,7 @@ import org.hibernate.HibernateException;
|
|||
import org.hibernate.collection.spi.PersistentIdentifierBag;
|
||||
import org.hibernate.collection.spi.PersistentCollection;
|
||||
import org.hibernate.engine.spi.SharedSessionContractImplementor;
|
||||
import org.hibernate.metamodel.CollectionClassification;
|
||||
import org.hibernate.persister.collection.CollectionPersister;
|
||||
import org.hibernate.type.spi.TypeConfiguration;
|
||||
|
||||
|
@ -21,6 +22,11 @@ public class IdentifierBagType extends CollectionType {
|
|||
super( typeConfiguration, role, propertyRef );
|
||||
}
|
||||
|
||||
@Override
|
||||
public CollectionClassification getCollectionClassification() {
|
||||
return CollectionClassification.ID_BAG;
|
||||
}
|
||||
|
||||
@Override
|
||||
public PersistentCollection instantiate(
|
||||
SharedSessionContractImplementor session,
|
||||
|
|
|
@ -12,15 +12,23 @@ import java.util.List;
|
|||
import org.hibernate.collection.spi.PersistentList;
|
||||
import org.hibernate.collection.spi.PersistentCollection;
|
||||
import org.hibernate.engine.spi.SharedSessionContractImplementor;
|
||||
import org.hibernate.metamodel.CollectionClassification;
|
||||
import org.hibernate.persister.collection.CollectionPersister;
|
||||
import org.hibernate.type.spi.TypeConfiguration;
|
||||
|
||||
import static org.hibernate.metamodel.CollectionClassification.LIST;
|
||||
|
||||
public class ListType extends CollectionType {
|
||||
|
||||
public ListType(TypeConfiguration typeConfiguration, String role, String propertyRef) {
|
||||
super( typeConfiguration, role, propertyRef );
|
||||
}
|
||||
|
||||
@Override
|
||||
public CollectionClassification getCollectionClassification() {
|
||||
return LIST;
|
||||
}
|
||||
|
||||
@Override
|
||||
public PersistentCollection instantiate(SharedSessionContractImplementor session, CollectionPersister persister, Object key) {
|
||||
return new PersistentList( session );
|
||||
|
|
|
@ -14,6 +14,7 @@ import org.hibernate.HibernateException;
|
|||
import org.hibernate.collection.spi.PersistentMap;
|
||||
import org.hibernate.collection.spi.PersistentCollection;
|
||||
import org.hibernate.engine.spi.SharedSessionContractImplementor;
|
||||
import org.hibernate.metamodel.CollectionClassification;
|
||||
import org.hibernate.persister.collection.CollectionPersister;
|
||||
import org.hibernate.type.spi.TypeConfiguration;
|
||||
|
||||
|
@ -24,6 +25,11 @@ public class MapType extends CollectionType {
|
|||
super( typeConfiguration, role, propertyRef );
|
||||
}
|
||||
|
||||
@Override
|
||||
public CollectionClassification getCollectionClassification() {
|
||||
return CollectionClassification.MAP;
|
||||
}
|
||||
|
||||
@Override
|
||||
public PersistentCollection instantiate(
|
||||
SharedSessionContractImplementor session,
|
||||
|
|
|
@ -7,6 +7,7 @@
|
|||
package org.hibernate.type;
|
||||
|
||||
import org.hibernate.internal.util.collections.CollectionHelper;
|
||||
import org.hibernate.metamodel.CollectionClassification;
|
||||
import org.hibernate.type.spi.TypeConfiguration;
|
||||
|
||||
/**
|
||||
|
@ -18,6 +19,11 @@ public class OrderedMapType extends MapType {
|
|||
super( typeConfiguration, role, propertyRef );
|
||||
}
|
||||
|
||||
@Override
|
||||
public CollectionClassification getCollectionClassification() {
|
||||
return CollectionClassification.ORDERED_MAP;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Object instantiate(int anticipatedSize) {
|
||||
return anticipatedSize > 0
|
||||
|
|
|
@ -7,6 +7,7 @@
|
|||
package org.hibernate.type;
|
||||
|
||||
import org.hibernate.internal.util.collections.CollectionHelper;
|
||||
import org.hibernate.metamodel.CollectionClassification;
|
||||
import org.hibernate.type.spi.TypeConfiguration;
|
||||
|
||||
/**
|
||||
|
@ -18,6 +19,11 @@ public class OrderedSetType extends SetType {
|
|||
super( typeConfiguration, role, propertyRef );
|
||||
}
|
||||
|
||||
@Override
|
||||
public CollectionClassification getCollectionClassification() {
|
||||
return CollectionClassification.ORDERED_SET;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Object instantiate(int anticipatedSize) {
|
||||
return anticipatedSize > 0
|
||||
|
|
|
@ -10,6 +10,7 @@ import org.hibernate.collection.spi.PersistentSet;
|
|||
import org.hibernate.collection.spi.PersistentCollection;
|
||||
import org.hibernate.engine.spi.SharedSessionContractImplementor;
|
||||
import org.hibernate.internal.util.collections.CollectionHelper;
|
||||
import org.hibernate.metamodel.CollectionClassification;
|
||||
import org.hibernate.persister.collection.CollectionPersister;
|
||||
import org.hibernate.type.spi.TypeConfiguration;
|
||||
|
||||
|
@ -20,8 +21,8 @@ public class SetType extends CollectionType {
|
|||
}
|
||||
|
||||
@Override
|
||||
public PersistentCollection instantiate(SharedSessionContractImplementor session, CollectionPersister persister, Object key) {
|
||||
return new PersistentSet( session );
|
||||
public CollectionClassification getCollectionClassification() {
|
||||
return CollectionClassification.SET;
|
||||
}
|
||||
|
||||
@Override
|
||||
|
@ -29,6 +30,11 @@ public class SetType extends CollectionType {
|
|||
return java.util.Set.class;
|
||||
}
|
||||
|
||||
@Override
|
||||
public PersistentCollection instantiate(SharedSessionContractImplementor session, CollectionPersister persister, Object key) {
|
||||
return new PersistentSet( session );
|
||||
}
|
||||
|
||||
@Override
|
||||
public PersistentCollection wrap(SharedSessionContractImplementor session, Object collection) {
|
||||
return new PersistentSet( session, (java.util.Set) collection );
|
||||
|
|
|
@ -12,6 +12,7 @@ import java.util.TreeMap;
|
|||
import org.hibernate.collection.spi.PersistentSortedMap;
|
||||
import org.hibernate.collection.spi.PersistentCollection;
|
||||
import org.hibernate.engine.spi.SharedSessionContractImplementor;
|
||||
import org.hibernate.metamodel.CollectionClassification;
|
||||
import org.hibernate.persister.collection.CollectionPersister;
|
||||
import org.hibernate.type.spi.TypeConfiguration;
|
||||
|
||||
|
@ -26,14 +27,19 @@ public class SortedMapType extends MapType {
|
|||
}
|
||||
|
||||
@Override
|
||||
public PersistentCollection instantiate(SharedSessionContractImplementor session, CollectionPersister persister, Object key) {
|
||||
return new PersistentSortedMap( session, comparator );
|
||||
public CollectionClassification getCollectionClassification() {
|
||||
return CollectionClassification.SORTED_MAP;
|
||||
}
|
||||
|
||||
public Class getReturnedClass() {
|
||||
return java.util.SortedMap.class;
|
||||
}
|
||||
|
||||
@Override
|
||||
public PersistentCollection instantiate(SharedSessionContractImplementor session, CollectionPersister persister, Object key) {
|
||||
return new PersistentSortedMap( session, comparator );
|
||||
}
|
||||
|
||||
@SuppressWarnings( {"unchecked"})
|
||||
public Object instantiate(int anticipatedSize) {
|
||||
return new TreeMap(comparator);
|
||||
|
|
|
@ -12,6 +12,7 @@ import java.util.TreeSet;
|
|||
import org.hibernate.collection.spi.PersistentSortedSet;
|
||||
import org.hibernate.collection.spi.PersistentCollection;
|
||||
import org.hibernate.engine.spi.SharedSessionContractImplementor;
|
||||
import org.hibernate.metamodel.CollectionClassification;
|
||||
import org.hibernate.persister.collection.CollectionPersister;
|
||||
import org.hibernate.type.spi.TypeConfiguration;
|
||||
|
||||
|
@ -25,14 +26,19 @@ public class SortedSetType extends SetType {
|
|||
}
|
||||
|
||||
@Override
|
||||
public PersistentCollection instantiate(SharedSessionContractImplementor session, CollectionPersister persister, Object key) {
|
||||
return new PersistentSortedSet( session, comparator );
|
||||
public CollectionClassification getCollectionClassification() {
|
||||
return CollectionClassification.SORTED_SET;
|
||||
}
|
||||
|
||||
public Class getReturnedClass() {
|
||||
return java.util.SortedSet.class;
|
||||
}
|
||||
|
||||
@Override
|
||||
public PersistentCollection instantiate(SharedSessionContractImplementor session, CollectionPersister persister, Object key) {
|
||||
return new PersistentSortedSet( session, comparator );
|
||||
}
|
||||
|
||||
@SuppressWarnings( {"unchecked"})
|
||||
public Object instantiate(int anticipatedSize) {
|
||||
return new TreeSet(comparator);
|
||||
|
|
|
@ -12,15 +12,27 @@ import java.util.Map;
|
|||
import org.hibernate.HibernateException;
|
||||
import org.hibernate.collection.spi.PersistentCollection;
|
||||
import org.hibernate.engine.spi.SharedSessionContractImplementor;
|
||||
import org.hibernate.metamodel.CollectionClassification;
|
||||
import org.hibernate.persister.collection.CollectionPersister;
|
||||
|
||||
/**
|
||||
* A custom type for mapping user-written classes that implement {@code PersistentCollection}
|
||||
*
|
||||
* @author Gavin King
|
||||
* @see PersistentCollection
|
||||
*
|
||||
* @author Gavin King
|
||||
* @author Steve Ebersole
|
||||
*/
|
||||
public interface UserCollectionType {
|
||||
/**
|
||||
* The classification mapped by this custom type
|
||||
*/
|
||||
CollectionClassification getClassification();
|
||||
|
||||
/**
|
||||
* The Java type that this type maps.
|
||||
*/
|
||||
Class<?> getCollectionClass();
|
||||
|
||||
/**
|
||||
* Instantiate an uninitialized instance of the collection wrapper
|
||||
|
|
|
@ -10,6 +10,7 @@ import java.util.Properties;
|
|||
import java.util.function.BiConsumer;
|
||||
|
||||
import org.hibernate.MappingException;
|
||||
import org.hibernate.annotations.Type;
|
||||
import org.hibernate.type.BasicType;
|
||||
import org.hibernate.type.spi.TypeConfiguration;
|
||||
import org.hibernate.type.spi.TypeConfigurationAware;
|
||||
|
@ -18,7 +19,7 @@ import org.hibernate.type.spi.TypeConfigurationAware;
|
|||
* Convenience UserType implementation to mimic the legacy `@Type` annotation
|
||||
* which based on the {@code hbm.xml} mapping's String-based type support
|
||||
*
|
||||
* @see org.hibernate.annotations.CustomType
|
||||
* @see Type
|
||||
*/
|
||||
public class UserTypeLegacyBridge extends BaseUserTypeSupport<Object> implements ParameterizedType, TypeConfigurationAware {
|
||||
public static final String TYPE_NAME_PARAM_KEY = "hbm-type-name";
|
||||
|
|
|
@ -9,7 +9,7 @@ package org.hibernate.orm.test.annotations.basic;
|
|||
import java.sql.Types;
|
||||
import java.util.Set;
|
||||
|
||||
import org.hibernate.annotations.CustomType;
|
||||
import org.hibernate.annotations.Type;
|
||||
import org.hibernate.boot.Metadata;
|
||||
import org.hibernate.boot.MetadataSources;
|
||||
import org.hibernate.boot.registry.StandardServiceRegistry;
|
||||
|
@ -49,7 +49,7 @@ public class CollectionAsBasicTest {
|
|||
public Integer id;
|
||||
public String name;
|
||||
@Basic
|
||||
@CustomType( DelimitedStringsJavaTypeDescriptor.class )
|
||||
@Type( DelimitedStringsJavaTypeDescriptor.class )
|
||||
Set<String> tags;
|
||||
}
|
||||
|
||||
|
|
|
@ -6,7 +6,7 @@
|
|||
*/
|
||||
package org.hibernate.orm.test.annotations.generics;
|
||||
|
||||
import org.hibernate.annotations.CustomType;
|
||||
import org.hibernate.annotations.Type;
|
||||
|
||||
import jakarta.persistence.Entity;
|
||||
import jakarta.persistence.GeneratedValue;
|
||||
|
@ -22,7 +22,7 @@ public class Gene<T, STE extends Enum> {
|
|||
private Integer id;
|
||||
private STE state;
|
||||
|
||||
@CustomType( StateType.class )
|
||||
@Type( StateType.class )
|
||||
public STE getState() {
|
||||
return state;
|
||||
}
|
||||
|
|
|
@ -23,7 +23,7 @@
|
|||
*/
|
||||
package org.hibernate.orm.test.annotations.type.dynamicparameterized;
|
||||
|
||||
import org.hibernate.annotations.CustomType;
|
||||
import org.hibernate.annotations.Type;
|
||||
import org.hibernate.annotations.Parameter;
|
||||
|
||||
import jakarta.persistence.Access;
|
||||
|
@ -41,26 +41,26 @@ import jakarta.persistence.Table;
|
|||
public class Entity1 extends AbstractEntity {
|
||||
|
||||
@Column(name = "PROP1")
|
||||
@CustomType( MyStringType.class )
|
||||
@Type( MyStringType.class )
|
||||
String entity1_Prop1;
|
||||
|
||||
@Column(name = "PROP2")
|
||||
@CustomType( MyStringType.class )
|
||||
@Type( MyStringType.class )
|
||||
String entity1_Prop2;
|
||||
|
||||
@Column(name = "PROP3")
|
||||
@CustomType( value = MyStringType.class, parameters = @Parameter(name = "suffix", value = "foo"))
|
||||
@Type( value = MyStringType.class, parameters = @Parameter(name = "suffix", value = "foo"))
|
||||
String entity1_Prop3;
|
||||
|
||||
@Column(name = "PROP4")
|
||||
@CustomType( value = MyStringType.class, parameters = @Parameter(name = "suffix", value = "bar"))
|
||||
@Type( value = MyStringType.class, parameters = @Parameter(name = "suffix", value = "bar"))
|
||||
String entity1_Prop4;
|
||||
|
||||
@Column(name = "PROP5")
|
||||
@CustomType( MyStringType.class )
|
||||
@Type( MyStringType.class )
|
||||
String entity1_Prop5;
|
||||
|
||||
@Column(name = "PROP6")
|
||||
@CustomType( MyStringType.class )
|
||||
@Type( MyStringType.class )
|
||||
String entity1_Prop6;
|
||||
}
|
||||
|
|
|
@ -23,7 +23,7 @@
|
|||
*/
|
||||
package org.hibernate.orm.test.annotations.type.dynamicparameterized;
|
||||
|
||||
import org.hibernate.annotations.CustomType;
|
||||
import org.hibernate.annotations.Type;
|
||||
import org.hibernate.annotations.Parameter;
|
||||
|
||||
import jakarta.persistence.Access;
|
||||
|
@ -41,26 +41,26 @@ import jakarta.persistence.Table;
|
|||
public class Entity2 extends AbstractEntity {
|
||||
|
||||
@Column(name = "PROP1")
|
||||
@CustomType( MyStringType.class )
|
||||
@Type( MyStringType.class )
|
||||
String entity2_Prop1;
|
||||
|
||||
@Column(name = "PROP2")
|
||||
@CustomType( MyStringType.class )
|
||||
@Type( MyStringType.class )
|
||||
String entity2_Prop2;
|
||||
|
||||
@Column(name = "PROP3")
|
||||
@CustomType( MyStringType.class )
|
||||
@Type( MyStringType.class )
|
||||
String entity2_Prop3;
|
||||
|
||||
@Column(name = "PROP4")
|
||||
@CustomType( MyStringType.class )
|
||||
@Type( MyStringType.class )
|
||||
String entity2_Prop4;
|
||||
|
||||
@Column(name = "PROP5")
|
||||
@CustomType( value = MyStringType.class, parameters = @Parameter(name = "suffix", value = "blah"))
|
||||
@Type( value = MyStringType.class, parameters = @Parameter(name = "suffix", value = "blah"))
|
||||
String entity2_Prop5;
|
||||
|
||||
@Column(name = "PROP6")
|
||||
@CustomType( value = MyStringType.class, parameters = @Parameter(name = "suffix", value = "yeah"))
|
||||
@Type( value = MyStringType.class, parameters = @Parameter(name = "suffix", value = "yeah"))
|
||||
String entity2_Prop6;
|
||||
}
|
||||
|
|
|
@ -7,14 +7,12 @@
|
|||
package org.hibernate.orm.test.bytecode.enhancement.lazy.cache;
|
||||
|
||||
import java.nio.charset.Charset;
|
||||
import java.sql.Types;
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
||||
import org.hibernate.annotations.Cache;
|
||||
import org.hibernate.annotations.CacheConcurrencyStrategy;
|
||||
import org.hibernate.annotations.CustomType;
|
||||
import org.hibernate.annotations.JdbcTypeCode;
|
||||
import org.hibernate.annotations.Type;
|
||||
import org.hibernate.cfg.AvailableSettings;
|
||||
import org.hibernate.cfg.Configuration;
|
||||
import org.hibernate.usertype.UserTypeLegacyBridge;
|
||||
|
@ -97,7 +95,7 @@ public class LazyInCacheTest extends BaseCoreFunctionalTestCase {
|
|||
List<Tag> tags = new ArrayList<>();
|
||||
|
||||
@Basic( fetch = FetchType.LAZY )
|
||||
@CustomType( BinaryCustomType.class )
|
||||
@Type( BinaryCustomType.class )
|
||||
// @JdbcTypeCode(Types.LONGVARBINARY)
|
||||
byte[] data;
|
||||
}
|
||||
|
|
|
@ -6,10 +6,6 @@
|
|||
*/
|
||||
package org.hibernate.orm.test.cfg.annotations;
|
||||
|
||||
import static org.junit.Assert.assertEquals;
|
||||
import static org.mockito.Mockito.mock;
|
||||
import static org.mockito.Mockito.when;
|
||||
|
||||
import java.sql.SQLException;
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
|
@ -22,15 +18,20 @@ import org.hibernate.cfg.AnnotatedJoinColumn;
|
|||
import org.hibernate.cfg.InheritanceState;
|
||||
import org.hibernate.cfg.PropertyHolder;
|
||||
import org.hibernate.cfg.annotations.CollectionBinder;
|
||||
import org.hibernate.collection.internal.StandardBagSemantics;
|
||||
import org.hibernate.mapping.Collection;
|
||||
import org.hibernate.mapping.PersistentClass;
|
||||
import org.hibernate.mapping.Table;
|
||||
|
||||
import org.hibernate.testing.TestForIssue;
|
||||
import org.hibernate.testing.junit4.BaseUnitTestCase;
|
||||
import org.junit.Test;
|
||||
|
||||
import org.mockito.Mockito;
|
||||
|
||||
import static org.junit.Assert.assertEquals;
|
||||
import static org.mockito.Mockito.mock;
|
||||
import static org.mockito.Mockito.when;
|
||||
|
||||
/**
|
||||
* Test for HHH-10106
|
||||
*
|
||||
|
@ -56,7 +57,7 @@ public class CollectionBinderTest extends BaseUnitTestCase {
|
|||
|
||||
String expectMessage = "Association [abc] for entity [CollectionBinderTest] references unmapped class [List]";
|
||||
try {
|
||||
new CollectionBinder( (t) -> StandardBagSemantics.INSTANCE, false, buildingContext ) {
|
||||
new CollectionBinder( null, false, buildingContext ) {
|
||||
|
||||
{
|
||||
final PropertyHolder propertyHolder = Mockito.mock(PropertyHolder.class);
|
||||
|
|
|
@ -14,7 +14,7 @@ import java.sql.Types;
|
|||
import java.util.Comparator;
|
||||
|
||||
import org.hibernate.HibernateException;
|
||||
import org.hibernate.annotations.CustomType;
|
||||
import org.hibernate.annotations.Type;
|
||||
import org.hibernate.cfg.AvailableSettings;
|
||||
import org.hibernate.engine.spi.SharedSessionContractImplementor;
|
||||
import org.hibernate.usertype.UserType;
|
||||
|
@ -71,7 +71,7 @@ public class UserTypeComparableIdTest {
|
|||
public static class SomeEntity {
|
||||
|
||||
@Id
|
||||
@CustomType( CustomIdType.class )
|
||||
@Type( CustomIdType.class )
|
||||
@Column(name = "id")
|
||||
private CustomId customId;
|
||||
|
||||
|
|
|
@ -18,7 +18,7 @@ import jakarta.persistence.Id;
|
|||
import jakarta.persistence.Table;
|
||||
|
||||
import org.hibernate.HibernateException;
|
||||
import org.hibernate.annotations.CustomType;
|
||||
import org.hibernate.annotations.Type;
|
||||
import org.hibernate.engine.spi.SharedSessionContractImplementor;
|
||||
import org.hibernate.usertype.UserType;
|
||||
|
||||
|
@ -63,7 +63,7 @@ public class UserTypeNonComparableIdTest {
|
|||
public static class SomeEntity {
|
||||
|
||||
@Id
|
||||
@CustomType( CustomIdType.class )
|
||||
@Type( CustomIdType.class )
|
||||
@Column(name = "id")
|
||||
private CustomId customId;
|
||||
|
||||
|
|
|
@ -17,7 +17,7 @@ import java.util.Objects;
|
|||
import org.hibernate.HibernateException;
|
||||
import org.hibernate.Session;
|
||||
import org.hibernate.SessionFactory;
|
||||
import org.hibernate.annotations.CustomType;
|
||||
import org.hibernate.annotations.Type;
|
||||
import org.hibernate.cfg.AvailableSettings;
|
||||
import org.hibernate.engine.spi.SharedSessionContractImplementor;
|
||||
import org.hibernate.orm.test.jpa.BaseEntityManagerFunctionalTestCase;
|
||||
|
@ -122,7 +122,7 @@ public class QueryParametersValidationTest extends BaseEntityManagerFunctionalTe
|
|||
@GeneratedValue(strategy = GenerationType.AUTO)
|
||||
private Long id;
|
||||
|
||||
@CustomType( QueryParametersValidationTest.BooleanUserType.class )
|
||||
@Type( QueryParametersValidationTest.BooleanUserType.class )
|
||||
private boolean active;
|
||||
}
|
||||
|
||||
|
|
|
@ -15,6 +15,7 @@ import java.util.Arrays;
|
|||
import java.util.List;
|
||||
|
||||
import org.hibernate.HibernateException;
|
||||
import org.hibernate.annotations.Type;
|
||||
import org.hibernate.engine.spi.SessionFactoryImplementor;
|
||||
import org.hibernate.engine.spi.SharedSessionContractImplementor;
|
||||
import org.hibernate.query.TypedParameterValue;
|
||||
|
@ -114,7 +115,7 @@ public class TypedValueParametersTest {
|
|||
@Id
|
||||
private int id;
|
||||
|
||||
@org.hibernate.annotations.CustomType( TagUserType.class )
|
||||
@Type( TagUserType.class )
|
||||
@Column(name = "tags")
|
||||
private List<String> tags = new ArrayList<>();
|
||||
|
||||
|
|
|
@ -9,11 +9,9 @@ package org.hibernate.orm.test.mapping.collections;
|
|||
import java.util.Collection;
|
||||
import java.util.List;
|
||||
|
||||
import org.hibernate.annotations.CollectionClassificationType;
|
||||
import org.hibernate.cfg.AvailableSettings;
|
||||
import org.hibernate.mapping.Bag;
|
||||
import org.hibernate.mapping.Property;
|
||||
import org.hibernate.metamodel.CollectionClassification;
|
||||
|
||||
import org.hibernate.testing.orm.junit.DomainModel;
|
||||
import org.hibernate.testing.orm.junit.DomainModelScope;
|
||||
|
@ -26,6 +24,7 @@ import jakarta.persistence.Basic;
|
|||
import jakarta.persistence.ElementCollection;
|
||||
import jakarta.persistence.Entity;
|
||||
import jakarta.persistence.Id;
|
||||
import jakarta.persistence.OrderColumn;
|
||||
import jakarta.persistence.Table;
|
||||
|
||||
import static org.assertj.core.api.Assertions.assertThat;
|
||||
|
@ -82,11 +81,11 @@ public class ImplicitListAsBagSemanticsTests {
|
|||
private Collection<String> implicitBag;
|
||||
|
||||
@ElementCollection
|
||||
@CollectionClassificationType( CollectionClassification.BAG )
|
||||
@org.hibernate.annotations.Bag
|
||||
private List<String> explicitBag;
|
||||
|
||||
@ElementCollection
|
||||
@CollectionClassificationType( CollectionClassification.LIST )
|
||||
@OrderColumn( name = "explicit_list_position" )
|
||||
private List<String> explicitList;
|
||||
|
||||
private AnEntity() {
|
||||
|
|
|
@ -6,12 +6,9 @@
|
|||
*/
|
||||
package org.hibernate.orm.test.mapping.collections;
|
||||
|
||||
import java.lang.annotation.Annotation;
|
||||
import java.util.Collection;
|
||||
import java.util.List;
|
||||
|
||||
import org.hibernate.annotations.CollectionClassificationType;
|
||||
import org.hibernate.cfg.AvailableSettings;
|
||||
import org.hibernate.mapping.Bag;
|
||||
import org.hibernate.mapping.Property;
|
||||
import org.hibernate.metamodel.CollectionClassification;
|
||||
|
@ -19,7 +16,6 @@ import org.hibernate.metamodel.CollectionClassification;
|
|||
import org.hibernate.testing.orm.junit.DomainModel;
|
||||
import org.hibernate.testing.orm.junit.DomainModelScope;
|
||||
import org.hibernate.testing.orm.junit.ServiceRegistry;
|
||||
import org.hibernate.testing.orm.junit.Setting;
|
||||
import org.hibernate.testing.orm.junit.SettingProvider;
|
||||
import org.junit.jupiter.api.Test;
|
||||
|
||||
|
@ -27,6 +23,7 @@ import jakarta.persistence.Basic;
|
|||
import jakarta.persistence.ElementCollection;
|
||||
import jakarta.persistence.Entity;
|
||||
import jakarta.persistence.Id;
|
||||
import jakarta.persistence.OrderColumn;
|
||||
import jakarta.persistence.Table;
|
||||
|
||||
import static org.assertj.core.api.Assertions.assertThat;
|
||||
|
@ -75,11 +72,11 @@ public class ImplicitListAsListSemanticsTests {
|
|||
private Collection<String> implicitBag;
|
||||
|
||||
@ElementCollection
|
||||
@CollectionClassificationType( CollectionClassification.BAG )
|
||||
@org.hibernate.annotations.Bag
|
||||
private List<String> explicitBag;
|
||||
|
||||
@ElementCollection
|
||||
@CollectionClassificationType( CollectionClassification.LIST )
|
||||
@OrderColumn( name = "explicit_list_position" )
|
||||
private List<String> explicitList;
|
||||
|
||||
private AnEntity() {
|
||||
|
|
|
@ -9,11 +9,9 @@ package org.hibernate.orm.test.mapping.collections;
|
|||
import java.util.Collection;
|
||||
import java.util.List;
|
||||
|
||||
import org.hibernate.annotations.CollectionClassificationType;
|
||||
import org.hibernate.cfg.AvailableSettings;
|
||||
import org.hibernate.mapping.Bag;
|
||||
import org.hibernate.mapping.Property;
|
||||
import org.hibernate.metamodel.CollectionClassification;
|
||||
|
||||
import org.hibernate.testing.orm.junit.DomainModel;
|
||||
import org.hibernate.testing.orm.junit.DomainModelScope;
|
||||
|
@ -23,6 +21,7 @@ import jakarta.persistence.Basic;
|
|||
import jakarta.persistence.ElementCollection;
|
||||
import jakarta.persistence.Entity;
|
||||
import jakarta.persistence.Id;
|
||||
import jakarta.persistence.OrderColumn;
|
||||
import jakarta.persistence.Table;
|
||||
|
||||
import static org.assertj.core.api.Assertions.assertThat;
|
||||
|
@ -69,11 +68,11 @@ public class ImplicitListDefaultSemanticsTests {
|
|||
private Collection<String> implicitBag;
|
||||
|
||||
@ElementCollection
|
||||
@CollectionClassificationType( CollectionClassification.BAG )
|
||||
@org.hibernate.annotations.Bag
|
||||
private List<String> explicitBag;
|
||||
|
||||
@ElementCollection
|
||||
@CollectionClassificationType( CollectionClassification.LIST )
|
||||
@OrderColumn( name = "explicit_list_position" )
|
||||
private List<String> explicitList;
|
||||
|
||||
private AnEntity() {
|
||||
|
|
|
@ -20,7 +20,8 @@ import static org.assertj.core.api.Assertions.assertThat;
|
|||
* @author Steve Ebersole
|
||||
*/
|
||||
@DomainModel( annotatedClasses = {
|
||||
EntityWithBagAsCollection.class
|
||||
EntityWithBagAsCollection.class,
|
||||
EntityWithBagAsList.class
|
||||
} )
|
||||
public class BagTests {
|
||||
@Test
|
||||
|
@ -32,4 +33,14 @@ public class BagTests {
|
|||
assertThat( namesMapping.getCollectionSemantics().getCollectionClassification() ).isEqualTo( CollectionClassification.BAG );
|
||||
} );
|
||||
}
|
||||
|
||||
@Test
|
||||
public void verifyListMarkedAsBag(DomainModelScope scope) {
|
||||
scope.withHierarchy( EntityWithBagAsList.class, (entityDescriptor) -> {
|
||||
final Property names = entityDescriptor.getProperty( "names" );
|
||||
final Collection namesMapping = (Collection) names.getValue();
|
||||
|
||||
assertThat( namesMapping.getCollectionSemantics().getCollectionClassification() ).isEqualTo( CollectionClassification.BAG );
|
||||
} );
|
||||
}
|
||||
}
|
||||
|
|
|
@ -6,11 +6,9 @@
|
|||
*/
|
||||
package org.hibernate.orm.test.mapping.collections.classification.bag;
|
||||
|
||||
import java.util.Collection;
|
||||
import java.util.List;
|
||||
|
||||
import org.hibernate.annotations.CollectionClassificationType;
|
||||
import org.hibernate.metamodel.CollectionClassification;
|
||||
import org.hibernate.annotations.Bag;
|
||||
import org.hibernate.orm.test.mapping.collections.classification.Name;
|
||||
|
||||
import jakarta.persistence.Basic;
|
||||
|
@ -18,8 +16,6 @@ import jakarta.persistence.ElementCollection;
|
|||
import jakarta.persistence.Entity;
|
||||
import jakarta.persistence.Id;
|
||||
|
||||
import static org.hibernate.metamodel.CollectionClassification.BAG;
|
||||
|
||||
/**
|
||||
* @author Steve Ebersole
|
||||
*/
|
||||
|
@ -36,7 +32,7 @@ public class EntityWithBagAsList {
|
|||
|
||||
//tag::collections-bag-list-ex[]
|
||||
@ElementCollection
|
||||
@CollectionClassificationType( BAG )
|
||||
@Bag
|
||||
private List<Name> names;
|
||||
//end::collections-bag-list-ex[]
|
||||
|
||||
|
|
|
@ -1,63 +0,0 @@
|
|||
/*
|
||||
* Hibernate, Relational Persistence for Idiomatic Java
|
||||
*
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later
|
||||
* See the lgpl.txt file in the root directory or http://www.gnu.org/licenses/lgpl-2.1.html
|
||||
*/
|
||||
package org.hibernate.orm.test.mapping.collections.classification.explicit;
|
||||
|
||||
import java.util.Collection;
|
||||
|
||||
import org.hibernate.annotations.CollectionClassificationType;
|
||||
import org.hibernate.orm.test.mapping.collections.classification.Name;
|
||||
|
||||
import jakarta.persistence.Basic;
|
||||
import jakarta.persistence.ElementCollection;
|
||||
import jakarta.persistence.Entity;
|
||||
import jakarta.persistence.Id;
|
||||
|
||||
import static org.hibernate.metamodel.CollectionClassification.SET;
|
||||
|
||||
/**
|
||||
* @author Steve Ebersole
|
||||
*/
|
||||
//tag::collections-bag-set-ex[]
|
||||
@Entity
|
||||
public class EntityWithExplicitSetClassification {
|
||||
// ...
|
||||
//end::collections-bag-set-ex[]
|
||||
|
||||
@Id
|
||||
private Integer id;
|
||||
@Basic
|
||||
private String name;
|
||||
|
||||
//tag::collections-bag-set-ex[]
|
||||
@ElementCollection
|
||||
@CollectionClassificationType(SET)
|
||||
private Collection<Name> names;
|
||||
//end::collections-bag-set-ex[]
|
||||
|
||||
private EntityWithExplicitSetClassification() {
|
||||
// for Hibernate use
|
||||
}
|
||||
|
||||
public EntityWithExplicitSetClassification(Integer id, String name) {
|
||||
this.id = id;
|
||||
this.name = name;
|
||||
}
|
||||
|
||||
public Integer getId() {
|
||||
return id;
|
||||
}
|
||||
|
||||
public String getName() {
|
||||
return name;
|
||||
}
|
||||
|
||||
public void setName(String name) {
|
||||
this.name = name;
|
||||
}
|
||||
//tag::collections-bag-set-ex[]
|
||||
}
|
||||
//end::collections-bag-set-ex[]
|
|
@ -1,10 +1,10 @@
|
|||
/*
|
||||
* Hibernate, Relational Persistence for Idiomatic Java
|
||||
*
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later.
|
||||
* See the lgpl.txt file in the root directory or <http://www.gnu.org/licenses/lgpl-2.1.html>.
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later
|
||||
* See the lgpl.txt file in the root directory or http://www.gnu.org/licenses/lgpl-2.1.html
|
||||
*/
|
||||
package org.hibernate.orm.test.mapping.type.collection.custom.basic;
|
||||
package org.hibernate.orm.test.mapping.collections.custom.basic;
|
||||
|
||||
import jakarta.persistence.Entity;
|
||||
import jakarta.persistence.GeneratedValue;
|
|
@ -1,10 +1,10 @@
|
|||
/*
|
||||
* Hibernate, Relational Persistence for Idiomatic Java
|
||||
*
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later.
|
||||
* See the lgpl.txt file in the root directory or <http://www.gnu.org/licenses/lgpl-2.1.html>.
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later
|
||||
* See the lgpl.txt file in the root directory or http://www.gnu.org/licenses/lgpl-2.1.html
|
||||
*/
|
||||
package org.hibernate.orm.test.mapping.type.collection.custom.basic;
|
||||
package org.hibernate.orm.test.mapping.collections.custom.basic;
|
||||
|
||||
import java.util.List;
|
||||
|
|
@ -1,10 +1,10 @@
|
|||
/*
|
||||
* Hibernate, Relational Persistence for Idiomatic Java
|
||||
*
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later.
|
||||
* See the lgpl.txt file in the root directory or <http://www.gnu.org/licenses/lgpl-2.1.html>.
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later
|
||||
* See the lgpl.txt file in the root directory or http://www.gnu.org/licenses/lgpl-2.1.html
|
||||
*/
|
||||
package org.hibernate.orm.test.mapping.type.collection.custom.basic;
|
||||
package org.hibernate.orm.test.mapping.collections.custom.basic;
|
||||
|
||||
import java.util.ArrayList;
|
||||
|
|
@ -1,10 +1,10 @@
|
|||
/*
|
||||
* Hibernate, Relational Persistence for Idiomatic Java
|
||||
*
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later.
|
||||
* See the lgpl.txt file in the root directory or <http://www.gnu.org/licenses/lgpl-2.1.html>.
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later
|
||||
* See the lgpl.txt file in the root directory or http://www.gnu.org/licenses/lgpl-2.1.html
|
||||
*/
|
||||
package org.hibernate.orm.test.mapping.type.collection.custom.basic;
|
||||
package org.hibernate.orm.test.mapping.collections.custom.basic;
|
||||
|
||||
import java.util.Iterator;
|
||||
import java.util.Map;
|
||||
|
@ -12,6 +12,7 @@ import java.util.Map;
|
|||
import org.hibernate.HibernateException;
|
||||
import org.hibernate.collection.spi.PersistentCollection;
|
||||
import org.hibernate.engine.spi.SharedSessionContractImplementor;
|
||||
import org.hibernate.metamodel.CollectionClassification;
|
||||
import org.hibernate.persister.collection.CollectionPersister;
|
||||
import org.hibernate.usertype.UserCollectionType;
|
||||
|
||||
|
@ -19,6 +20,16 @@ public class MyListType implements UserCollectionType {
|
|||
|
||||
static int lastInstantiationRequest = -2;
|
||||
|
||||
@Override
|
||||
public CollectionClassification getClassification() {
|
||||
return CollectionClassification.LIST;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Class<?> getCollectionClass() {
|
||||
return IMyList.class;
|
||||
}
|
||||
|
||||
@Override
|
||||
public PersistentCollection instantiate(SharedSessionContractImplementor session, CollectionPersister persister) throws HibernateException {
|
||||
return new PersistentMyList( session );
|
|
@ -1,10 +1,10 @@
|
|||
/*
|
||||
* Hibernate, Relational Persistence for Idiomatic Java
|
||||
*
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later.
|
||||
* See the lgpl.txt file in the root directory or <http://www.gnu.org/licenses/lgpl-2.1.html>.
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later
|
||||
* See the lgpl.txt file in the root directory or http://www.gnu.org/licenses/lgpl-2.1.html
|
||||
*/
|
||||
package org.hibernate.orm.test.mapping.type.collection.custom.basic;
|
||||
package org.hibernate.orm.test.mapping.collections.custom.basic;
|
||||
|
||||
import org.hibernate.collection.spi.PersistentList;
|
||||
import org.hibernate.engine.spi.SharedSessionContractImplementor;
|
|
@ -1,10 +1,10 @@
|
|||
/*
|
||||
* Hibernate, Relational Persistence for Idiomatic Java
|
||||
*
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later.
|
||||
* See the lgpl.txt file in the root directory or <http://www.gnu.org/licenses/lgpl-2.1.html>.
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later
|
||||
* See the lgpl.txt file in the root directory or http://www.gnu.org/licenses/lgpl-2.1.html
|
||||
*/
|
||||
package org.hibernate.orm.test.mapping.type.collection.custom.basic;
|
||||
package org.hibernate.orm.test.mapping.collections.custom.basic;
|
||||
|
||||
import java.util.List;
|
||||
|
|
@ -1,10 +1,10 @@
|
|||
/*
|
||||
* Hibernate, Relational Persistence for Idiomatic Java
|
||||
*
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later.
|
||||
* See the lgpl.txt file in the root directory or <http://www.gnu.org/licenses/lgpl-2.1.html>.
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later
|
||||
* See the lgpl.txt file in the root directory or http://www.gnu.org/licenses/lgpl-2.1.html
|
||||
*/
|
||||
package org.hibernate.orm.test.mapping.type.collection.custom.basic;
|
||||
package org.hibernate.orm.test.mapping.collections.custom.basic;
|
||||
|
||||
/**
|
||||
* @author Steve Ebersole
|
|
@ -1,10 +1,10 @@
|
|||
/*
|
||||
* Hibernate, Relational Persistence for Idiomatic Java
|
||||
*
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later.
|
||||
* See the lgpl.txt file in the root directory or <http://www.gnu.org/licenses/lgpl-2.1.html>.
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later
|
||||
* See the lgpl.txt file in the root directory or http://www.gnu.org/licenses/lgpl-2.1.html
|
||||
*/
|
||||
package org.hibernate.orm.test.mapping.type.collection.custom.basic;
|
||||
package org.hibernate.orm.test.mapping.collections.custom.basic;
|
||||
|
||||
/**
|
||||
* @author Steve Ebersole
|
||||
|
@ -17,6 +17,6 @@ public class UserCollectionTypeHbmVariantTest extends UserCollectionTypeTest {
|
|||
|
||||
@Override
|
||||
public String[] getMappings() {
|
||||
return new String[] { "/org/hibernate/orm/test/mapping/type/collection/custom/basic/UserPermissions.hbm.xml" };
|
||||
return new String[] { "/org/hibernate/orm/test/mapping/collections/custom/basic/UserPermissions.hbm.xml" };
|
||||
}
|
||||
}
|
|
@ -1,10 +1,10 @@
|
|||
/*
|
||||
* Hibernate, Relational Persistence for Idiomatic Java
|
||||
*
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later.
|
||||
* See the lgpl.txt file in the root directory or <http://www.gnu.org/licenses/lgpl-2.1.html>.
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later
|
||||
* See the lgpl.txt file in the root directory or http://www.gnu.org/licenses/lgpl-2.1.html
|
||||
*/
|
||||
package org.hibernate.orm.test.mapping.type.collection.custom.basic;
|
||||
package org.hibernate.orm.test.mapping.collections.custom.basic;
|
||||
|
||||
import jakarta.persistence.criteria.CriteriaBuilder;
|
||||
import jakarta.persistence.criteria.CriteriaQuery;
|
|
@ -2,8 +2,8 @@
|
|||
<!--
|
||||
~ Hibernate, Relational Persistence for Idiomatic Java
|
||||
~
|
||||
~ License: GNU Lesser General Public License (LGPL), version 2.1 or later.
|
||||
~ See the lgpl.txt file in the root directory or <http://www.gnu.org/licenses/lgpl-2.1.html>.
|
||||
~ License: GNU Lesser General Public License (LGPL), version 2.1 or later
|
||||
~ See the lgpl.txt file in the root directory or http://www.gnu.org/licenses/lgpl-2.1.html
|
||||
-->
|
||||
<!DOCTYPE hibernate-mapping PUBLIC
|
||||
"-//Hibernate/Hibernate Mapping DTD 3.0//EN"
|
||||
|
@ -13,14 +13,14 @@
|
|||
This mapping is a basic example of how to write a UserCollectionType.
|
||||
-->
|
||||
|
||||
<hibernate-mapping package="org.hibernate.orm.test.mapping.type.collection.custom.basic" default-access="field">
|
||||
<hibernate-mapping package="org.hibernate.orm.test.mapping.collections.custom.basic" default-access="field">
|
||||
|
||||
<import class="Permission"/>
|
||||
|
||||
<class name="User" table="UC_BSC_USER">
|
||||
<id name="id"/>
|
||||
<property name="userName"/>
|
||||
<list name="emailAddresses" fetch="join" cascade="all, delete-orphan" collection-type="org.hibernate.orm.test.mapping.type.collection.custom.basic.MyListType">
|
||||
<list name="emailAddresses" fetch="join" cascade="all, delete-orphan" collection-type="MyListType">
|
||||
<key column="userName"/>
|
||||
<list-index column="displayOrder" base="1"/>
|
||||
<one-to-many class="Email"/>
|
|
@ -4,7 +4,7 @@
|
|||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later
|
||||
* See the lgpl.txt file in the root directory or http://www.gnu.org/licenses/lgpl-2.1.html
|
||||
*/
|
||||
package org.hibernate.orm.test.mapping.type.collection.custom.declaredtype.explicitsemantics;
|
||||
package org.hibernate.orm.test.mapping.collections.custom.declaredtype;
|
||||
|
||||
import jakarta.persistence.Entity;
|
||||
import jakarta.persistence.GeneratedValue;
|
||||
|
@ -15,9 +15,8 @@ import jakarta.persistence.Id;
|
|||
* @author Gavin King
|
||||
* @author Steve Ebersole
|
||||
*/
|
||||
@Entity(name = "Email")
|
||||
@Entity
|
||||
public class Email {
|
||||
|
||||
private Long id;
|
||||
private String address;
|
||||
|
||||
|
@ -29,7 +28,7 @@ public class Email {
|
|||
}
|
||||
|
||||
@Id
|
||||
@GeneratedValue(strategy = GenerationType.AUTO)
|
||||
@GeneratedValue( strategy = GenerationType.AUTO )
|
||||
public Long getId() {
|
||||
return id;
|
||||
}
|
||||
|
@ -48,11 +47,9 @@ public class Email {
|
|||
|
||||
@Override
|
||||
public boolean equals(Object that) {
|
||||
if ( !( that instanceof Email ) ) {
|
||||
return false;
|
||||
}
|
||||
if ( !(that instanceof Email ) ) return false;
|
||||
Email p = (Email) that;
|
||||
return this.address.equals( p.address );
|
||||
return this.address.equals(p.address);
|
||||
}
|
||||
|
||||
@Override
|
|
@ -4,7 +4,7 @@
|
|||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later
|
||||
* See the lgpl.txt file in the root directory or http://www.gnu.org/licenses/lgpl-2.1.html
|
||||
*/
|
||||
package org.hibernate.orm.test.mapping.type.collection.custom.declaredtype;
|
||||
package org.hibernate.orm.test.mapping.collections.custom.declaredtype;
|
||||
|
||||
import java.util.ArrayList;
|
||||
|
|
@ -4,7 +4,7 @@
|
|||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later
|
||||
* See the lgpl.txt file in the root directory or http://www.gnu.org/licenses/lgpl-2.1.html
|
||||
*/
|
||||
package org.hibernate.orm.test.mapping.type.collection.custom.declaredtype;
|
||||
package org.hibernate.orm.test.mapping.collections.custom.declaredtype;
|
||||
|
||||
import java.util.Iterator;
|
||||
import java.util.Map;
|
||||
|
@ -12,6 +12,7 @@ import java.util.Map;
|
|||
import org.hibernate.HibernateException;
|
||||
import org.hibernate.collection.spi.PersistentCollection;
|
||||
import org.hibernate.engine.spi.SharedSessionContractImplementor;
|
||||
import org.hibernate.metamodel.CollectionClassification;
|
||||
import org.hibernate.persister.collection.CollectionPersister;
|
||||
import org.hibernate.usertype.UserCollectionType;
|
||||
|
||||
|
@ -20,6 +21,16 @@ import org.hibernate.usertype.UserCollectionType;
|
|||
*/
|
||||
public class HeadListType implements UserCollectionType {
|
||||
|
||||
@Override
|
||||
public CollectionClassification getClassification() {
|
||||
return CollectionClassification.LIST;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Class<?> getCollectionClass() {
|
||||
return IHeadList.class;
|
||||
}
|
||||
|
||||
@Override
|
||||
public PersistentCollection instantiate(SharedSessionContractImplementor session, CollectionPersister persister) throws HibernateException {
|
||||
return new PersistentHeadList( session );
|
|
@ -4,7 +4,7 @@
|
|||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later
|
||||
* See the lgpl.txt file in the root directory or http://www.gnu.org/licenses/lgpl-2.1.html
|
||||
*/
|
||||
package org.hibernate.orm.test.mapping.type.collection.custom.declaredtype;
|
||||
package org.hibernate.orm.test.mapping.collections.custom.declaredtype;
|
||||
|
||||
import java.util.List;
|
||||
|
|
@ -4,7 +4,7 @@
|
|||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later
|
||||
* See the lgpl.txt file in the root directory or http://www.gnu.org/licenses/lgpl-2.1.html
|
||||
*/
|
||||
package org.hibernate.orm.test.mapping.type.collection.custom.declaredtype;
|
||||
package org.hibernate.orm.test.mapping.collections.custom.declaredtype;
|
||||
|
||||
import org.hibernate.collection.spi.PersistentList;
|
||||
import org.hibernate.engine.spi.SharedSessionContractImplementor;
|
|
@ -4,7 +4,7 @@
|
|||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later
|
||||
* See the lgpl.txt file in the root directory or http://www.gnu.org/licenses/lgpl-2.1.html
|
||||
*/
|
||||
package org.hibernate.orm.test.mapping.type.collection.custom.declaredtype;
|
||||
package org.hibernate.orm.test.mapping.collections.custom.declaredtype;
|
||||
|
||||
import org.hibernate.annotations.CollectionType;
|
||||
|
|
@ -1,3 +1,10 @@
|
|||
/*
|
||||
* Hibernate, Relational Persistence for Idiomatic Java
|
||||
*
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later
|
||||
* See the lgpl.txt file in the root directory or http://www.gnu.org/licenses/lgpl-2.1.html
|
||||
*/
|
||||
|
||||
/*
|
||||
* Hibernate, Relational Persistence for Idiomatic Java
|
||||
*
|
||||
|
@ -21,7 +28,7 @@
|
|||
* 51 Franklin Street, Fifth Floor
|
||||
* Boston, MA 02110-1301 USA
|
||||
*/
|
||||
package org.hibernate.orm.test.mapping.type.collection.custom.declaredtype;
|
||||
package org.hibernate.orm.test.mapping.collections.custom.declaredtype;
|
||||
|
||||
/**
|
||||
* @author Steve Ebersole
|
|
@ -0,0 +1,17 @@
|
|||
/*
|
||||
* Hibernate, Relational Persistence for Idiomatic Java
|
||||
*
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later
|
||||
* See the lgpl.txt file in the root directory or http://www.gnu.org/licenses/lgpl-2.1.html
|
||||
*/
|
||||
package org.hibernate.orm.test.mapping.collections.custom.declaredtype;
|
||||
|
||||
/**
|
||||
* @author Steve Ebersole
|
||||
*/
|
||||
public class UserCollectionTypeHbmVariantTest extends UserCollectionTypeTest {
|
||||
@Override
|
||||
public String[] getMappings() {
|
||||
return new String[] { "mapping/collections/custom/declaredtype/UserPermissions.hbm.xml" };
|
||||
}
|
||||
}
|
|
@ -1,3 +1,10 @@
|
|||
/*
|
||||
* Hibernate, Relational Persistence for Idiomatic Java
|
||||
*
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later
|
||||
* See the lgpl.txt file in the root directory or http://www.gnu.org/licenses/lgpl-2.1.html
|
||||
*/
|
||||
|
||||
/*
|
||||
* Hibernate, Relational Persistence for Idiomatic Java
|
||||
*
|
||||
|
@ -21,7 +28,7 @@
|
|||
* 51 Franklin Street, Fifth Floor
|
||||
* Boston, MA 02110-1301 USA
|
||||
*/
|
||||
package org.hibernate.orm.test.mapping.type.collection.custom.declaredtype;
|
||||
package org.hibernate.orm.test.mapping.collections.custom.declaredtype;
|
||||
|
||||
import jakarta.persistence.criteria.CriteriaBuilder;
|
||||
import jakarta.persistence.criteria.CriteriaQuery;
|
|
@ -1,4 +1,10 @@
|
|||
<?xml version="1.0"?>
|
||||
<!--
|
||||
~ Hibernate, Relational Persistence for Idiomatic Java
|
||||
~
|
||||
~ License: GNU Lesser General Public License (LGPL), version 2.1 or later
|
||||
~ See the lgpl.txt file in the root directory or http://www.gnu.org/licenses/lgpl-2.1.html
|
||||
-->
|
||||
<!DOCTYPE hibernate-mapping PUBLIC
|
||||
"-//Hibernate/Hibernate Mapping DTD 3.0//EN"
|
||||
"http://www.hibernate.org/dtd/hibernate-mapping-3.0.dtd">
|
||||
|
@ -7,14 +13,14 @@
|
|||
This mapping is a basic example of how to write a UserCollectionType.
|
||||
-->
|
||||
|
||||
<hibernate-mapping package="org.hibernate.orm.test.mapping.type.collection.custom.declaredtype" default-access="field">
|
||||
<hibernate-mapping package="org.hibernate.orm.test.mapping.collections.custom.declaredtype" default-access="field">
|
||||
|
||||
<import class="Permission"/>
|
||||
|
||||
<class name="org.hibernate.orm.test.mapping.type.collection.custom.declaredtype.User" table="UC_BSC_USER">
|
||||
<class name="User" table="UC_BSC_USER">
|
||||
<id name="id"/>
|
||||
<property name="userName"/>
|
||||
<list name="emailAddresses" fetch="join" cascade="all, delete-orphan" collection-type="org.hibernate.orm.test.mapping.type.collection.custom.declaredtype.HeadListType">
|
||||
<list name="emailAddresses" fetch="join" cascade="all, delete-orphan" collection-type="HeadListType">
|
||||
<key column="userName"/>
|
||||
<list-index column="displayOrder" base="1"/>
|
||||
<one-to-many class="Email"/>
|
|
@ -1,3 +1,10 @@
|
|||
/*
|
||||
* Hibernate, Relational Persistence for Idiomatic Java
|
||||
*
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later
|
||||
* See the lgpl.txt file in the root directory or http://www.gnu.org/licenses/lgpl-2.1.html
|
||||
*/
|
||||
|
||||
/*
|
||||
* Hibernate, Relational Persistence for Idiomatic Java
|
||||
*
|
||||
|
@ -21,7 +28,7 @@
|
|||
* 51 Franklin Street, Fifth Floor
|
||||
* Boston, MA 02110-1301 USA
|
||||
*/
|
||||
package org.hibernate.orm.test.mapping.type.collection.custom.declaredtype;
|
||||
package org.hibernate.orm.test.mapping.collections.custom.declaredtype;
|
||||
|
||||
import org.hibernate.annotations.CollectionType;
|
||||
|
|
@ -1,3 +1,10 @@
|
|||
/*
|
||||
* Hibernate, Relational Persistence for Idiomatic Java
|
||||
*
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later
|
||||
* See the lgpl.txt file in the root directory or http://www.gnu.org/licenses/lgpl-2.1.html
|
||||
*/
|
||||
|
||||
/*
|
||||
* Hibernate, Relational Persistence for Idiomatic Java
|
||||
*
|
||||
|
@ -21,7 +28,7 @@
|
|||
* 51 Franklin Street, Fifth Floor
|
||||
* Boston, MA 02110-1301 USA
|
||||
*/
|
||||
package org.hibernate.orm.test.mapping.type.collection.custom.declaredtype;
|
||||
package org.hibernate.orm.test.mapping.collections.custom.declaredtype;
|
||||
|
||||
import org.hibernate.AnnotationException;
|
||||
import org.hibernate.testing.junit4.BaseCoreFunctionalTestCase;
|
|
@ -1,10 +1,10 @@
|
|||
/*
|
||||
* Hibernate, Relational Persistence for Idiomatic Java
|
||||
*
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later.
|
||||
* See the lgpl.txt file in the root directory or <http://www.gnu.org/licenses/lgpl-2.1.html>.
|
||||
* License: GNU Lesser General Public License (LGPL), version 2.1 or later
|
||||
* See the lgpl.txt file in the root directory or http://www.gnu.org/licenses/lgpl-2.1.html
|
||||
*/
|
||||
package org.hibernate.orm.test.mapping.type.collection.custom.parameterized;
|
||||
package org.hibernate.orm.test.mapping.collections.custom.parameterized;
|
||||
|
||||
import java.util.List;
|
||||
|
Some files were not shown because too many files have changed in this diff Show More
Loading…
Reference in New Issue