All Downloads are FREE. Search and download functionalities are using the official Maven repository.

org.springframework.data.mapping.PersistentProperty Maven / Gradle / Ivy

The newest version!
/*
 * Copyright 2011-2024 the original author or authors.
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *      https://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */
package org.springframework.data.mapping;

import java.lang.annotation.Annotation;
import java.lang.reflect.Field;
import java.lang.reflect.Method;
import java.util.Collection;
import java.util.Map;

import org.springframework.core.annotation.AnnotatedElementUtils;
import org.springframework.core.annotation.AnnotationUtils;
import org.springframework.data.util.TypeInformation;
import org.springframework.lang.Nullable;
import org.springframework.util.Assert;

/**
 * @author Graeme Rocher
 * @author Jon Brisbin
 * @author Oliver Gierke
 * @author Mark Paluch
 * @author Jens Schauder
 * @author Christoph Strobl
 * @author Johannes Englmeier
 */
public interface PersistentProperty

> { /** * Returns the {@link PersistentEntity} owning the current {@link PersistentProperty}. * * @return never {@literal null}. */ PersistentEntity getOwner(); /** * The name of the property * * @return The property name */ String getName(); /** * The type of the property * * @return The property type */ Class getType(); /** * Returns the {@link TypeInformation} of the property. * * @return */ TypeInformation getTypeInformation(); /** * Returns the detected {@link TypeInformation TypeInformations} if the property references a * {@link PersistentEntity}. Will return an {@literal empty} {@link Iterable} in case it refers to a simple type. Will * return the {@link Collection}'s component types or the {@link Map}'s value type transparently. * * @return never {@literal null}. * @since 2.6 */ Iterable> getPersistentEntityTypeInformation(); /** * Returns the getter method to access the property value if available. Might return {@literal null} in case there is * no getter method with a return type assignable to the actual property's type. * * @return the getter method to access the property value if available, otherwise {@literal null}. */ @Nullable Method getGetter(); default Method getRequiredGetter() { Method getter = getGetter(); if (getter == null) { throw new IllegalArgumentException(String.format("No getter available for persistent property %s", this)); } return getter; } /** * Returns the setter method to set a property value. Might return {@literal null} in case there is no setter * available. * * @return the setter method to set a property value if available, otherwise {@literal null}. */ @Nullable Method getSetter(); default Method getRequiredSetter() { Method setter = getSetter(); if (setter == null) { throw new IllegalArgumentException(String.format("No setter available for persistent property %s", this)); } return setter; } /** * Returns the with {@link Method} to set a property value on a new object instance. Might return {@literal null} in * case there is no with available. *

* With {@link Method methods} are property-bound instance {@link Method methods} that accept a single argument of the * property type creating a new object instance. * *

	 * class Person {
	 * 	final String id;
	 * 	final String name;
	 *
	 * 	// …
	 *
	 * 	Person withName(String name) {
	 * 		return new Person(this.id, name);
	 * 	}
	 * }
	 * 
* * @return the with {@link Method} to set a property value on a new object instance if available, otherwise * {@literal null}. * @since 2.1 */ @Nullable Method getWither(); default Method getRequiredWither() { Method wither = getWither(); if (wither == null) { throw new IllegalArgumentException(String.format("No wither available for persistent property %s", this)); } return wither; } @Nullable Field getField(); default Field getRequiredField() { Field field = getField(); if (field == null) { throw new IllegalArgumentException(String.format("No field backing persistent property %s", this)); } return field; } /** * @return {@literal null} if no expression defined. */ @Nullable String getSpelExpression(); /** * @return {@literal null} if property is not part of an {@link Association}. */ @Nullable Association

getAssociation(); /** * Get the {@link Association} of this property. * * @return never {@literal null}. * @throws IllegalStateException if not involved in an {@link Association}. */ default Association

getRequiredAssociation() { Association

association = getAssociation(); if (association != null) { return association; } throw new IllegalStateException("No association found"); } /** * Returns whether the type of the {@link PersistentProperty} is actually to be regarded as {@link PersistentEntity} * in turn. * * @return {@literal true} a {@link PersistentEntity}. */ boolean isEntity(); /** * Returns whether the property is a potential identifier property of the owning {@link PersistentEntity}. * This method is mainly used by {@link PersistentEntity} implementation to discover id property candidates on * {@link PersistentEntity} creation you should rather call {@link PersistentEntity#isIdProperty(PersistentProperty)} * to determine whether the current property is the id property of that {@link PersistentEntity} under consideration. * * @return {@literal true} if the {@literal id} property. */ boolean isIdProperty(); /** * Returns whether the current property is a potential version property of the owning * {@link PersistentEntity}. This method is mainly used by {@link PersistentEntity} implementation to discover version * property candidates on {@link PersistentEntity} creation you should rather call * {@link PersistentEntity#isVersionProperty(PersistentProperty)} to determine whether the current property is the * version property of that {@link PersistentEntity} under consideration. * * @return */ boolean isVersionProperty(); /** * Returns whether the property is a {@link Collection}, {@link Iterable} or an array. * * @return */ boolean isCollectionLike(); /** * Returns whether the property is a {@link Map}. * * @return */ boolean isMap(); /** * Returns whether the property is an array. * * @return */ boolean isArray(); /** * Returns whether the property is transient. * * @return */ boolean isTransient(); /** * Returns whether the current property is writable, i.e. if the value held for it shall be written to the data store. * * @return * @since 1.9 */ boolean isWritable(); /** * Returns whether the current property is readable through {@link PersistentPropertyAccessor}, i.e. if it is not * {@link #isTransient()}, if the value can be set on the current instance or read to create a new instance as per * {@link #getWither()} or via Kotlin Copy methods. * * @return * @since 3.2 */ boolean isReadable(); /** * Returns whether the current property is immutable, i.e. if there is no setter or the backing {@link Field} is * {@code final}. * * @return * @see java.lang.reflect.Modifier#isFinal(int) * @since 2.1 */ boolean isImmutable(); /** * Returns whether the property is an {@link Association}. * * @return */ boolean isAssociation(); /** * Returns the component type of the type if it is a {@link java.util.Collection}. Will return the type of the key if * the property is a {@link java.util.Map}. * * @return the component type, the map's key type or {@literal null} if neither {@link java.util.Collection} nor * {@link java.util.Map}. */ @Nullable Class getComponentType(); /** * Returns the raw type as it's pulled from from the reflected property. * * @return the raw type of the property. */ Class getRawType(); /** * Returns the type of the values if the property is a {@link java.util.Map}. * * @return the map's value type or {@literal null} if no {@link java.util.Map} */ @Nullable Class getMapValueType(); /** * Returns the actual type of the property. This will be the original property type if no generics were used, the * component type for collection-like types and arrays as well as the value type for map properties. * * @return */ Class getActualType(); /** * Looks up the annotation of the given type on the {@link PersistentProperty}. Will inspect accessors and the * potentially backing field and traverse accessor methods to potentially available super types. * * @param annotationType the annotation to look up, must not be {@literal null}. * @return the annotation of the given type. Can be {@literal null}. * @see AnnotationUtils#findAnnotation(Method, Class) */ @Nullable A findAnnotation(Class annotationType); /** * Looks up the annotation of the given type on the {@link PersistentProperty}. Will inspect accessors and the * potentially backing field and traverse accessor methods to potentially available super types. * * @param annotationType the annotation to look up, must not be {@literal null}. * @return the annotation of the given type. * @throws IllegalStateException if the required {@code annotationType} is not found. * @since 2.0 */ default A getRequiredAnnotation(Class annotationType) throws IllegalStateException { A annotation = findAnnotation(annotationType); if (annotation != null) { return annotation; } throw new IllegalStateException( String.format("Required annotation %s not found for %s", annotationType, getName())); } /** * Looks up the annotation of the given type on the property and the owning type if no annotation can be found on it. * Useful to lookup annotations that can be configured on the type but overridden on an individual property. * * @param annotationType must not be {@literal null}. * @return the annotation of the given type. Can be {@literal null}. */ @Nullable A findPropertyOrOwnerAnnotation(Class annotationType); /** * Returns whether the {@link PersistentProperty} has an annotation of the given type. * * @param annotationType the annotation to lookup, must not be {@literal null}. * @return whether the {@link PersistentProperty} has an annotation of the given type. */ boolean isAnnotationPresent(Class annotationType); /** * Returns whether property access shall be used for reading the property value. This means it will use the getter * instead of field access. * * @return */ boolean usePropertyAccess(); /** * Returns whether the actual type of the property carries the given annotation. * * @param annotationType must not be {@literal null}. * @return * @since 2.1 * @see #getActualType() */ default boolean hasActualTypeAnnotation(Class annotationType) { Assert.notNull(annotationType, "Annotation type must not be null"); return AnnotatedElementUtils.hasAnnotation(getActualType(), annotationType); } /** * Return the type the property refers to in case it's an association, i.e. {@link #isAssociation()} returns * {@literal true}. That means, that implementations must return a non-{@literal null} value from this method * in that case. We also recommend to return {@literal null} for non-associations right away to establish symmetry * between this method and {@link #isAssociation()}. * * @return the type the property refers to in case it's an association, i.e. {@link #isAssociation()} returns * {@literal true}. * @since 2.1 */ @Nullable Class getAssociationTargetType(); /** * Return the type the property refers to in case it's an association, i.e. {@link #isAssociation()} returns * {@literal true}. That means, that implementations must return a non-{@literal null} value from this method * in that case. We also recommend to return {@literal null} for non-associations right away to establish symmetry * between this method and {@link #isAssociation()}. * * @return the type the property refers to in case it's an association, i.e. {@link #isAssociation()} returns * {@literal true}. * @since 2.6 */ @Nullable TypeInformation getAssociationTargetTypeInformation(); /** * Returns a {@link PersistentPropertyAccessor} for the current property's owning value. * * @param owner must not be {@literal null}. * @return will never be {@literal null}. * @since 2.3 */ default PersistentPropertyAccessor getAccessorForOwner(T owner) { Assert.notNull(owner, "Owner must not be null"); return getOwner().getPropertyAccessor(owner); } }





© 2015 - 2024 Weber Informatics LLC | Privacy Policy