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

org.apache.openjpa.persistence.meta.Members Maven / Gradle / Ivy

There is a newer version: 4.0.0
Show newest version
/*
 * Licensed to the Apache Software Foundation (ASF) under one
 * or more contributor license agreements.  See the NOTICE file
 * distributed with this work for additional information
 * regarding copyright ownership.  The ASF licenses this file
 * to you 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
 *
 * http://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.apache.openjpa.persistence.meta;

import java.util.Collection;
import java.util.Set;

import javax.persistence.metamodel.Attribute;
import javax.persistence.metamodel.CollectionAttribute;
import javax.persistence.metamodel.ListAttribute;
import javax.persistence.metamodel.ManagedType;
import javax.persistence.metamodel.MapAttribute;
import javax.persistence.metamodel.PluralAttribute;
import javax.persistence.metamodel.SetAttribute;
import javax.persistence.metamodel.SingularAttribute;
import javax.persistence.metamodel.Type;

import org.apache.openjpa.meta.FieldMetaData;
import org.apache.openjpa.meta.JavaTypes;

/**
 * Persistent attribute according to JPA 2.0 metamodel.
 * 
 * Implemented as a thin adapter to OpenJPA FieldMetadata. Mostly immutable.
 * 
 * @author Pinaki Poddar
 * 
 * @since 2.0.0
 *
 */
public class Members {
    /**
     * An attribute of a Java type. A persistent attribute is realized as a field and getter/setter
     * method of a Java class. This implementation adapts kernel's {@link FieldMetaData} construct 
     * to meet the JPA API contract.
	 *
	 *
     * @param  The type that contains this attribute
     * @param  The type of this attribute
	 */
    public static abstract class Member implements Attribute, Comparable> {
        public final AbstractManagedType owner;
        public final FieldMetaData fmd;

        /**
         * Supply immutable parts.
         * 
         * @param owner the persistent type that contains this attribute
         * @param fmd the kernel's concrete representation of this attribute
         */
        protected Member(AbstractManagedType owner, FieldMetaData fmd) {
            this.owner = owner;
            this.fmd = fmd;
        }

        /**
         *  Returns the managed type which declared this attribute.
         */
        public final ManagedType getDeclaringType() {
            return (ManagedType)owner.model.managedType(fmd.getDeclaringType());
        }
        
        /**
         *  Returns the java.lang.reflect.Member for this attribute. 
         */
        public final java.lang.reflect.Member getJavaMember() {
            return fmd.getBackingMember();
        }
        
        /**
         *  Gets the Java type of this attribute.
         */
        public final Class getJavaType() {
            return (Class)fmd.getDeclaredType();
        }
        
        /**
         * Gets the name of this attribute.
         */
        public final String getName() {
            return fmd.getName();
        }

        /**
         * Returns the type that represents the type of this attribute.
         */
        public final Type getType() {
            return owner.model.getType(isCollection() ?
                   fmd.getElement().getDeclaredType() : fmd.getDeclaredType());
        }
        
        /**
         * Affirms if this attribute is an association.
         */
        public final boolean isAssociation() {
            return fmd.isDeclaredTypePC();
        }

        /**
         * Affirms if this attribute is a collection.
         */
        public final boolean isCollection() {
            int typeCode = fmd.getDeclaredTypeCode();
            return  typeCode == JavaTypes.COLLECTION
                 || typeCode == JavaTypes.MAP
                 || typeCode == JavaTypes.ARRAY;
        }
        
        /**
         *  Returns the persistent category for the attribute.
         */
        public PersistentAttributeType getPersistentAttributeType() {
            if (fmd.isEmbeddedPC())
                return PersistentAttributeType.EMBEDDED;
            if (fmd.isElementCollection())
                return PersistentAttributeType.ELEMENT_COLLECTION;
            return PersistentAttributeType.BASIC;
        }

