/******************************************************************************* * Copyright (c) 1998, 2015 Oracle and/or its affiliates. All rights reserved. * This program and the accompanying materials are made available under the * terms of the Eclipse Public License v1.0 and Eclipse Distribution License v. 1.0 * which accompanies this distribution. * The Eclipse Public License is available at http://www.eclipse.org/legal/epl-v10.html * and the Eclipse Distribution License is available at * http://www.eclipse.org/org/documents/edl-v10.php. * * Contributors: * Oracle - initial API and implementation from Oracle TopLink * 05/16/2008-1.0M8 Guy Pelletier * - 218084: Implement metadata merging functionality between mapping files * 05/23/2008-1.0M8 Guy Pelletier * - 211330: Add attributes-complete support to the EclipseLink-ORM.XML Schema * 09/23/2008-1.1 Guy Pelletier * - 241651: JPA 2.0 Access Type support * 12/12/2008-1.1 Guy Pelletier * - 249860: Implement table per class inheritance support. * 01/28/2009-2.0 Guy Pelletier * - 248293: JPA 2.0 Element Collections (part 1) * 02/06/2009-2.0 Guy Pelletier * - 248293: JPA 2.0 Element Collections (part 2) * 03/27/2009-2.0 Guy Pelletier * - 241413: JPA 2.0 Add EclipseLink support for Map type attributes * 04/24/2009-2.0 Guy Pelletier * - 270011: JPA 2.0 MappedById support * 06/16/2009-2.0 Guy Pelletier * - 277039: JPA 2.0 Cache Usage Settings * 06/25/2009-2.0 Michael O'Brien * - 266912: change MappedSuperclass handling in stage2 to pre process accessors * in support of the custom descriptors holding mappings required by the Metamodel * 09/24//2009-2.0 Michael O'Brien * - 266912: In initIdClass() store IdClass names for use by the Metamodel API * 10/21/2009-2.0 Guy Pelletier * - 290567: mappedbyid support incomplete * 12/2/2009-2.1 Guy Pelletier * - 296289: Add current annotation metadata support on mapped superclasses to EclipseLink-ORM.XML Schema * 01/19/2010-2.1 Guy Pelletier * - 211322: Add fetch-group(s) support to the EclipseLink-ORM.XML Schema * 05/04/2010-2.1 Guy Pelletier * - 309373: Add parent class attribute to EclipseLink-ORM * 06/01/2010-2.1 Guy Pelletier * - 315195: Add new property to avoid reading XML during the canonical model generation * 06/09/2010-2.0.3 Guy Pelletier * - 313401: shared-cache-mode defaults to NONE when the element value is unrecognized * 06/14/2010-2.2 Guy Pelletier * - 264417: Table generation is incorrect for JoinTables in AssociationOverrides * 06/22/2010-2.2 Guy Pelletier * - 308729: Persistent Unit deployment exception when mappedsuperclass has no annotations but has lifecycle callbacks * 07/05/2010-2.1.1 Guy Pelletier * - 317708: Exception thrown when using LAZY fetch on VIRTUAL mapping * 08/04/2010-2.1.1 Guy Pelletier * - 315782: JPA2 derived identity metadata processing validation doesn't account for autoboxing * 10/15/2010-2.2 Guy Pelletier * - 322008: Improve usability of additional criteria applied to queries at the session/EM * 10/28/2010-2.2 Guy Pelletier * - 3223850: Primary key metadata issues * 12/01/2010-2.2 Guy Pelletier * - 331234: xml-mapping-metadata-complete overriden by metadata-complete specification * 03/08/2011-2.3 Guy Pelletier * - 337323: Multi-tenant with shared schema support * 03/24/2011-2.3 Guy Pelletier * - 337323: Multi-tenant with shared schema support (part 1) * 03/24/2011-2.3 Guy Pelletier * - 337323: Multi-tenant with shared schema support (part 8) * 07/03/2011-2.3.1 Guy Pelletier * - 348756: m_cascadeOnDelete boolean should be changed to Boolean * 02/08/2012-2.4 Guy Pelletier * - 350487: JPA 2.1 Specification defined support for Stored Procedure Calls * 11/19/2012-2.5 Guy Pelletier * - 389090: JPA 2.1 DDL Generation Support (foreign key metadata support) * 11/29/2012-2.5 Guy Pelletier * - 395406: Fix nightly static weave test errors ******************************************************************************/ package org.eclipse.persistence.internal.jpa.metadata.accessors.classes; import java.util.ArrayList; import java.util.Collection; import java.util.HashMap; import java.util.List; import java.util.Map; import org.eclipse.persistence.annotations.AdditionalCriteria; import org.eclipse.persistence.annotations.Cache; import org.eclipse.persistence.annotations.CacheIndex; import org.eclipse.persistence.annotations.CacheIndexes; import org.eclipse.persistence.annotations.CacheInterceptor; import org.eclipse.persistence.annotations.FetchGroup; import org.eclipse.persistence.annotations.FetchGroups; import org.eclipse.persistence.annotations.NamedStoredFunctionQueries; import org.eclipse.persistence.annotations.NamedStoredFunctionQuery; import org.eclipse.persistence.annotations.PrimaryKey; import org.eclipse.persistence.annotations.QueryRedirectors; import org.eclipse.persistence.annotations.ExistenceChecking; import org.eclipse.persistence.annotations.Multitenant; import org.eclipse.persistence.annotations.OptimisticLocking; import org.eclipse.persistence.annotations.ReadOnly; import org.eclipse.persistence.annotations.SerializedObject; import org.eclipse.persistence.annotations.UuidGenerator; import org.eclipse.persistence.internal.jpa.metadata.accessors.objects.MetadataAccessibleObject; import org.eclipse.persistence.internal.jpa.metadata.accessors.objects.MetadataAnnotation; import org.eclipse.persistence.internal.jpa.metadata.accessors.objects.MetadataClass; import org.eclipse.persistence.internal.jpa.metadata.accessors.objects.MetadataField; import org.eclipse.persistence.internal.jpa.metadata.accessors.objects.MetadataMethod; import org.eclipse.persistence.internal.jpa.metadata.additionalcriteria.AdditionalCriteriaMetadata; import org.eclipse.persistence.internal.jpa.metadata.cache.CacheIndexMetadata; import org.eclipse.persistence.internal.jpa.metadata.cache.CacheInterceptorMetadata; import org.eclipse.persistence.internal.jpa.metadata.cache.CacheMetadata; import org.eclipse.persistence.internal.jpa.metadata.listeners.EntityListenerMetadata; import org.eclipse.persistence.internal.jpa.metadata.locking.OptimisticLockingMetadata; import org.eclipse.persistence.internal.jpa.metadata.multitenant.MultitenantMetadata; import org.eclipse.persistence.internal.jpa.metadata.MetadataDescriptor; import org.eclipse.persistence.internal.jpa.metadata.MetadataLogger; import org.eclipse.persistence.internal.jpa.metadata.MetadataProject; import org.eclipse.persistence.internal.jpa.metadata.ORMetadata; import org.eclipse.persistence.internal.jpa.metadata.columns.PrimaryKeyMetadata; import org.eclipse.persistence.internal.jpa.metadata.queries.FetchGroupMetadata; import org.eclipse.persistence.internal.jpa.metadata.queries.NamedNativeQueryMetadata; import org.eclipse.persistence.internal.jpa.metadata.queries.NamedPLSQLStoredFunctionQueryMetadata; import org.eclipse.persistence.internal.jpa.metadata.queries.NamedPLSQLStoredProcedureQueryMetadata; import org.eclipse.persistence.internal.jpa.metadata.queries.NamedQueryMetadata; import org.eclipse.persistence.internal.jpa.metadata.queries.NamedStoredFunctionQueryMetadata; import org.eclipse.persistence.internal.jpa.metadata.queries.NamedStoredProcedureQueryMetadata; import org.eclipse.persistence.internal.jpa.metadata.queries.QueryRedirectorsMetadata; import org.eclipse.persistence.internal.jpa.metadata.queries.SQLResultSetMappingMetadata; import org.eclipse.persistence.internal.jpa.metadata.sequencing.SequenceGeneratorMetadata; import org.eclipse.persistence.internal.jpa.metadata.sequencing.TableGeneratorMetadata; import org.eclipse.persistence.internal.jpa.metadata.sequencing.UuidGeneratorMetadata; import org.eclipse.persistence.internal.jpa.metadata.sop.SerializedObjectPolicyMetadata; import org.eclipse.persistence.internal.jpa.metadata.xml.XMLEntityMappings; import org.eclipse.persistence.platform.database.oracle.annotations.NamedPLSQLStoredFunctionQueries; import org.eclipse.persistence.platform.database.oracle.annotations.NamedPLSQLStoredFunctionQuery; import org.eclipse.persistence.platform.database.oracle.annotations.NamedPLSQLStoredProcedureQueries; import org.eclipse.persistence.platform.database.oracle.annotations.NamedPLSQLStoredProcedureQuery; import org.eclipse.persistence.queries.FetchGroupTracker; import static org.eclipse.persistence.internal.jpa.metadata.MetadataConstants.JPA_ACCESS_FIELD; import static org.eclipse.persistence.internal.jpa.metadata.MetadataConstants.JPA_ACCESS_PROPERTY; import static org.eclipse.persistence.internal.jpa.metadata.MetadataConstants.JPA_CACHEABLE; import static org.eclipse.persistence.internal.jpa.metadata.MetadataConstants.JPA_EXCLUDE_DEFAULT_LISTENERS; import static org.eclipse.persistence.internal.jpa.metadata.MetadataConstants.JPA_EXCLUDE_SUPERCLASS_LISTENERS; import static org.eclipse.persistence.internal.jpa.metadata.MetadataConstants.JPA_ENTITY_LISTENERS; import static org.eclipse.persistence.internal.jpa.metadata.MetadataConstants.JPA_ID_CLASS; import static org.eclipse.persistence.internal.jpa.metadata.MetadataConstants.JPA_NAMED_NATIVE_QUERIES; import static org.eclipse.persistence.internal.jpa.metadata.MetadataConstants.JPA_NAMED_NATIVE_QUERY; import static org.eclipse.persistence.internal.jpa.metadata.MetadataConstants.JPA_NAMED_QUERIES; import static org.eclipse.persistence.internal.jpa.metadata.MetadataConstants.JPA_NAMED_QUERY; import static org.eclipse.persistence.internal.jpa.metadata.MetadataConstants.JPA_NAMED_STORED_PROCEDURE_QUERIES; import static org.eclipse.persistence.internal.jpa.metadata.MetadataConstants.JPA_NAMED_STORED_PROCEDURE_QUERY; import static org.eclipse.persistence.internal.jpa.metadata.MetadataConstants.JPA_SEQUENCE_GENERATOR; import static org.eclipse.persistence.internal.jpa.metadata.MetadataConstants.JPA_SQL_RESULT_SET_MAPPING; import static org.eclipse.persistence.internal.jpa.metadata.MetadataConstants.JPA_SQL_RESULT_SET_MAPPINGS; import static org.eclipse.persistence.internal.jpa.metadata.MetadataConstants.JPA_TABLE_GENERATOR; import static org.eclipse.persistence.internal.jpa.metadata.MetadataConstants.JPA_TRANSIENT; /** * INTERNAL: * A mapped superclass accessor. * * When adding new metadata objects, be sure to include their initialization in * initXMLObject. This sets the accessible object and the location of the * ORMetadata which is used when merging. Also new member metadata variables * need to be added to the merge method. * * Key notes: * - any metadata mapped from XML to this class must be compared in the * equals method. * - any metadata mapped from XML to this class must be handled in the merge * method. (merging is done at the accessor/mapping level) * - any metadata mapped from XML to this class must be initialized in the * initXMLObject method. * - methods should be preserved in alphabetical order. * * @author Guy Pelletier * @since TopLink EJB 3.0 Reference Implementation */ public class MappedSuperclassAccessor extends ClassAccessor { private Boolean m_excludeDefaultListeners; private Boolean m_excludeSuperclassListeners; private AdditionalCriteriaMetadata m_additionalCriteria; private Boolean m_cacheable; private Boolean m_readOnly; private CacheMetadata m_cache; private CacheInterceptorMetadata m_cacheInterceptor; private List<CacheIndexMetadata> m_cacheIndexes = new ArrayList<CacheIndexMetadata>(); private List<EntityListenerMetadata> m_entityListeners = new ArrayList<EntityListenerMetadata>(); private List<FetchGroupMetadata> m_fetchGroups = new ArrayList<FetchGroupMetadata>(); private List<NamedQueryMetadata> m_namedQueries = new ArrayList<NamedQueryMetadata>(); private List<NamedNativeQueryMetadata> m_namedNativeQueries = new ArrayList<NamedNativeQueryMetadata>(); private List<NamedStoredFunctionQueryMetadata> m_namedStoredFunctionQueries = new ArrayList<NamedStoredFunctionQueryMetadata>(); private List<NamedStoredProcedureQueryMetadata> m_namedStoredProcedureQueries = new ArrayList<NamedStoredProcedureQueryMetadata>(); private List<NamedPLSQLStoredFunctionQueryMetadata> m_namedPLSQLStoredFunctionQueries = new ArrayList<NamedPLSQLStoredFunctionQueryMetadata>(); private List<NamedPLSQLStoredProcedureQueryMetadata> m_namedPLSQLStoredProcedureQueries = new ArrayList<NamedPLSQLStoredProcedureQueryMetadata>(); private List<SQLResultSetMappingMetadata> m_sqlResultSetMappings = new ArrayList<SQLResultSetMappingMetadata>(); private MetadataClass m_idClass; private MultitenantMetadata m_multitenant; private OptimisticLockingMetadata m_optimisticLocking; private PrimaryKeyMetadata m_primaryKey; private QueryRedirectorsMetadata m_queryRedirectors; private SequenceGeneratorMetadata m_sequenceGenerator; private TableGeneratorMetadata m_tableGenerator; private UuidGeneratorMetadata m_uuidGenerator; private SerializedObjectPolicyMetadata m_serializedObjectPolicy; private String m_existenceChecking; private String m_idClassName; private String m_prePersist; private String m_postPersist; private String m_preRemove; private String m_postRemove; private String m_preUpdate; private String m_postUpdate; private String m_postLoad; /** * INTERNAL: * Used for OX mapping. */ public MappedSuperclassAccessor() { super("<mapped-superclass>"); } /** * INTERNAL: * Used for OX mapping. */ public MappedSuperclassAccessor(String xmlElement) { super(xmlElement); } /** * INTERNAL: */ public MappedSuperclassAccessor(MetadataAnnotation annotation, MetadataClass cls, MetadataProject project) { super(annotation, cls, project); } /** * INTERNAL: */ public MappedSuperclassAccessor(MetadataAnnotation annotation, MetadataClass cls, MetadataDescriptor descriptor) { super(annotation, cls, descriptor); } /** * INTERNAL: * Used for OX mapping. */ public boolean excludeDefaultListeners() { return m_excludeDefaultListeners != null && m_excludeDefaultListeners.booleanValue(); } /** * INTERNAL: * Used for OX mapping. */ public boolean excludeSuperclassListeners() { return m_excludeSuperclassListeners != null && m_excludeSuperclassListeners.booleanValue(); } /** * INTERNAL: * Used for OX mapping. */ public AdditionalCriteriaMetadata getAdditionalCriteria() { return m_additionalCriteria; } /** * INTERNAL: * Used for OX mapping. */ public CacheMetadata getCache() { return m_cache; } /** * INTERNAL: * Used for OX mapping. */ public List<CacheIndexMetadata> getCacheIndexes() { return m_cacheIndexes; } /** * INTERNAL: * Used for OX mapping. */ public Boolean getCacheable() { return m_cacheable; } /** * INTERNAL: * Used for OX mapping. */ public CacheInterceptorMetadata getCacheInterceptor() { return m_cacheInterceptor; } /** * INTERNAL: * Used for OX mapping. */ public List<EntityListenerMetadata> getEntityListeners() { return m_entityListeners; } /** * INTERNAL: * Used for OX mapping. */ public Boolean getExcludeDefaultListeners() { return m_excludeDefaultListeners; } /** * INTERNAL: * Used for OX mapping. */ public Boolean getExcludeSuperclassListeners() { return m_excludeSuperclassListeners; } /** * INTERNAL: * Used for OX mapping. */ public String getExistenceChecking() { return m_existenceChecking; } /** * INTERNAL: * Used for OX mapping. */ public List<FetchGroupMetadata> getFetchGroups() { return m_fetchGroups; } /** * INTERNAL: */ protected MetadataClass getIdClass() { return m_idClass; } /** * INTERNAL: * Used for OX mapping. */ public String getIdClassName() { return m_idClassName; } /** * INTERNAL: * Used for OX mapping. */ public MultitenantMetadata getMultitenant() { return m_multitenant; } /** * INTERNAL: * Used for OX mapping. */ public List<NamedNativeQueryMetadata> getNamedNativeQueries() { return m_namedNativeQueries; } /** * INTERNAL: * Used for OX mapping. */ public List<NamedPLSQLStoredFunctionQueryMetadata> getNamedPLSQLStoredFunctionQueries() { return m_namedPLSQLStoredFunctionQueries; } /** * INTERNAL: * Used for OX mapping. */ public List<NamedPLSQLStoredProcedureQueryMetadata> getNamedPLSQLStoredProcedureQueries() { return m_namedPLSQLStoredProcedureQueries; } /** * INTERNAL: * Used for OX mapping. */ public List<NamedQueryMetadata> getNamedQueries() { return m_namedQueries; } /** * INTERNAL: * Used for OX mapping. */ public List<NamedStoredFunctionQueryMetadata> getNamedStoredFunctionQueries() { return m_namedStoredFunctionQueries; } /** * INTERNAL: * Used for OX mapping. */ public List<NamedStoredProcedureQueryMetadata> getNamedStoredProcedureQueries() { return m_namedStoredProcedureQueries; } /** * INTERNAL: * Used for OX mapping. */ public OptimisticLockingMetadata getOptimisticLocking() { return m_optimisticLocking; } /** * INTERNAL: * Used for OX mapping. */ public String getPostLoad() { return m_postLoad; } /** * INTERNAL: * Used for OX mapping. */ public String getPostPersist() { return m_postPersist; } /** * INTERNAL: * Used for OX mapping. */ public String getPostRemove() { return m_postRemove; } /** * INTERNAL: * Used for OX mapping. */ public String getPostUpdate() { return m_postUpdate; } /** * INTERNAL: * Used for OX mapping. */ public String getPrePersist() { return m_prePersist; } /** * INTERNAL: * Used for OX mapping. */ public String getPreRemove() { return m_preRemove; } /** * INTERNAL: * Used for OX mapping. */ public String getPreUpdate() { return m_preUpdate; } /** * INTERNAL: * Used for OX mapping. */ public PrimaryKeyMetadata getPrimaryKey() { return m_primaryKey; } /** * INTERNAL: * Used for OX mapping. */ public QueryRedirectorsMetadata getQueryRedirectors() { return m_queryRedirectors; } /** * INTERNAL: * Used for OX mapping. */ public Boolean getReadOnly() { return m_readOnly; } /** * INTERNAL: * Used for OX mapping. */ public SequenceGeneratorMetadata getSequenceGenerator() { return m_sequenceGenerator; } /** * INTERNAL: * Used for OX mapping. */ public List<SQLResultSetMappingMetadata> getSqlResultSetMappings() { return m_sqlResultSetMappings; } /** * INTERNAL: * Used for OX mapping. */ public SerializedObjectPolicyMetadata getSerializedObjectPolicy() { return m_serializedObjectPolicy; } /** * INTERNAL: * Used for OX mapping. */ public TableGeneratorMetadata getTableGenerator() { return m_tableGenerator; } /** * INTERNAL: * Used for OX mapping. */ public UuidGeneratorMetadata getUuidGenerator() { return m_uuidGenerator; } /** * INTERNAL: * Return true if any given field defines object relational persistence * mapping annotations. This method is used when determining the access type * of this accessor. Note: Through the annotation target, it is invalid to * specify a lifecycle annotation on a field so we don't need to check as we * do when checking the methods. * * @see processAccessType() */ protected boolean hasObjectRelationalFieldMappingAnnotationsDefined() { Collection<MetadataField> fields = getJavaClass().getFields().values(); for (MetadataField field : fields) { if (field.hasDeclaredAnnotations(this) && !field.isEclipseLinkWeavedField()) { return true; } } return false; } /** * INTERNAL: * Return true if any given method defines object relational persistence * mapping annotations. This method is used when determining the access type * of this accessor. Note: life cycle annotations are NOT object relational * mappings therefore should not influence the decision. * * @see processAccessType() */ protected boolean hasObjectRelationalMethodMappingAnnotationsDefined() { Collection<MetadataMethod> methods = getJavaClass().getMethods().values(); for (MetadataMethod method : methods) { if (method.hasDeclaredAnnotations(this) && ! method.isALifeCycleCallbackMethod()) { return true; } } return false; } /** * INTERNAL: * This method is called in the pre-processing stage since we want to * gather a list of id classes used throughout the persistence unit. This * will help us build accessors, namely, mappedById accessors that can * reference an id class type. */ protected void initIdClass() { if (m_idClass == null || m_idClass.equals(void.class)) { // Check for an IdClass annotation. if (isAnnotationPresent(JPA_ID_CLASS)) { m_idClass = getMetadataClass(getAnnotation(JPA_ID_CLASS).getAttributeString("value")); } } else { // We have an XML specification. Log a message if an annotation has also been defined. if (isAnnotationPresent(JPA_ID_CLASS)) { getLogger().logConfigMessage(MetadataLogger.OVERRIDE_ANNOTATION_WITH_XML, getAnnotation(JPA_ID_CLASS), getJavaClassName(), getLocation()); } } // Add the id class to the known list of id classes for this project. if (m_idClass != null && ! m_idClass.equals(void.class)) { getProject().addIdClass(m_idClass.getName()); // 266912: We store the IdClass (not an EmbeddableId) for use by the Metamodel API getProject().getProject().addMetamodelIdClassMapEntry(getAccessibleObject().getName(), m_idClass.getName()); } } /** * INTERNAL: */ @Override public void initXMLObject(MetadataAccessibleObject accessibleObject, XMLEntityMappings entityMappings) { super.initXMLObject(accessibleObject, entityMappings); // Initialize single objects. initXMLObject(m_additionalCriteria, accessibleObject); initXMLObject(m_cache, accessibleObject); initXMLObject(m_cacheInterceptor, accessibleObject); initXMLObject(m_optimisticLocking, accessibleObject); initXMLObject(m_primaryKey, accessibleObject); initXMLObject(m_queryRedirectors, accessibleObject); initXMLObject(m_sequenceGenerator, accessibleObject); initXMLObject(m_serializedObjectPolicy, accessibleObject); initXMLObject(m_tableGenerator, accessibleObject); initXMLObject(m_uuidGenerator, accessibleObject); initXMLObject(m_multitenant, accessibleObject); // Initialize lists of objects. initXMLObjects(m_entityListeners, accessibleObject); initXMLObjects(m_fetchGroups, accessibleObject); initXMLObjects(m_namedQueries, accessibleObject); initXMLObjects(m_namedNativeQueries, accessibleObject); initXMLObjects(m_namedStoredFunctionQueries, accessibleObject); initXMLObjects(m_namedStoredProcedureQueries, accessibleObject); initXMLObjects(m_namedPLSQLStoredFunctionQueries, accessibleObject); initXMLObjects(m_namedPLSQLStoredProcedureQueries, accessibleObject); initXMLObjects(m_sqlResultSetMappings, accessibleObject); // Simple class object m_idClass = initXMLClassName(m_idClassName); } /** * INTERNAL: * Return whether this accessor represents a MappedSuperclass */ @Override public boolean isMappedSuperclass() { return true; } /** * INTERNAL: * Mapped-superclass level merging details. Merging is only done on * accessors from XML. Since entities and embeddables are initialized * before merging, for any class name specifications we can not only merge * the class names but must also merge the initialized classes since we * do not re-initialize class accessors after a merge. Mapped superclasses * are not initialized till they are reloaded therefore merging only the * class names is needed, however merging their respective MetadataClasses * will do nothing since merging null with null yields null. */ @Override public void merge(ORMetadata metadata) { super.merge(metadata); MappedSuperclassAccessor accessor = (MappedSuperclassAccessor) metadata; // Simple object merging. m_excludeDefaultListeners = (Boolean) mergeSimpleObjects(m_excludeDefaultListeners, accessor.excludeDefaultListeners(), accessor, "<exclude-default-listeners>"); m_excludeSuperclassListeners = (Boolean) mergeSimpleObjects(m_excludeSuperclassListeners, accessor.excludeSuperclassListeners(), accessor, "<exclude-superclass-listeners>"); m_cacheable = (Boolean) mergeSimpleObjects(m_cacheable, accessor.getCacheable(), accessor, "@cacheable"); m_readOnly = (Boolean) mergeSimpleObjects(m_readOnly, accessor.getReadOnly(), accessor, "@read-only"); m_idClass = (MetadataClass) mergeSimpleObjects(m_idClass, accessor.getIdClass(), accessor, "<id-class>"); m_idClassName = (String) mergeSimpleObjects(m_idClassName, accessor.getIdClassName(), accessor, "<id-class>"); m_prePersist = (String) mergeSimpleObjects(m_prePersist, accessor.getPrePersist(), accessor, "<pre-persist>"); m_postPersist = (String) mergeSimpleObjects(m_postPersist, accessor.getPostPersist(), accessor, "<post-persist>"); m_preRemove = (String) mergeSimpleObjects(m_preRemove, accessor.getPreRemove(), accessor, "<pre-remove>"); m_postRemove = (String) mergeSimpleObjects(m_postRemove, accessor.getPostRemove(), accessor, "<post-remove>"); m_preUpdate = (String) mergeSimpleObjects(m_preUpdate, accessor.getPreUpdate(), accessor, "<pre-update>"); m_postUpdate = (String) mergeSimpleObjects(m_postUpdate, accessor.getPostUpdate(), accessor, "<post-update>"); m_postLoad = (String) mergeSimpleObjects(m_postLoad, accessor.getPostLoad(), accessor, "<post-load>"); m_existenceChecking = (String) mergeSimpleObjects(m_existenceChecking, accessor.getExistenceChecking(), accessor, "@existence-checking"); // ORMetadata object merging. m_additionalCriteria = (AdditionalCriteriaMetadata) mergeORObjects(m_additionalCriteria, accessor.getAdditionalCriteria()); m_cache = (CacheMetadata) mergeORObjects(m_cache, accessor.getCache()); m_cacheInterceptor = (CacheInterceptorMetadata) mergeORObjects(m_cacheInterceptor, accessor.getCacheInterceptor()); m_optimisticLocking = (OptimisticLockingMetadata) mergeORObjects(m_optimisticLocking, accessor.getOptimisticLocking()); m_primaryKey = (PrimaryKeyMetadata) mergeORObjects(m_primaryKey, accessor.getPrimaryKey()); m_queryRedirectors = (QueryRedirectorsMetadata) mergeORObjects(m_queryRedirectors, accessor.getQueryRedirectors()); m_sequenceGenerator = (SequenceGeneratorMetadata) mergeORObjects(m_sequenceGenerator, accessor.getSequenceGenerator()); m_serializedObjectPolicy = (SerializedObjectPolicyMetadata) mergeORObjects(m_serializedObjectPolicy, accessor.getSerializedObjectPolicy()); m_tableGenerator = (TableGeneratorMetadata) mergeORObjects(m_tableGenerator, accessor.getTableGenerator()); m_uuidGenerator = (UuidGeneratorMetadata) mergeORObjects(m_uuidGenerator, accessor.getUuidGenerator()); m_multitenant = (MultitenantMetadata) mergeORObjects(m_multitenant, accessor.getMultitenant()); // ORMetadata list merging. m_entityListeners = mergeORObjectLists(m_entityListeners, accessor.getEntityListeners()); m_fetchGroups = mergeORObjectLists(m_fetchGroups, accessor.getFetchGroups()); m_namedQueries = mergeORObjectLists(m_namedQueries, accessor.getNamedQueries()); m_namedNativeQueries = mergeORObjectLists(m_namedNativeQueries, accessor.getNamedNativeQueries()); m_namedStoredFunctionQueries = mergeORObjectLists(m_namedStoredFunctionQueries, accessor.getNamedStoredFunctionQueries()); m_namedStoredProcedureQueries = mergeORObjectLists(m_namedStoredProcedureQueries, accessor.getNamedStoredProcedureQueries()); m_namedPLSQLStoredFunctionQueries = mergeORObjectLists(m_namedPLSQLStoredFunctionQueries, accessor.getNamedPLSQLStoredFunctionQueries()); m_namedPLSQLStoredProcedureQueries = mergeORObjectLists(m_namedPLSQLStoredProcedureQueries, accessor.getNamedPLSQLStoredProcedureQueries()); m_sqlResultSetMappings = mergeORObjectLists(m_sqlResultSetMappings, accessor.getSqlResultSetMappings()); } /** * INTERNAL: * The pre-process method is called during regular deployment and metadata * processing. * * This method will pre-process the items of interest on this mapped * superclass for each entity class that inherits from it. The order of * processing is important, care must be taken if changes must be made. */ @Override public void preProcess() { // Add any id class definition to the project. initIdClass(); // Set a cacheable flag if specified on the entity's descriptor. processCacheable(); // Process our parents metadata after processing our own. super.preProcess(); } /** * INTERNAL: * Process the items of interest on a mapped superclass. */ @Override public void process() { // Process the fetch group metadata. processFetchGroups(); // Process the named query metadata. processNamedQueries(); // Process the named native query metadata. processNamedNativeQueries(); // Process the named stored procedure query metadata processNamedStoredProcedureQueries(); // Process the named stored function query metadata processNamedStoredFunctionQueries(); // Process the named PLSQL stored procedure query metadata processNamedPLSQLStoredProcedureQueries(); // Process the named PLSQL stored function query metadata processNamedPLSQLStoredFunctionQueries(); // Process the sql result set mapping metadata processSqlResultSetMappings(); // Process the table generator metadata. processTableGenerator(); // Process the uuid generator metadata. processUuidGenerator(); // Process the sequence generator metadata. processSequenceGenerator(); // Process serialized object policy metadata processSerializedObjectPolicy(); // Process the id class metadata. processIdClass(); // Process the primary key metadata. processPrimaryKey(); // Process the exclude default listeners metadata. processExcludeDefaultListeners(); // Process the exclude superclass listeners metadata. processExcludeSuperclassListeners(); // Process the optimistic locking policy metadata. processOptimisticLocking(); // Process any cache metadata (Cache and CacheInterceptor) taking the // cacheable and persistence unit global setting into consideration. processCaching(); // Process the Default Redirectors processDefaultRedirectors(); // Process the read only metadata. processReadOnly(); // Process the existence checking metadata. processExistenceChecking(); // Process the additional criteria metadata. processAdditionalCriteria(); // Process the multitenant metadata processMultitenant(); // Process our parents metadata after processing our own. super.process(); } /** * INTERNAL: * Process the additional criteria metadata specified on an entity or * mapped superclass. Once the additional criteria are processed from * XML process the additional criteria from annotations. This order of * processing must be maintained. */ protected void processAdditionalCriteria() { if (m_additionalCriteria != null || isAnnotationPresent(AdditionalCriteria.class)) { // We have additional criteria available. If the descriptor already // has additional criteria, then we are processing a mapped // superclass and should ignore the additional criteria for this // descriptor. if (getDescriptor().hasAdditionalCriteria()) { // Ignore additional criteria on mapped superclass if additional // criteria is already defined on the entity. getLogger().logConfigMessage(MetadataLogger.IGNORE_MAPPED_SUPERCLASS_ADDITIONAL_CRITERIA, getDescriptor().getJavaClass(), getJavaClass()); } else if (m_additionalCriteria != null) { // Process the additional criteria that was specified in XML. m_additionalCriteria.process(getDescriptor()); } else { // Process the additional criteria from the annotation. new AdditionalCriteriaMetadata(getAnnotation(AdditionalCriteria.class), this).process(getDescriptor()); } } } /** * INTERNAL: * Process the accessType for a MappedSuperclass. * This function is referenced by MetadataProject.addMetamodelMappedSuperclass(). * The overridden function on the subclass must be used in all other cases. * @since EclipseLink 1.2 for the JPA 2.0 Reference Implementation */ @Override public void processAccessType() { // 266912: Note: this function is a port of the subclass protected EntityAccessor.processAccessType() minus step 1 and 2 String explicitAccessType = getAccess(); String defaultAccessType = null; // 1 - If there are no mapped superclasses or no mapped superclasses // without an explicit access type. Check where the annotations are // defined on this entity class. if (hasObjectRelationalFieldMappingAnnotationsDefined()) { defaultAccessType = JPA_ACCESS_FIELD; } else if (hasObjectRelationalMethodMappingAnnotationsDefined()) { defaultAccessType = JPA_ACCESS_PROPERTY; } else { // 2 - If there are no annotations defined on either the // fields or properties, check for an xml default from // persistence-unit-metadata-defaults or entity-mappings. if (getDescriptor().getDefaultAccess() != null) { defaultAccessType = getDescriptor().getDefaultAccess(); } else { // 3 - We've exhausted our search, set the access type to FIELD. defaultAccessType = JPA_ACCESS_FIELD; } } // Finally set the default access type on the descriptor and log a // message to the user if we are defaulting the access type for this // entity to use that default. getDescriptor().setDefaultAccess(defaultAccessType); if (explicitAccessType == null) { getLogger().logConfigMessage(MetadataLogger.ACCESS_TYPE, defaultAccessType, getJavaClass()); } // This access type setting on the class descriptor will be used to // weave the class properly. getDescriptor().setAccessTypeOnClassDescriptor(getAccessType()); } /** * INTERNAL: * Process a cache metadata. */ protected void processCache() { if (m_cache != null || isAnnotationPresent(Cache.class)) { if (getDescriptor().isInheritanceSubclass()) { // Ignore cache if specified on an inheritance subclass. getLogger().logWarningMessage(MetadataLogger.IGNORE_INHERITANCE_SUBCLASS_CACHE, getJavaClass()); } else if (getDescriptor().hasCache()) { // Ignore cache on mapped superclass if cache is already // defined on the entity. getLogger().logConfigMessage(MetadataLogger.IGNORE_MAPPED_SUPERCLASS_CACHE, getDescriptor().getJavaClass(), getJavaClass()); } else { if (m_cache == null) { new CacheMetadata(getAnnotation(Cache.class), this).process(getDescriptor(), getJavaClass()); } else { m_cache.process(getDescriptor(), getJavaClass()); } } } } /** * INTERNAL: * Called in pre-process. It is called from an entity accessor and in * turn is called on the mapped-superclasses of that entity. */ protected void processCacheable() { if (m_cacheable != null || isAnnotationPresent(JPA_CACHEABLE)) { if (getDescriptor().hasCacheable()) { // Ignore cacheable on mapped superclass if cacheable is already // defined on the entity. getLogger().logConfigMessage(MetadataLogger.IGNORE_MAPPED_SUPERCLASS_CACHE, getDescriptor().getJavaClass(), getJavaClass()); } else { // Set the cacheable setting on the descriptor. if (m_cacheable == null) { m_cacheable = (Boolean) getAnnotation(JPA_CACHEABLE).getAttributeBooleanDefaultTrue("value"); } getDescriptor().setCacheable(m_cacheable); } } } /** * INTERNAL: * Process a cache interceptor metadata. */ protected void processCacheInterceptor() { if (m_cacheInterceptor != null || isAnnotationPresent(CacheInterceptor.class)) { if (getDescriptor().isInheritanceSubclass()) { // Ignore cache interceptor if specified on an inheritance subclass. getLogger().logWarningMessage(MetadataLogger.IGNORE_INHERITANCE_SUBCLASS_CACHE_INTERCEPTOR, getJavaClass()); } else if (getDescriptor().hasCacheInterceptor()) { // Ignore cache interceptor on mapped superclass if cache // interceptor is already defined on the entity. getLogger().logConfigMessage(MetadataLogger.IGNORE_MAPPED_SUPERCLASS_CACHE_INTERCEPTOR, getDescriptor().getJavaClass(), getJavaClass()); } else { if (m_cacheInterceptor == null) { new CacheInterceptorMetadata(getAnnotation(CacheInterceptor.class), this).process(getDescriptor(), getJavaClass()); } else { m_cacheInterceptor.process(getDescriptor(), getJavaClass()); } } } } /** * INTERNAL: * Process a caching metadata. This method will be called on an entity's * mapped superclasses (bottom --> up). We go through the mapped * superclasses to not only apply a cache setting but log ignore messages. */ protected void processCaching() { // The settings for processing cache metadata are as follows: // ALL or no setting // ENABLE_SELECTIVE and Cacheable(true) // DISABLE_SELECTIVE and Cacheable(true) if (getProject().isSharedCacheModeAll() || getProject().isSharedCacheModeEnableSelective()|| getProject().isSharedCacheModeDisableSelective()) { processCachingMetadata(); } } /** * INTERNAL: * Process a caching metadata. These are the items we process to configure * the entity's cache settings. */ protected void processCachingMetadata() { processCache(); processCacheInterceptor(); processCacheIndexes(); } /** * INTERNAL: * Process cache index information for the given metadata descriptor. */ protected void processCacheIndexes() { // TODO: This method is adding annotation metadata to XML metadata. This // is wrong and does not follow the spec ideology. XML metadata should // override not merge with annotations. if (isAnnotationPresent(CacheIndex.class)) { m_cacheIndexes.add(new CacheIndexMetadata(getAnnotation(CacheIndex.class), this)); } if (isAnnotationPresent(CacheIndexes.class)) { for (Object index : getAnnotation(CacheIndexes.class).getAttributeArray("value")) { m_cacheIndexes.add(new CacheIndexMetadata((MetadataAnnotation) index, this)); } } for (CacheIndexMetadata indexMetadata : m_cacheIndexes) { indexMetadata.process(getDescriptor(), null); } } /** * INTERNAL: * Process a default redirector metadata. */ protected void processDefaultRedirectors() { if (m_queryRedirectors != null || isAnnotationPresent(QueryRedirectors.class)) { if (getDescriptor().isInheritanceSubclass()) { // Ignore query redirector if specified on an inheritance subclass. getLogger().logWarningMessage(MetadataLogger.IGNORE_INHERITANCE_SUBCLASS_DEFAULT_REDIRECTORS, getJavaClass()); } else if (getDescriptor().hasDefaultRedirectors()) { // Ignore query redirector on mapped superclass if query // redirector is already defined on the entity. getLogger().logConfigMessage(MetadataLogger.IGNORE_MAPPED_SUPERCLASS_DEFAULT_REDIRECTORS, getDescriptor().getJavaClass(), getJavaClass()); } else { if (m_queryRedirectors == null) { new QueryRedirectorsMetadata(getAnnotation(QueryRedirectors.class), this).process(getDescriptor(), getJavaClass()); } else { m_queryRedirectors.process(getDescriptor(), getJavaClass()); } } } } /** * INTERNAL: * Process the entity listeners for this class accessor. Entity listeners * defined in XML will override those specified on the class. */ public void processEntityListeners(ClassLoader loader) { if (m_entityListeners.isEmpty()) { // Look for an annotation. MetadataAnnotation entityListeners = getAnnotation(JPA_ENTITY_LISTENERS); if (entityListeners != null) { for (Object entityListenerClass : entityListeners.getAttributeArray("value")) { EntityListenerMetadata listener = new EntityListenerMetadata(entityListeners, getMetadataClass((String) entityListenerClass, false), this); listener.process(this, loader, false); } } } else { // Process the listeners defined in XML. for (EntityListenerMetadata listener : m_entityListeners) { listener.process(this, loader, false); } } } /** * INTERNAL: * Process the exclude-default-listeners value. */ protected void processExcludeDefaultListeners() { if (excludeDefaultListeners()) { getDescriptor().setExcludeDefaultListeners(true); } else { // Don't overrite a true flag that could be set from a subclass // that already excluded them. if (isAnnotationPresent(JPA_EXCLUDE_DEFAULT_LISTENERS)) { getDescriptor().setExcludeDefaultListeners(true); } } } /** * INTERNAL: * Process the ExcludeSuperclassListeners value if one is specified (taking * metadata-complete into consideration). */ protected void processExcludeSuperclassListeners() { if (excludeSuperclassListeners()) { getDescriptor().setExcludeSuperclassListeners(true); } else { // Don't overrite a true flag that could be set from a subclass // that already excluded them. if (isAnnotationPresent(JPA_EXCLUDE_SUPERCLASS_LISTENERS)) { getDescriptor().setExcludeSuperclassListeners(true); } } } /** * INTERNAL: * Process the ExistenceChecking value if one is specified (taking * metadata-complete into consideration). */ protected void processExistenceChecking() { MetadataAnnotation existenceChecking = getAnnotation(ExistenceChecking.class); if (m_existenceChecking != null || existenceChecking != null) { if (getDescriptor().hasExistenceChecking()) { // Ignore existence-checking on mapped superclass if existence // checking is already defined on the entity. getLogger().logConfigMessage(MetadataLogger.IGNORE_MAPPED_SUPERCLASS_EXISTENCE_CHECKING, getDescriptor().getJavaClass(), getJavaClass()); } else { if (m_existenceChecking == null) { getDescriptor().setExistenceChecking(existenceChecking.getAttributeString("value")); } else { if (existenceChecking != null) { getLogger().logConfigMessage(MetadataLogger.OVERRIDE_ANNOTATION_WITH_XML, existenceChecking, getJavaClassName(), getLocation()); } getDescriptor().setExistenceChecking(m_existenceChecking); } } } } /** * INTERNAL: */ protected void processFetchGroup(FetchGroupMetadata fetchGroup, Map<String, FetchGroupMetadata> fetchGroups) { if (fetchGroup.shouldOverride(fetchGroups.get(fetchGroup.getName()))) { fetchGroups.put(fetchGroup.getName(), fetchGroup); } } /** * INTERNAL: * Process the fetch groups for this class. We need to go through both * the XML list and those defined in annotations. Must look for multiple * same named fetch groups within XML and annotations and XML named fetch * groups must override a similar named fetch group defined within an * annotation. * * This method will be called from both Entity And MappedSuperclass. The * fetch groups from the entity are added first followed by those from its * mapped superclass(es). */ protected void processFetchGroups() { Map<String, FetchGroupMetadata> fetchGroups = new HashMap<String, FetchGroupMetadata>(); // Process the XML fetch groups first. for (FetchGroupMetadata fetchGroup : m_fetchGroups) { processFetchGroup(fetchGroup, fetchGroups); } // Process the fetch group annotations. // Look for a @FetchGroup. if (isAnnotationPresent(FetchGroups.class)) { for (Object fetchGroup : getAnnotation(FetchGroups.class).getAttributeArray("value")) { processFetchGroup(new FetchGroupMetadata((MetadataAnnotation) fetchGroup, this), fetchGroups); } } // Look for a @FetchGroup. if (isAnnotationPresent(FetchGroup.class)) { processFetchGroup(new FetchGroupMetadata(getAnnotation(FetchGroup.class), this), fetchGroups); } // Now process all the fetch groups we found to the descriptor only // if weaving is enabled or if the descriptors java class for this // accessor implements the FetchGroupTracker interface. if (getProject().isWeavingFetchGroupsEnabled() || getDescriptor().getJavaClass().extendsInterface(FetchGroupTracker.class)) { for (FetchGroupMetadata fetchGroup : fetchGroups.values()) { fetchGroup.process(this); } } else if (! fetchGroups.isEmpty()) { getLogger().logWarningMessage(MetadataLogger.IGNORE_FETCH_GROUP, getJavaClass(), getDescriptor().getJavaClass()); } } /** * INTERNAL: * Process an IdClass metadata. It is used to specify composite primary * keys. The primary keys will be processed and stored from the PK class so * that they may be validated against the fields or properties of the entity * bean. The access type of a primary key class is determined by the access * type of the entity for which it is the primary key. */ protected void processIdClass() { if (m_idClass != null && !m_idClass.equals(void.class)) { getDescriptor().setPKClass(m_idClass); if (getDescriptor().usesDefaultPropertyAccess()) { for (MetadataMethod method : m_idClass.getMethods().values()) { // The is valid check will throw an exception if needed. if (!method.isAnnotationPresent(JPA_TRANSIENT) && method.isValidPersistenceMethod(false, this)) { getDescriptor().addPKClassId(method.getAttributeName(), getBoxedType(method.getType())); } } } else { for (MetadataField field : m_idClass.getFields().values()) { // The is valid check will throw an exception if needed. if (!field.isAnnotationPresent(JPA_TRANSIENT) && field.isValidPersistenceField(false, this)) { getDescriptor().addPKClassId(field.getName(), getBoxedType(field.getType())); } } } } } /** * INTERNAL: * Used to process mapped superclasses when creating descriptors for a * metamodel. The MappedSuperclass Descriptors here are separate from * non-MappedSuperclass Descriptors. * @since EclipseLink 1.2 for the JPA 2.0 Reference Implementation */ public void processMetamodelDescriptor() { for (MappedSuperclassAccessor mappedSuperclass : getProject().getMetamodelMappedSuperclasses()) { mappedSuperclass.processMappingAccessors(); } } /** * INTERNAL: * Process the multitenant metadata specified on a mapped superclass and * apply it to a sub-entity that has no multitenant metadata specified. */ protected void processMultitenant() { if (m_multitenant != null || isAnnotationPresent(Multitenant.class)) { // We have multitenant metadata available. If the descriptor already // has multi-tenant settings ignore the multi-tenant metadata. if (getDescriptor().hasMultitenant()) { // Ignore multitenant on mapped superclass if multitenant is // already defined on the entity. getLogger().logConfigMessage(MetadataLogger.IGNORE_MAPPED_SUPERCLASS_MULTITENANT, getDescriptor().getJavaClass(), getJavaClass()); } else if (m_multitenant != null) { // We have multitenant metadata loaded from XML. Log a warning // if equivalent annotation metadata is specified. if (isAnnotationPresent(Multitenant.class)) { getLogger().logConfigMessage(MetadataLogger.OVERRIDE_ANNOTATION_WITH_XML, getAnnotation(Multitenant.class), getJavaClassName(), getLocation()); } // Process the multitenant metadata that was specified in XML. m_multitenant.process(getDescriptor()); } else { // Process the multitenant from the annotation. new MultitenantMetadata(getAnnotation(Multitenant.class), this).process(getDescriptor()); } } } /** * INTERNAL: * Process/collect the named native queries on this accessor and add them * to the project for later processing. */ protected void processNamedNativeQueries() { // Process the XML named native queries first. for (NamedNativeQueryMetadata namedNativeQuery : m_namedNativeQueries) { getProject().addQuery(namedNativeQuery); } // Process the named native query annotations. // Look for a @NamedNativeQueries. MetadataAnnotation namedNativeQueries = getAnnotation(JPA_NAMED_NATIVE_QUERIES); if (namedNativeQueries != null) { for (Object namedNativeQuery : namedNativeQueries.getAttributeArray("value")) { getProject().addQuery(new NamedNativeQueryMetadata((MetadataAnnotation) namedNativeQuery, this)); } } // Look for a @NamedNativeQuery. MetadataAnnotation namedNativeQuery = getAnnotation(JPA_NAMED_NATIVE_QUERY); if (namedNativeQuery != null) { getProject().addQuery(new NamedNativeQueryMetadata(namedNativeQuery, this)); } } /** * INTERNAL: * Process/collect the named PLSQL stored function queries on this accessor * and add them to the project for later processing. */ protected void processNamedPLSQLStoredFunctionQueries() { // Process the XML named PLSQL stored function queries first. for (NamedPLSQLStoredFunctionQueryMetadata namedPLSQLStoredFunctionQuery : m_namedPLSQLStoredFunctionQueries) { getProject().addQuery(namedPLSQLStoredFunctionQuery); } // Process the named PLSQL stored function query annotations. // Look for a @NamedPLSQLStoredFunctionQueries. MetadataAnnotation namedPLSQLStoredFunctionQueries = getAnnotation(NamedPLSQLStoredFunctionQueries.class); if (namedPLSQLStoredFunctionQueries != null) { for (Object namedPLSQLStoredFunctionQuery : namedPLSQLStoredFunctionQueries.getAttributeArray("value")) { getProject().addQuery(new NamedPLSQLStoredFunctionQueryMetadata((MetadataAnnotation) namedPLSQLStoredFunctionQuery, this)); } } // Look for a @NamedPLSQLStoredFunctionQuery. MetadataAnnotation namedPLSQLStoredFunctionQuery = getAnnotation(NamedPLSQLStoredFunctionQuery.class); if (namedPLSQLStoredFunctionQuery != null) { getProject().addQuery(new NamedPLSQLStoredFunctionQueryMetadata(namedPLSQLStoredFunctionQuery, this)); } } /** * INTERNAL: * Process/collect the named PLSQL stored procedure queries on this accessor * and add them to the project for later processing. */ protected void processNamedPLSQLStoredProcedureQueries() { // Process the XML named PLSQL stored procedure queries queries first. for (NamedPLSQLStoredProcedureQueryMetadata namedPLSQLStoredProcedureQuery : m_namedPLSQLStoredProcedureQueries) { getProject().addQuery(namedPLSQLStoredProcedureQuery); } // Process the named PLSQL stored procedure query annotations. // Look for a @NamedPLSQLStoredProcedureQueries. MetadataAnnotation namedPLSQLStoredProcedureQueries = getAnnotation(NamedPLSQLStoredProcedureQueries.class); if (namedPLSQLStoredProcedureQueries != null) { for (Object namedPLSQLStoredProcedureQuery : namedPLSQLStoredProcedureQueries.getAttributeArray("value")) { getProject().addQuery(new NamedPLSQLStoredProcedureQueryMetadata((MetadataAnnotation) namedPLSQLStoredProcedureQuery, this)); } } // Look for a @NamedPLSQLStoredProcedureQuery. MetadataAnnotation namedPLSQLStoredProcedureQuery = getAnnotation(NamedPLSQLStoredProcedureQuery.class); if (namedPLSQLStoredProcedureQuery != null) { getProject().addQuery(new NamedPLSQLStoredProcedureQueryMetadata(namedPLSQLStoredProcedureQuery, this)); } } /** * INTERNAL: * Process/collect the named queries on this accessor and add them to the * project for later processing. */ protected void processNamedQueries() { // Process the XML named queries first. for (NamedQueryMetadata namedQuery : m_namedQueries) { getProject().addQuery(namedQuery); } // Process the named query annotations. // Look for a @NamedQueries. if (isAnnotationPresent(JPA_NAMED_QUERIES)) { for (Object namedQuery : (Object[]) getAnnotation(JPA_NAMED_QUERIES).getAttributeArray("value")) { getProject().addQuery(new NamedQueryMetadata((MetadataAnnotation) namedQuery, this)); } } // Look for a @NamedQuery. if (isAnnotationPresent(JPA_NAMED_QUERY)) { getProject().addQuery(new NamedQueryMetadata(getAnnotation(JPA_NAMED_QUERY), this)); } } /** * INTERNAL: * Process/collect the named stored procedure queries on this accessor and * add them to the project for later processing. */ protected void processNamedStoredFunctionQueries() { // Process the XML named stored function queries first. for (NamedStoredFunctionQueryMetadata namedStoredFunctionQuery : m_namedStoredFunctionQueries) { getProject().addQuery(namedStoredFunctionQuery); } // Process the named stored function query annotations. // Look for a @NamedStoredFunctionQueries. MetadataAnnotation namedStoredFunctionQueries = getAnnotation(NamedStoredFunctionQueries.class); if (namedStoredFunctionQueries != null) { for (Object namedStoredFunctionQuery : namedStoredFunctionQueries.getAttributeArray("value")) { getProject().addQuery(new NamedStoredFunctionQueryMetadata((MetadataAnnotation) namedStoredFunctionQuery, this)); } } // Look for a @NamedStoredFunctionQuery. MetadataAnnotation namedStoredFunctionQuery = getAnnotation(NamedStoredFunctionQuery.class); if (namedStoredFunctionQuery != null) { getProject().addQuery(new NamedStoredFunctionQueryMetadata(namedStoredFunctionQuery, this)); } } /** * INTERNAL: * Process/collect the named stored function queries on this accessor and * add them to the project for later processing. */ protected void processNamedStoredProcedureQueries() { // Process the XML named stored procedure queries first. for (NamedStoredProcedureQueryMetadata namedStoredProcedureQuery : m_namedStoredProcedureQueries) { getProject().addQuery(namedStoredProcedureQuery); } // Process the JPA named stored procedure query annotations. // Look for a JPA @NamedStoredProcedureQueries. MetadataAnnotation jpaNamedStoredProcedureQueries = getAnnotation(JPA_NAMED_STORED_PROCEDURE_QUERIES); if (jpaNamedStoredProcedureQueries != null) { for (Object jpaNamedStoredProcedureQuery :jpaNamedStoredProcedureQueries.getAttributeArray("value")) { getProject().addQuery(new NamedStoredProcedureQueryMetadata((MetadataAnnotation) jpaNamedStoredProcedureQuery, this)); } } // Look for a JPA @NamedStoredProcedureQuery. MetadataAnnotation jpaNamedStoredProcedureQuery = getAnnotation(JPA_NAMED_STORED_PROCEDURE_QUERY); if (jpaNamedStoredProcedureQuery != null) { getProject().addQuery(new NamedStoredProcedureQueryMetadata(jpaNamedStoredProcedureQuery, this)); } // Process the named stored procedure query annotations. // Look for a @NamedStoredProcedureQueries. MetadataAnnotation namedStoredProcedureQueries = getAnnotation(org.eclipse.persistence.annotations.NamedStoredProcedureQueries.class); if (namedStoredProcedureQueries != null) { for (Object namedStoredProcedureQuery : namedStoredProcedureQueries.getAttributeArray("value")) { getProject().addQuery(new NamedStoredProcedureQueryMetadata((MetadataAnnotation) namedStoredProcedureQuery, this)); } } // Look for a @NamedStoredProcedureQuery. MetadataAnnotation namedStoredProcedureQuery = getAnnotation(org.eclipse.persistence.annotations.NamedStoredProcedureQuery.class); if (namedStoredProcedureQuery != null) { getProject().addQuery(new NamedStoredProcedureQueryMetadata(namedStoredProcedureQuery, this)); } } /** * INTERNAL: * Process an OptimisticLockingMetadata. */ protected void processOptimisticLocking() { if (getDescriptor().usesOptimisticLocking()) { if (m_optimisticLocking != null || isAnnotationPresent(OptimisticLocking.class)) { // We must be processing a mapped superclass to an entity that // defined its own optimistic locking meta data. Ignore it and // log a warning. getLogger().logConfigMessage(MetadataLogger.IGNORE_MAPPED_SUPERCLASS_OPTIMISTIC_LOCKING, getDescriptor().getJavaClass(), getJavaClass()); } } else { MetadataAnnotation optimisticLocking = getAnnotation(OptimisticLocking.class); if (m_optimisticLocking == null) { if (optimisticLocking != null) { // Process the meta data for this accessor's descriptor. new OptimisticLockingMetadata(optimisticLocking, this).process(getDescriptor()); } } else { // If there is an annotation log a warning that we are // ignoring it. if (optimisticLocking != null) { getLogger().logConfigMessage(MetadataLogger.OVERRIDE_ANNOTATION_WITH_XML, optimisticLocking, getJavaClassName(), getLocation()); } // Process the meta data for this accessor's descriptor. m_optimisticLocking.process(getDescriptor()); } } } /** * INTERNAL: * Process a read only setting. */ protected void processReadOnly() { MetadataAnnotation readOnly = getAnnotation(ReadOnly.class); if (m_readOnly != null || readOnly != null) { if (getDescriptor().isInheritanceSubclass()) { // Ignore read only if specified on an inheritance subclass. getLogger().logWarningMessage(MetadataLogger.IGNORE_INHERITANCE_SUBCLASS_READ_ONLY, getJavaClass()); } else if (getDescriptor().hasReadOnly()) { // Ignore read only on mapped superclass if read only is already // defined on the entity. getLogger().logConfigMessage(MetadataLogger.IGNORE_MAPPED_SUPERCLASS_READ_ONLY, getDescriptor().getJavaClass(), getJavaClass()); } else { if (m_readOnly == null) { getDescriptor().setReadOnly(true); } else { if (readOnly != null) { getLogger().logConfigMessage(MetadataLogger.OVERRIDE_ANNOTATION_WITH_XML, readOnly, getJavaClassName(), getLocation()); } getDescriptor().setReadOnly(m_readOnly); } } } } /** * INTERNAL: * Process the primary key annotation. */ protected void processPrimaryKey() { if (m_primaryKey != null || isAnnotationPresent(PrimaryKey.class)) { if (getDescriptor().hasPrimaryKey()) { // Ignore primary key on mapped superclass if primary key // metadata is already defined on the entity. getLogger().logConfigMessage(MetadataLogger.IGNORE_MAPPED_SUPERCLASS_PRIMARY_KEY, getDescriptor().getJavaClass(), getJavaClass()); } else { if (m_primaryKey == null) { new PrimaryKeyMetadata(getAnnotation(PrimaryKey.class), this).process(getDescriptor()); } else { if (isAnnotationPresent(PrimaryKey.class)) { getLogger().logConfigMessage(MetadataLogger.OVERRIDE_ANNOTATION_WITH_XML, getAnnotation(PrimaryKey.class), getJavaClassName(), getLocation()); } m_primaryKey.process(getDescriptor()); } } } } /** * INTERNAL: * Process a SequenceGenerator annotation into a common metadata sequence * generator and add it to the project. */ protected void processSequenceGenerator() { // Process the xml defined sequence generator first. if (m_sequenceGenerator != null) { getProject().addSequenceGenerator(m_sequenceGenerator, getDescriptor().getDefaultCatalog(), getDescriptor().getDefaultSchema()); } if (isAnnotationPresent(JPA_SEQUENCE_GENERATOR)) { // Ask the common processor to process what we found. getProject().addSequenceGenerator(new SequenceGeneratorMetadata(getAnnotation(JPA_SEQUENCE_GENERATOR), this), getDescriptor().getDefaultCatalog(), getDescriptor().getDefaultSchema()); } } /** * INTERNAL: * Process a SerializedObjectPolicyMetadata. */ protected void processSerializedObjectPolicy() { if (m_serializedObjectPolicy == null) { if (isAnnotationPresent(SerializedObject.class)) { new SerializedObjectPolicyMetadata(getAnnotation(SerializedObject.class), this).process(getDescriptor()); } } else { if (isAnnotationPresent(SerializedObject.class)) { getLogger().logConfigMessage(MetadataLogger.OVERRIDE_ANNOTATION_WITH_XML, getAnnotation(SerializedObject.class), getJavaClassName(), getLocation()); } m_serializedObjectPolicy.process(getDescriptor()); } } /** * INTERNAL: * Process the sql result set mappings for the given class which could be * an entity or a mapped superclass. */ protected void processSqlResultSetMappings() { // Process the XML sql result set mapping elements first. for (SQLResultSetMappingMetadata sqlResultSetMapping : m_sqlResultSetMappings) { getProject().addSQLResultSetMapping(sqlResultSetMapping); } // Process the sql result set mapping query annotations. // Look for a @SqlResultSetMappings. MetadataAnnotation sqlResultSetMappings = getAnnotation(JPA_SQL_RESULT_SET_MAPPINGS); if (sqlResultSetMappings != null) { for (Object sqlResultSetMapping : sqlResultSetMappings.getAttributeArray("value")) { getProject().addSQLResultSetMapping(new SQLResultSetMappingMetadata((MetadataAnnotation) sqlResultSetMapping, this)); } } else { // Look for a @SqlResultSetMapping. MetadataAnnotation sqlResultSetMapping = getAnnotation(JPA_SQL_RESULT_SET_MAPPING); if (sqlResultSetMapping != null) { getProject().addSQLResultSetMapping(new SQLResultSetMappingMetadata(sqlResultSetMapping, this)); } } } /** * INTERNAL: * Process a TableGenerator annotation into a common metadata table * generator and add it to the project. */ protected void processTableGenerator() { // Process the xml defined table generator first. if (m_tableGenerator != null) { getProject().addTableGenerator(m_tableGenerator, getDescriptor().getDefaultCatalog(), getDescriptor().getDefaultSchema()); } if (isAnnotationPresent(JPA_TABLE_GENERATOR)) { getProject().addTableGenerator(new TableGeneratorMetadata(getAnnotation(JPA_TABLE_GENERATOR), this), getDescriptor().getDefaultCatalog(), getDescriptor().getDefaultSchema()); } } /** * INTERNAL: * Process a TableGenerator annotation into a common metadata table * generator and add it to the project. */ protected void processUuidGenerator() { // Process the xml defined table generator first. if (m_uuidGenerator != null) { getProject().addUuidGenerator(m_uuidGenerator); } if (isAnnotationPresent(UuidGenerator.class)) { getProject().addUuidGenerator(new UuidGeneratorMetadata(getAnnotation(UuidGenerator.class), this)); } } /** * INTERNAL: * Used for OX mapping. */ public void setAdditionalCriteria(AdditionalCriteriaMetadata additionalCriteria) { m_additionalCriteria = additionalCriteria; } /** * INTERNAL: * Used for OX mapping. */ public void setCache(CacheMetadata cache) { m_cache = cache; } /** * INTERNAL: * Used for OX mapping. */ public void setCacheIndexes(List<CacheIndexMetadata> indexes) { m_cacheIndexes = indexes; } /** * INTERNAL: * Used for OX mapping. */ public void setCacheable(Boolean cacheable) { m_cacheable = cacheable; } /** * INTERNAL: * Used for OX mapping. */ public void setCacheInterceptor(CacheInterceptorMetadata cacheInterceptor) { m_cacheInterceptor = cacheInterceptor; } /** * INTERNAL: * Used for OX mapping. */ public void setEntityListeners(List<EntityListenerMetadata> entityListeners) { m_entityListeners = entityListeners; } /** * INTERNAL: * Used for OX mapping. */ public void setExcludeDefaultListeners(Boolean excludeDefaultListeners) { m_excludeDefaultListeners = excludeDefaultListeners; } /** * INTERNAL: * Used for OX mapping */ public void setExcludeSuperclassListeners(Boolean excludeSuperclassListeners) { m_excludeSuperclassListeners = excludeSuperclassListeners; } /** * INTERNAL: * Used for OX mapping. */ public void setExistenceChecking(String checking) { m_existenceChecking = checking; } /** * INTERNAL: * Used for OX mapping. */ public void setFetchGroups(List<FetchGroupMetadata> fetchGroups) { m_fetchGroups = fetchGroups; } /** * INTERNAL: */ protected void setIdClass(MetadataClass idClass) { m_idClass = idClass; } /** * INTERNAL: * Used for OX mapping. */ public void setIdClassName(String idClassName) { m_idClassName = idClassName; } /** * INTERNAL: * Used for OX mapping. */ public void setMultitenant(MultitenantMetadata multitenant) { m_multitenant = multitenant; } /** * INTERNAL: * Used for OX mapping. */ public void setNamedNativeQueries(List<NamedNativeQueryMetadata> namedNativeQueries) { m_namedNativeQueries = namedNativeQueries; } /** * INTERNAL: * Used for OX mapping. */ public void setNamedPLSQLStoredFunctionQueries(List<NamedPLSQLStoredFunctionQueryMetadata> namedPLSQLStoredFunctionQueries) { m_namedPLSQLStoredFunctionQueries = namedPLSQLStoredFunctionQueries; } /** * INTERNAL: * Used for OX mapping. */ public void setNamedPLSQLStoredProcedureQueries(List<NamedPLSQLStoredProcedureQueryMetadata> namedPLSQLStoredProcedureQueries) { m_namedPLSQLStoredProcedureQueries = namedPLSQLStoredProcedureQueries; } /** * INTERNAL: * Used for OX mapping. */ public void setNamedQueries(List<NamedQueryMetadata> namedQueries) { m_namedQueries = namedQueries; } /** * INTERNAL: * Used for OX mapping. */ public void setNamedStoredFunctionQueries(List<NamedStoredFunctionQueryMetadata> namedStoredFunctionQueries) { m_namedStoredFunctionQueries = namedStoredFunctionQueries; } /** * INTERNAL: * Used for OX mapping. */ public void setNamedStoredProcedureQueries(List<NamedStoredProcedureQueryMetadata> namedStoredProcedureQueries) { m_namedStoredProcedureQueries = namedStoredProcedureQueries; } /** * INTERNAL: * Used for OX mapping. */ public void setOptimisticLocking(OptimisticLockingMetadata optimisticLocking) { m_optimisticLocking = optimisticLocking; } /** * INTERNAL: * Used for OX mapping. */ public void setPostLoad(String postLoad) { m_postLoad = postLoad; } /** * INTERNAL: */ public void setPostPersist(String postPersist) { m_postPersist = postPersist; } /** * INTERNAL: */ public void setPostRemove(String postRemove) { m_postRemove = postRemove; } /** * INTERNAL: */ public void setPostUpdate(String postUpdate) { m_postUpdate = postUpdate; } /** * INTERNAL: */ public void setPrePersist(String prePersist) { m_prePersist = prePersist; } /** * INTERNAL: */ public void setPreRemove(String preRemove) { m_preRemove = preRemove; } /** * INTERNAL: */ public void setPreUpdate(String preUpdate) { m_preUpdate = preUpdate; } /** * INTERNAL: * Used for OX mapping. */ public void setPrimaryKey(PrimaryKeyMetadata primaryKey) { m_primaryKey = primaryKey; } /** * INTERNAL: * Used for OX mapping. */ public void setQueryRedirectors(QueryRedirectorsMetadata redirectors) { m_queryRedirectors = redirectors; } /** * INTERNAL: * Used for OX mapping. */ public void setReadOnly(Boolean readOnly) { m_readOnly = readOnly; } /** * INTERNAL: * Used for OX mapping. */ public void setSequenceGenerator(SequenceGeneratorMetadata sequenceGenerator) { m_sequenceGenerator = sequenceGenerator; } /** * INTERNAL: * Used for OX mapping. */ public void setSerializedObjectPolicy(SerializedObjectPolicyMetadata serializedObjectPolicy) { m_serializedObjectPolicy = serializedObjectPolicy; } /** * INTERNAL: * Used for OX mapping. */ public void setSqlResultSetMappings(List<SQLResultSetMappingMetadata> sqlResultSetMappings) { m_sqlResultSetMappings = sqlResultSetMappings; } /** * INTERNAL: * Used for OX mapping. */ public void setTableGenerator(TableGeneratorMetadata tableGenerator) { m_tableGenerator = tableGenerator; } /** * INTERNAL: * Used for OX mapping. */ public void setUuidGenerator(UuidGeneratorMetadata uuidGenerator) { m_uuidGenerator = uuidGenerator; } }