// Path: src/main/java/com/_4dconcept/springframework/data/marklogic/core/mapping/MarklogicPersistentEntity.java
// public interface MarklogicPersistentEntity<T> extends PersistentEntity<T, MarklogicPersistentProperty> {
// 
//     /**
//      * @return the uri the entity shall be persisted to.
//      */
//     String getUri();
// 
//     /**
//      * @return the default defaultCollection the entity should be created with
//      */
//     String getDefaultCollection();
// 
//     /**
//      * @return true if the id is to be found in property fragment
//      */
//     boolean idInPropertyFragment();
// 
// }
// 
// Path: src/main/java/com/_4dconcept/springframework/data/marklogic/core/mapping/MarklogicPersistentProperty.java
// public interface MarklogicPersistentProperty extends PersistentProperty<MarklogicPersistentProperty> {
// 
//     /**
//      * @return whether the property is explicitly marked as an identifier property of the owning {@link PersistentEntity}.
//      */
//     boolean isExplicitIdProperty();
// 
//     /**
//      * @return the full qualified name of the property
//      */
//     QName getQName();
// 
//     Optional<Method> getReadMethod();
// 
// }


import com._4dconcept.springframework.data.marklogic.core.mapping.MarklogicPersistentEntity;
import com._4dconcept.springframework.data.marklogic.core.mapping.MarklogicPersistentProperty;
import org.springframework.dao.InvalidDataAccessApiUsageException;
import org.springframework.dao.TypeMismatchDataAccessException;
import org.springframework.data.mapping.context.MappingContext;
import org.springframework.expression.Expression;
import org.springframework.expression.ParserContext;
import org.springframework.expression.common.LiteralExpression;
import org.springframework.expression.spel.standard.SpelExpressionParser;
import org.springframework.lang.Nullable;
import org.springframework.util.StringUtils;
import java.util.function.Supplier;
package com._4dconcept.springframework.data.marklogic;



/**
 * Helper class featuring helper methods for working with Marklogic specific elements.
 * Mainly intended for internal use within the framework.
 *
 * @author stoussaint
 * @since 2017-11-30
 */
public final class MarklogicUtils {

    private static final SpelExpressionParser PARSER = new SpelExpressionParser();

    /**
     * Private constructor to prevent instantiation.
     */
    private MarklogicUtils() {}

    /**
     * Expands the given expression using the provided type as context.
     *
     * @param expression the expression to expand
     * @param entityType the entityType used as context
     * @return the expanded expression. If the given expression is a literal or null, it is return as it.
     */
    @Nullable
    public static String expandsExpression(@Nullable String expression, @Nullable Class<?> entityType) {
        return expandsExpression(expression, entityType, null, null);
    }

    /**
     * Expands the given expression using the provided type, entity and id as context.
     *
     * @param expression the expression to expand
     * @param entityType the entityType used as context
     * @param entity the entity to use as context
     * @return the expanded expression. If the given expression is a literal or null, it is return as it.
     */
    @Nullable
    public static String expandsExpression(@Nullable String expression, @Nullable Class<?> entityType, @Nullable Object entity, @Nullable Supplier<Object> idSupplier) {
        return expandsExpression(expression, new DocumentExpressionContext() {
            @Override
            public Class<?> getEntityClass() {
                return entityType;
            }

            @Override
            public Object getEntity() {
                return entity;
            }

            @Override
            public Object getId() {
                return idSupplier != null ? idSupplier.get() : null;
            }
        });
    }

    @Nullable
// Path: src/main/java/com/_4dconcept/springframework/data/marklogic/core/mapping/MarklogicPersistentEntity.java
// public interface MarklogicPersistentEntity<T> extends PersistentEntity<T, MarklogicPersistentProperty> {
// 
//     /**
//      * @return the uri the entity shall be persisted to.
//      */
//     String getUri();
// 
//     /**
//      * @return the default defaultCollection the entity should be created with
//      */
//     String getDefaultCollection();
// 
//     /**
//      * @return true if the id is to be found in property fragment
//      */
//     boolean idInPropertyFragment();
// 
// }
// 
// Path: src/main/java/com/_4dconcept/springframework/data/marklogic/core/mapping/MarklogicPersistentProperty.java
// public interface MarklogicPersistentProperty extends PersistentProperty<MarklogicPersistentProperty> {
// 
//     /**
//      * @return whether the property is explicitly marked as an identifier property of the owning {@link PersistentEntity}.
//      */
//     boolean isExplicitIdProperty();
// 
//     /**
//      * @return the full qualified name of the property
//      */
//     QName getQName();
// 
//     Optional<Method> getReadMethod();
// 
// }


// Path: src/main/java/com/_4dconcept/springframework/data/marklogic/MarklogicUtils.java
import com._4dconcept.springframework.data.marklogic.core.mapping.MarklogicPersistentEntity;
import com._4dconcept.springframework.data.marklogic.core.mapping.MarklogicPersistentProperty;
import org.springframework.dao.InvalidDataAccessApiUsageException;
import org.springframework.dao.TypeMismatchDataAccessException;
import org.springframework.data.mapping.context.MappingContext;
import org.springframework.expression.Expression;
import org.springframework.expression.ParserContext;
import org.springframework.expression.common.LiteralExpression;
import org.springframework.expression.spel.standard.SpelExpressionParser;
import org.springframework.lang.Nullable;
import org.springframework.util.StringUtils;
import java.util.function.Supplier;

package com._4dconcept.springframework.data.marklogic;



/**
 * Helper class featuring helper methods for working with Marklogic specific elements.
 * Mainly intended for internal use within the framework.
 *
 * @author stoussaint
 * @since 2017-11-30
 */
public final class MarklogicUtils {

    private static final SpelExpressionParser PARSER = new SpelExpressionParser();

    /**
     * Private constructor to prevent instantiation.
     */
    private MarklogicUtils() {}

    /**
     * Expands the given expression using the provided type as context.
     *
     * @param expression the expression to expand
     * @param entityType the entityType used as context
     * @return the expanded expression. If the given expression is a literal or null, it is return as it.
     */
    @Nullable
    public static String expandsExpression(@Nullable String expression, @Nullable Class<?> entityType) {
        return expandsExpression(expression, entityType, null, null);
    }

    /**
     * Expands the given expression using the provided type, entity and id as context.
     *
     * @param expression the expression to expand
     * @param entityType the entityType used as context
     * @param entity the entity to use as context
     * @return the expanded expression. If the given expression is a literal or null, it is return as it.
     */
    @Nullable
    public static String expandsExpression(@Nullable String expression, @Nullable Class<?> entityType, @Nullable Object entity, @Nullable Supplier<Object> idSupplier) {
        return expandsExpression(expression, new DocumentExpressionContext() {
            @Override
            public Class<?> getEntityClass() {
                return entityType;
            }

            @Override
            public Object getEntity() {
                return entity;
            }

            @Override
            public Object getId() {
                return idSupplier != null ? idSupplier.get() : null;
            }
        });
    }

    @Nullable
    public static Object retrieveIdentifier(Object object, MappingContext<? extends MarklogicPersistentEntity<?>, MarklogicPersistentProperty> mappingContext) {