        public int compareTo(Member o) {
            return fmd.getName().compareTo(o.fmd.getName());
        }
    }
    
    
    /**
     * Represents single-valued persistent attributes.
     *
     * @param  The type containing the represented attribute
     * @param  The type of the represented attribute
     */
    public static final class SingularAttributeImpl extends Member 
        implements SingularAttribute {

        public SingularAttributeImpl(AbstractManagedType owner, FieldMetaData fmd) {
            super(owner, fmd);
        }

        /**
         *  Affirms if this attribute is an id attribute.
         */
        public boolean isId() {
            return fmd.isPrimaryKey();
        }

        /**
         *  Affirms if this attribute represents a version attribute.
         */
        public boolean isVersion() {
            return fmd.isVersion();
        }

        /** 
         *  Affirms if this attribute can be null.
         */
        public boolean isOptional() {
            return fmd.getNullValue() != FieldMetaData.NULL_EXCEPTION;
        }

        /**
         *  Categorizes bindable type represented by this attribute.
         */ 
        public final BindableType getBindableType() {
            return fmd.isDeclaredTypePC() 
                ? BindableType.ENTITY_TYPE
                : BindableType.SINGULAR_ATTRIBUTE;
        }
       
        /**
         * Returns the bindable Java type of this attribute.
         * 
         * If the bindable category of this attribute is PLURAL_ATTRIBUTE, the Java element type 
         * is returned. If the bindable type is SINGULAR_ATTRIBUTE or ENTITY_TYPE, the Java type 
         * of the represented entity or attribute is returned.
         */
        public final Class getBindableJavaType() {
            return fmd.getElement().getDeclaredType();
        }
        
        /**
         * Categorizes the attribute.
         */
        public final PersistentAttributeType getPersistentAttributeType() {
            if (!fmd.isDeclaredTypePC())
                return super.getPersistentAttributeType();
            if (fmd.getValue().isEmbedded() && fmd.getAssociationType() == 0) {
                return PersistentAttributeType.EMBEDDED;
            }
            
            return fmd.getMappedByMetaData() == null || !fmd.getType().isAssignableFrom(Collection.class)
                 ? PersistentAttributeType.ONE_TO_ONE
                 : PersistentAttributeType.ONE_TO_MANY;
        }
    }

    /**
     * Root of multi-cardinality attribute.
     *
	 * @param  the type that owns this member
	 * @param  the container type that holds this member (e.g. java.util.Set<Employee>)
     * @param  the type of the element held by this member (e.g. Employee). 
     */
    public static abstract class PluralAttributeImpl extends Member
        implements PluralAttribute {
        
        public PluralAttributeImpl(AbstractManagedType owner, FieldMetaData fmd) {
            super(owner, fmd);
        }

        /**
         * Returns the type representing the element type of the collection.
         */
        public final Type getElementType() {
            return owner.model.getType(getBindableJavaType());
        }

        /**
         *  Returns the bindable category of this attribute.
         */ 
        public final BindableType getBindableType() {
            return BindableType.PLURAL_ATTRIBUTE;
        }
        
        /**
         * Returns the bindable Java type of this attribute.
         * 
         * For PLURAL_ATTRIBUTE, the Java element type is returned. 
         */
        public Class getBindableJavaType() {
            return fmd.getElement().getDeclaredType();
        }
        
        
        public PersistentAttributeType getPersistentAttributeType() {
            return PersistentAttributeType.ONE_TO_MANY;
        }
    }

    /**
     * Represents attributes declared as java.util.Collection<E>.
     */
    public static class CollectionAttributeImpl 
        extends PluralAttributeImpl, E> 
        implements CollectionAttribute {

        public CollectionAttributeImpl(AbstractManagedType owner, FieldMetaData fmd) {
            super(owner, fmd);
        }

        public CollectionType getCollectionType() {
            return CollectionType.COLLECTION;
        }
    }

    /**
     * Represents attributes declared as java.util.List<E>.
     */
    public static class ListAttributeImpl 
        extends PluralAttributeImpl, E> 
        implements ListAttribute {

        public ListAttributeImpl(AbstractManagedType owner, FieldMetaData fmd) {
            super(owner, fmd);
        }

        public CollectionType getCollectionType() {
            return CollectionType.LIST;
        }
    }

    /**
     * Represents attributes declared as java.util.Set<E>.
     */
    public static class SetAttributeImpl 
        extends PluralAttributeImpl, E> 
        implements SetAttribute {

        public SetAttributeImpl(AbstractManagedType owner, FieldMetaData fmd) {
            super(owner, fmd);
        }

        public CollectionType getCollectionType() {
            return CollectionType.SET;
        }
    }
    
    /**
     * Represents the keys of java.util.Map<K,V> in managed type <X> as a pseudo-attribute of type 
     * java.util.Set<K>.
     *
     * @param  the declaring type of the original java.util.Map<K,V> attribute 
     * @param  the type of the key of the original java.util.Map<K,V> attribute
     */
    public static class KeyAttributeImpl extends SetAttributeImpl {
        public KeyAttributeImpl(AbstractManagedType owner, FieldMetaData fmd){
            super(owner, fmd);
        }

        public Class getBindableJavaType() {
            return (Class)fmd.getKey().getDeclaredType();
        }
    }

    /**
     * Represents attributes declared as java.util.Map<K,V> in managed type <X>.
     */
    public static class MapAttributeImpl 
        extends PluralAttributeImpl, V> 
        implements MapAttribute {

        public MapAttributeImpl(AbstractManagedType owner, FieldMetaData fmd) {
            super(owner, fmd);
        }

        public CollectionType getCollectionType() {
            return CollectionType.MAP;
        }
        
        public Class getKeyJavaType() {
            return fmd.getKey().getDeclaredType();
        }

        public Type getKeyType() {
            return owner.model.getType(getKeyJavaType());
        }
        
        public PersistentAttributeType getPersistentAttributeType() {
            return PersistentAttributeType.MANY_TO_MANY;
        }
    }
}




© 2015 - 2024 Weber Informatics LLC | Privacy Policy