/// <summary> /// Converts a navigation property from SOM to metadata /// </summary> /// <param name="declaringEntityType"> entity type on which this navigation property was declared </param> /// <param name="somNavigationProperty"> The SOM element to process </param> /// <param name="providerManifest"> The provider manifest to be used for conversion </param> /// <param name="convertedItemCache"> The item collection for currently existing metadata objects </param> /// <param name="newGlobalItems"> The new GlobalItem objects that are created as a result of this conversion </param> /// <returns> The property object resulting from the convert </returns> private static NavigationProperty ConvertToNavigationProperty( EntityType declaringEntityType, SchemaObjectModel.NavigationProperty somNavigationProperty, DbProviderManifest providerManifest, ConversionCache convertedItemCache, Dictionary<SchemaElement, GlobalItem> newGlobalItems) { // Navigation properties cannot be primitive types, so we can ignore the possibility of having primitive type // facets var toEndEntityType = (EntityType)LoadSchemaElement( somNavigationProperty.Type, providerManifest, convertedItemCache, newGlobalItems); EdmType edmType = toEndEntityType; // Also load the relationship Type that this navigation property represents var relationshipType = (AssociationType)LoadSchemaElement( (Relationship)somNavigationProperty.Relationship, providerManifest, convertedItemCache, newGlobalItems); IRelationshipEnd somRelationshipEnd = null; somNavigationProperty.Relationship.TryGetEnd(somNavigationProperty.ToEnd.Name, out somRelationshipEnd); if (somRelationshipEnd.Multiplicity == RelationshipMultiplicity.Many) { edmType = toEndEntityType.GetCollectionType(); } else { Debug.Assert(somRelationshipEnd.Multiplicity != RelationshipMultiplicity.Many); edmType = toEndEntityType; } TypeUsage typeUsage; if (somRelationshipEnd.Multiplicity == RelationshipMultiplicity.One) { typeUsage = TypeUsage.Create( edmType, new FacetValues { Nullable = false }); } else { typeUsage = TypeUsage.Create(edmType); } // We need to make sure that both the ends of the relationtype are initialized. If there are not, then we should // initialize them here InitializeAssociationEndMember(relationshipType, somNavigationProperty.ToEnd, toEndEntityType); InitializeAssociationEndMember(relationshipType, somNavigationProperty.FromEnd, declaringEntityType); // The type of the navigation property must be a ref or collection depending on which end they belong to var navigationProperty = new NavigationProperty(somNavigationProperty.Name, typeUsage); navigationProperty.RelationshipType = relationshipType; navigationProperty.ToEndMember = (RelationshipEndMember)relationshipType.Members[somNavigationProperty.ToEnd.Name]; navigationProperty.FromEndMember = (RelationshipEndMember)relationshipType.Members[somNavigationProperty.FromEnd.Name]; // Extract the optional Documentation if (somNavigationProperty.Documentation != null) { navigationProperty.Documentation = ConvertToDocumentation(somNavigationProperty.Documentation); } AddOtherContent(somNavigationProperty, navigationProperty); return navigationProperty; }
/// <summary> /// Converts an entity container from SOM to metadata /// </summary> /// <param name="element"> The SOM element to process </param> /// <param name="providerManifest"> The provider manifest to be used for conversion </param> /// <param name="convertedItemCache"> The item collection for currently existing metadata objects </param> /// <param name="newGlobalItems"> The new GlobalItem objects that are created as a result of this conversion </param> /// <returns> The entity container object resulting from the convert </returns> private static EntityContainer ConvertToEntityContainer( SchemaObjectModel.EntityContainer element, DbProviderManifest providerManifest, ConversionCache convertedItemCache, Dictionary<SchemaElement, GlobalItem> newGlobalItems) { // Creating a new entity container object and populate with converted entity set objects var entityContainer = new EntityContainer(element.Name, GetDataSpace(providerManifest)); newGlobalItems.Add(element, entityContainer); foreach (var entitySet in element.EntitySets) { entityContainer.AddEntitySetBase( ConvertToEntitySet( entitySet, providerManifest, convertedItemCache, newGlobalItems)); } // Populate with converted relationship set objects foreach (var relationshipSet in element.RelationshipSets) { Debug.Assert( relationshipSet.Relationship.RelationshipKind == RelationshipKind.Association, "We do not support containment set"); entityContainer.AddEntitySetBase( ConvertToAssociationSet( relationshipSet, providerManifest, convertedItemCache, entityContainer, newGlobalItems)); } // Populate with converted function imports foreach (var functionImport in element.FunctionImports) { entityContainer.AddFunctionImport( ConvertToFunction( functionImport, providerManifest, convertedItemCache, entityContainer, newGlobalItems)); } // Extract the optional Documentation if (element.Documentation != null) { entityContainer.Documentation = ConvertToDocumentation(element.Documentation); } AddOtherContent(element, entityContainer); return entityContainer; }