| /******************************************************************************* |
| * 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.olingo.odata2.jpa.processor.core.model; |
| |
| import java.util.ArrayList; |
| import java.util.HashMap; |
| import java.util.LinkedHashMap; |
| import java.util.List; |
| |
| import org.apache.olingo.odata2.api.edm.provider.Association; |
| import org.apache.olingo.odata2.api.edm.provider.ComplexType; |
| import org.apache.olingo.odata2.api.edm.provider.EntityType; |
| import org.apache.olingo.odata2.api.edm.provider.NavigationProperty; |
| import org.apache.olingo.odata2.api.edm.provider.Schema; |
| import org.apache.olingo.odata2.jpa.processor.api.access.JPAEdmBuilder; |
| import org.apache.olingo.odata2.jpa.processor.api.exception.ODataJPAModelException; |
| import org.apache.olingo.odata2.jpa.processor.api.exception.ODataJPARuntimeException; |
| import org.apache.olingo.odata2.jpa.processor.api.model.JPAEdmAssociationView; |
| import org.apache.olingo.odata2.jpa.processor.api.model.JPAEdmComplexTypeView; |
| import org.apache.olingo.odata2.jpa.processor.api.model.JPAEdmEntityContainerView; |
| import org.apache.olingo.odata2.jpa.processor.api.model.JPAEdmEntitySetView; |
| import org.apache.olingo.odata2.jpa.processor.api.model.JPAEdmEntityTypeView; |
| import org.apache.olingo.odata2.jpa.processor.api.model.JPAEdmExtension; |
| import org.apache.olingo.odata2.jpa.processor.api.model.JPAEdmFunctionImportView; |
| import org.apache.olingo.odata2.jpa.processor.api.model.JPAEdmModelView; |
| import org.apache.olingo.odata2.jpa.processor.api.model.JPAEdmSchemaView; |
| import org.apache.olingo.odata2.jpa.processor.core.access.model.JPAEdmNameBuilder; |
| |
| public class JPAEdmSchema extends JPAEdmBaseViewImpl implements JPAEdmSchemaView { |
| |
| private Schema schema; |
| private JPAEdmComplexTypeView complexTypeView; |
| private JPAEdmEntityContainerView entityContainerView; |
| private JPAEdmAssociationView associationView = null; |
| private LinkedHashMap<Class<?>, String[]> customOperations = null; |
| |
| public JPAEdmSchema(final JPAEdmModelView modelView) { |
| super(modelView); |
| } |
| |
| @Override |
| public Schema getEdmSchema() { |
| return schema; |
| } |
| |
| @Override |
| public JPAEdmEntityContainerView getJPAEdmEntityContainerView() { |
| return entityContainerView; |
| } |
| |
| @Override |
| public JPAEdmComplexTypeView getJPAEdmComplexTypeView() { |
| return complexTypeView; |
| } |
| |
| @Override |
| public JPAEdmBuilder getBuilder() { |
| if (builder == null) { |
| builder = new JPAEdmSchemaBuilder(); |
| } |
| |
| return builder; |
| } |
| |
| @Override |
| public void clean() { |
| super.clean(); |
| schema = null; |
| } |
| |
| private class JPAEdmSchemaBuilder implements JPAEdmBuilder { |
| /* |
| * |
| * Each call to build method creates a new EDM Schema. The newly created |
| * schema is built with Entity Containers, associations, Complex Types |
| * and Entity Types. |
| * |
| * ************************************************************ Build |
| * EDM Schema - STEPS |
| * ************************************************************ 1) Build |
| * Name for EDM Schema 2) Build EDM Complex Types from JPA Embeddable |
| * Types 3) Add EDM Complex Types to EDM Schema 4) Build EDM Entity |
| * Container 5) Add EDM Entity Container to EDM Schema 6) Fetch Built |
| * EDM Entity Types from EDM Entity Container 7) Add EDM Entity Types to |
| * EDM Schema 8) Fetch Built EDM Association Sets from EDM Entity |
| * Container 9) Fetch Built EDM Associations from EDM Association Set |
| * 10) Add EDM Association to EDM Schema |
| * ************************************************************ Build |
| * EDM Schema - STEPS |
| * ************************************************************ |
| */ |
| @Override |
| public void build() throws ODataJPAModelException, ODataJPARuntimeException { |
| |
| schema = new Schema(); |
| JPAEdmNameBuilder.build(JPAEdmSchema.this); |
| |
| associationView = new JPAEdmAssociation(JPAEdmSchema.this); |
| |
| complexTypeView = new JPAEdmComplexType(JPAEdmSchema.this); |
| complexTypeView.getBuilder().build(); |
| |
| entityContainerView = new JPAEdmEntityContainer(JPAEdmSchema.this); |
| entityContainerView.getBuilder().build(); |
| schema.setEntityContainers(entityContainerView.getConsistentEdmEntityContainerList()); |
| |
| JPAEdmEntitySetView entitySetView = entityContainerView.getJPAEdmEntitySetView(); |
| if (entitySetView.isConsistent() && entitySetView.getJPAEdmEntityTypeView() != null) { |
| JPAEdmEntityTypeView entityTypeView = entitySetView.getJPAEdmEntityTypeView(); |
| if (entityTypeView.isConsistent() && !entityTypeView.getConsistentEdmEntityTypes().isEmpty()) { |
| schema.setEntityTypes(entityTypeView.getConsistentEdmEntityTypes()); |
| } |
| } |
| if (complexTypeView.isConsistent()) { |
| List<ComplexType> complexTypes = complexTypeView.getConsistentEdmComplexTypes(); |
| List<ComplexType> existingComplexTypes = new ArrayList<ComplexType>(); |
| for (ComplexType complexType : complexTypes) { |
| if (complexType != null && complexTypeView.isReferencedInKey(complexType.getName())) {// null check for |
| // exclude |
| existingComplexTypes.add(complexType); |
| } |
| } |
| if (!existingComplexTypes.isEmpty()) { |
| schema.setComplexTypes(existingComplexTypes); |
| } |
| } |
| |
| List<String> existingAssociationList = new ArrayList<String>(); |
| if (associationView.isConsistent() && !associationView.getConsistentEdmAssociationList().isEmpty()) { |
| |
| List<Association> consistentAssociationList = associationView.getConsistentEdmAssociationList(); |
| schema.setAssociations(consistentAssociationList); |
| for (Association association : consistentAssociationList) { |
| existingAssociationList.add(association.getName()); |
| } |
| |
| } |
| List<EntityType> entityTypes = |
| entityContainerView.getJPAEdmEntitySetView().getJPAEdmEntityTypeView().getConsistentEdmEntityTypes(); |
| List<NavigationProperty> navigationProperties; |
| if (entityTypes != null && !entityTypes.isEmpty()) { |
| for (EntityType entityType : entityTypes) { |
| |
| List<NavigationProperty> consistentNavigationProperties = null; |
| navigationProperties = entityType.getNavigationProperties(); |
| if (navigationProperties != null) { |
| consistentNavigationProperties = new ArrayList<NavigationProperty>(); |
| for (NavigationProperty navigationProperty : navigationProperties) { |
| if (existingAssociationList.contains(navigationProperty.getRelationship().getName())) { |
| consistentNavigationProperties.add(navigationProperty); |
| } |
| } |
| if (consistentNavigationProperties.isEmpty()) { |
| entityType.setNavigationProperties(null); |
| } else { |
| entityType.setNavigationProperties(consistentNavigationProperties); |
| } |
| } |
| |
| } |
| } |
| |
| JPAEdmExtension edmExtension = getJPAEdmExtension(); |
| if (edmExtension != null) { |
| edmExtension.extendJPAEdmSchema(JPAEdmSchema.this); |
| edmExtension.extendWithOperation(JPAEdmSchema.this); |
| |
| JPAEdmFunctionImportView functionImportView = new JPAEdmFunctionImport(JPAEdmSchema.this); |
| functionImportView.getBuilder().build(); |
| if (functionImportView.getConsistentFunctionImportList() != null) { |
| entityContainerView.getEdmEntityContainer().setFunctionImports( |
| functionImportView.getConsistentFunctionImportList()); |
| } |
| |
| } |
| } |
| |
| } |
| |
| @Override |
| public final JPAEdmAssociationView getJPAEdmAssociationView() { |
| return associationView; |
| } |
| |
| @Override |
| public void registerOperations(final Class<?> customClass, final String[] methodNames) { |
| if (customOperations == null) { |
| customOperations = new LinkedHashMap<Class<?>, String[]>(); |
| } |
| |
| customOperations.put(customClass, methodNames); |
| |
| } |
| |
| @Override |
| public HashMap<Class<?>, String[]> getRegisteredOperations() { |
| return customOperations; |
| } |
| } |