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

org.wamblee.persistence.PersistentFactory Maven / Gradle / Ivy

The newest version!
/*
 * Copyright 2005-2010 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
 * 
 *      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.wamblee.persistence;

import java.io.Serializable;
import java.util.List;
import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;

import javax.persistence.Id;
import javax.persistence.Version;

import org.wamblee.reflection.Accessor;
import org.wamblee.reflection.AnnotationUtils;

/**
 * Factory which creates a {@link Persistent} object for a given JPA entity for
 * interfacing with the primary key and version of the entity.
 * 
 * This utility only treats primary keys and fields that are annotated with @Id
 * and @Version. In case ORM files are used for the definition of primary key
 * and or version, then those fields are ignored.
 * 
 * @author Erik Brakkee
 * 
 */
public class PersistentFactory {

    /**
     * Cache of a mapping of class names to entity accessors.
     */
    private static Map CACHE = new ConcurrentHashMap();

    static class EntityAccessor {
        private Accessor pk;
        private Accessor version;

        public EntityAccessor(Accessor aPk, Accessor aVersion) {
            pk = aPk;
            version = aVersion;
        }

        public Accessor getPk() {
            return pk;
        }

        public Accessor getVersion() {
            return version;
        }
    }

    public static class EntityObjectAccessor implements Persistent {
        private EntityAccessor accessor;
        private Object entity;

        public EntityObjectAccessor(Object aEntity, EntityAccessor aAccessor) {
            accessor = aAccessor;
            entity = aEntity;
        }

        public EntityAccessor getAccessor() {
            return accessor;
        };

        @Override
        public Serializable getPrimaryKey() {
            if (accessor == null || accessor.getPk() == null) {
                return null;
            }
            return (Serializable) accessor.getPk().get(entity);
        }

        @Override
        public void setPrimaryKey(Serializable aKey) {
            if (accessor == null || accessor.getPk() == null) {
                return;
            }
            accessor.getPk().set(entity, aKey);
        }

        @Override
        public Number getPersistedVersion() {
            if (accessor == null || accessor.getVersion() == null) {
                return null;
            }
            return (Number) accessor.getVersion().get(entity);
        }

        @Override
        public void setPersistedVersion(Number aVersion) {
            if (accessor == null || accessor.getVersion() == null) {
                return;
            }
            accessor.getVersion().set(entity, aVersion);
        }
    }

    /**
     * Create the entity accessor for a given class or returns a cached instance
     * if one already exists.
     * 
     * @param aClass
     *            Class.
     * @return Entity accessor for the given class or null of the given object
     *         is not an entity.
     */
    public static EntityAccessor createEntityAccessor(Class aClass) {
        EntityAccessor accessor = CACHE.get(aClass.getName());
        if (accessor == null) {
            accessor = analyse(aClass);
            if (accessor != null) {
                CACHE.put(aClass.getName(), accessor);
            }
        }
        return accessor;
    }

    private static EntityAccessor analyse(Class aClass) {
        List pkAccessors = AnnotationUtils.analyse(aClass, Id.class);
        List versionAccessors = AnnotationUtils.analyse(aClass,
            Version.class);
        Accessor pk = null;
        if (pkAccessors.size() > 0) {
            pk = pkAccessors.get(0);
        }
        Accessor version = null;
        if (versionAccessors.size() > 0) {
            version = versionAccessors.get(0);
        }
        if (pk != null || version != null) {
            return new EntityAccessor(pk, version);
        }
        return null;
    }

    /**
     * Creates the {@link Persistent} wrapper for interfacing with primary key
     * and version of the entity.
     * 
     * @param aEntity
     *            Entity to use.
     * @return Persistent object or null if this is not an entity.
     */
    public static Persistent create(Object aEntity) {
        EntityAccessor accessor = createEntityAccessor(aEntity.getClass());
        if (accessor == null) {
            return null;
        }
        return new EntityObjectAccessor(aEntity, accessor);
    }
}




© 2015 - 2024 Weber Informatics LLC | Privacy Policy