Exemplo n.º 1
0
 private static void AddOtherContent(Som.SchemaElement element, MetadataItem item)
 {
     if (element.OtherContent.Count > 0)
     {
         item.AddMetadataProperties(element.OtherContent);
     }
 }
Exemplo n.º 2
0
        /// <summary>
        /// Converts an entity set from SOM to metadata
        /// </summary>
        /// <param name="set">The SOM element to process</param>
        /// <param name="containerName">the name of the container this will be added to</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 set object resulting from the convert</returns>
        private static EntitySet ConvertToEntitySet(Som.EntityContainerEntitySet set,
                                                    string containerName,
                                                    DbProviderManifest providerManifest,
                                                    ConversionCache convertedItemCache,
                                                    Dictionary<Som.SchemaElement, GlobalItem> newGlobalItems)
        {
            EntitySet entitySet = new EntitySet(set.Name, set.DbSchema, set.Table, set.DefiningQuery,
                                                 (EntityType)LoadSchemaElement(set.EntityType,
                                                                               providerManifest,
                                                                               convertedItemCache,
                                                                               newGlobalItems));

            // Extract the optional Documentation
            if (set.Documentation != null)
            {
                entitySet.Documentation = ConvertToDocumentation(set.Documentation);
            }
            AddOtherContent(set, entitySet);

            return entitySet;
        }
Exemplo n.º 3
0
        /// <summary>
        /// Converts an association type 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 association type object resulting from the convert</returns>
        private static AssociationType ConvertToAssociationType(Som.Relationship element,
                                                                DbProviderManifest providerManifest,
                                                                ConversionCache convertedItemCache,
                                                                Dictionary<Som.SchemaElement, GlobalItem> newGlobalItems)
        {
            Debug.Assert(element.RelationshipKind == RelationshipKind.Association);

            AssociationType associationType = new AssociationType(element.Name,
                                                                  element.Namespace,
                                                                  element.IsForeignKey,
                                                                  GetDataSpace(providerManifest));
            newGlobalItems.Add(element, associationType);

            foreach (Som.RelationshipEnd end in element.Ends)
            {
                Som.SchemaType entityTypeElement = end.Type;
                EntityType endEntityType = (EntityType)LoadSchemaElement(entityTypeElement,
                                                                providerManifest,
                                                                convertedItemCache,
                                                                newGlobalItems);

                AssociationEndMember endMember = InitializeAssociationEndMember(associationType, end, endEntityType);
                AddOtherContent(end, endMember);
                // Loop through and convert the operations
                foreach (Som.OnOperation operation in end.Operations)
                {
                    // Process only the ones that we recognize
                    if (operation.Operation != Som.Operation.Delete)
                    {
                        continue;
                    }

                    // Determine the action for this operation
                    OperationAction action = OperationAction.None;
                    switch (operation.Action)
                    {
                        case Som.Action.Cascade:
                            action = OperationAction.Cascade;
                            break;
                        case Som.Action.None:
                            action = OperationAction.None;
                            break;
                        default:
                            Debug.Fail("Operation action not supported.");
                            break;
                    }
                    endMember.DeleteBehavior = action;
                }

                // Extract optional Documentation from the end element
                if (end.Documentation != null)
                {
                    endMember.Documentation = ConvertToDocumentation(end.Documentation);
                }
            }

            Debug.Assert(associationType.ReferentialConstraints.Count == 0, "This must never have been initialized");

            for (int i = 0; i < element.Constraints.Count; i++)
            {
                Som.ReferentialConstraint constraint = element.Constraints[i];
                AssociationEndMember fromMember = (AssociationEndMember)associationType.Members[constraint.PrincipalRole.Name];
                AssociationEndMember toMember = (AssociationEndMember)associationType.Members[constraint.DependentRole.Name];
                EntityTypeBase fromEntityType = ((RefType)fromMember.TypeUsage.EdmType).ElementType;
                EntityTypeBase toEntityType = ((RefType)toMember.TypeUsage.EdmType).ElementType;

                ReferentialConstraint referentialConstraint = new ReferentialConstraint(fromMember, toMember,
                                                                                        GetProperties(fromEntityType, constraint.PrincipalRole.RoleProperties),
                                                                                        GetProperties(toEntityType, constraint.DependentRole.RoleProperties));

                // Attach the optional Documentation
                if (constraint.Documentation != null)
                    referentialConstraint.Documentation = ConvertToDocumentation(constraint.Documentation);
                if (constraint.PrincipalRole.Documentation != null)
                    referentialConstraint.FromRole.Documentation = ConvertToDocumentation(constraint.PrincipalRole.Documentation);
                if (constraint.DependentRole.Documentation != null)
                    referentialConstraint.ToRole.Documentation = ConvertToDocumentation(constraint.DependentRole.Documentation);


                associationType.AddReferentialConstraint(referentialConstraint);
                AddOtherContent(element.Constraints[i], referentialConstraint);

            }

            // Extract the optional Documentation
            if (element.Documentation != null)
            {
                associationType.Documentation = ConvertToDocumentation(element.Documentation);
            }
            AddOtherContent(element, associationType);

            return associationType;
        }
Exemplo n.º 4
0
        /// <summary>
        /// Initialize the end member if its not initialized already
        /// </summary>
        /// <param name="associationType"></param>
        /// <param name="end"></param>
        /// <param name="endMemberType"></param>
        private static AssociationEndMember InitializeAssociationEndMember(AssociationType associationType, Som.IRelationshipEnd end,
            EntityType endMemberType)
        {
            AssociationEndMember associationEnd;

            EdmMember member;
            // make sure that the end is not initialized as of yet
            if (!associationType.Members.TryGetValue(end.Name, false/*ignoreCase*/, out member))
            {
                // Create the end member and add the operations
                associationEnd = new AssociationEndMember(end.Name,
                                                          endMemberType.GetReferenceType(),
                                                          end.Multiplicity.Value);
                associationType.AddKeyMember(associationEnd);
            }
            else
            {
                associationEnd = (AssociationEndMember)member;
            }

            //Extract the optional Documentation
            Som.RelationshipEnd relationshipEnd = end as Som.RelationshipEnd;

            if (relationshipEnd != null && (relationshipEnd.Documentation != null))
            {
                associationEnd.Documentation = ConvertToDocumentation(relationshipEnd.Documentation);
            }

            return associationEnd;
        }
Exemplo n.º 5
0
        /// <summary>
        /// Converts a function from SOM to metadata
        /// </summary>
        /// <param name="somFunction">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="functionImportEntityContainer">For function imports, the entity container including the function declaration</param>
        /// <param name="newGlobalItems">The new GlobalItem objects that are created as a result of this conversion</param>
        /// <returns>The function object resulting from the convert</returns>
        private static EdmFunction ConvertToFunction(Som.Function somFunction,
                                                  DbProviderManifest providerManifest,
                                                  ConversionCache convertedItemCache,
                                                  EntityContainer functionImportEntityContainer,
                                                  Dictionary<Som.SchemaElement, GlobalItem> newGlobalItems)
        {
            // If we already have it, don't bother converting
            GlobalItem globalItem = null;

            // if we are converted the function import, we need not check the global items collection,
            // since the function imports are local to the entity container
            if (!somFunction.IsFunctionImport && newGlobalItems.TryGetValue(somFunction, out globalItem))
            {
                return (EdmFunction)globalItem;
            }

            bool areConvertingForProviderManifest = somFunction.Schema.DataModel == Som.SchemaDataModelOption.ProviderManifestModel;
            List<FunctionParameter> returnParameters = new List<FunctionParameter>();
            if (somFunction.ReturnTypeList != null)
            {
                int i = 0;
                foreach (Som.ReturnType somReturnType in somFunction.ReturnTypeList)
                {
                    TypeUsage returnType = GetFunctionTypeUsage(somFunction is Som.ModelFunction,
                                                            somFunction,
                                                            somReturnType,
                                                            providerManifest,
                                                            areConvertingForProviderManifest,
                                                            somReturnType.Type,
                                                            somReturnType.CollectionKind,
                                                            somReturnType.IsRefType /*isRefType*/,
                                                            somFunction,
                                                            convertedItemCache,
                                                            newGlobalItems);
                    if (null != returnType)
                    {
                        // Create the return parameter object, need to set the declaring type explicitly on the return parameter
                        // because we aren't adding it to the members collection
                        string modifier = i == 0 ? string.Empty : i.ToString(System.Globalization.CultureInfo.InvariantCulture);
                        i++;
                        FunctionParameter returnParameter = new FunctionParameter(EdmConstants.ReturnType + modifier, returnType, ParameterMode.ReturnValue);
                        AddOtherContent(somReturnType, returnParameter);
                        returnParameters.Add(returnParameter);
                    }
                    else
                    {
                        return null;
                    }
                }
            }
            // this case must be second to avoid calling somFunction.Type when returnTypeList has more than one element.
            else if (somFunction.Type != null)
            {
                TypeUsage returnType = GetFunctionTypeUsage(somFunction is Som.ModelFunction,
                                                        somFunction,
                                                        null,
                                                        providerManifest,
                                                        areConvertingForProviderManifest,
                                                        somFunction.Type,
                                                        somFunction.CollectionKind,
                                                        somFunction.IsReturnAttributeReftype /*isRefType*/,
                                                        somFunction,
                                                        convertedItemCache,
                                                        newGlobalItems);
                if (null != returnType)
                {
                    // Create the return parameter object, need to set the declaring type explicitly on the return parameter
                    // because we aren't adding it to the members collection                    
                    returnParameters.Add(new FunctionParameter(EdmConstants.ReturnType, returnType, ParameterMode.ReturnValue));
                }
                else
                {
                    //Return type was specified but we could not find a type usage
                    return null;
                }
            }

            string functionNamespace;
            EntitySet[] entitySets = null;
            if (somFunction.IsFunctionImport)
            {
                var somFunctionImport = (Som.FunctionImportElement)somFunction;
                functionNamespace = somFunctionImport.Container.Name;
                if (null != somFunctionImport.EntitySet)
                {
                    EntityContainer entityContainer;
                    Debug.Assert(somFunctionImport.ReturnTypeList == null || somFunctionImport.ReturnTypeList.Count == 1,
                        "EntitySet cannot be specified on a FunctionImport if there are multiple ReturnType children");

                    Debug.Assert(functionImportEntityContainer != null, "functionImportEntityContainer must be specified during function import conversion");
                    entityContainer = functionImportEntityContainer;
                    entitySets = new EntitySet[] { GetEntitySet(somFunctionImport.EntitySet, entityContainer) };
                }
                else if (null != somFunctionImport.ReturnTypeList)
                {
                    Debug.Assert(functionImportEntityContainer != null, "functionImportEntityContainer must be specified during function import conversion");
                    EntityContainer entityContainer = functionImportEntityContainer;
                    entitySets = somFunctionImport.ReturnTypeList
                        .Select(returnType => null != returnType.EntitySet
                            ? GetEntitySet(returnType.EntitySet, functionImportEntityContainer)
                            : null)
                        .ToArray();
                }
            }
            else
            {
                functionNamespace = somFunction.Namespace;
            }

            List<FunctionParameter> parameters = new List<FunctionParameter>();
            foreach (Som.Parameter somParameter in somFunction.Parameters)
            {
                TypeUsage parameterType = GetFunctionTypeUsage(somFunction is Som.ModelFunction,
                                                               somFunction,
                                                               somParameter,
                                                               providerManifest,
                                                               areConvertingForProviderManifest,
                                                               somParameter.Type,
                                                               somParameter.CollectionKind,
                                                               somParameter.IsRefType,
                                                               somParameter,
                                                               convertedItemCache,
                                                               newGlobalItems);
                if (parameterType == null)
                {
                    return null;
                }

                FunctionParameter parameter = new FunctionParameter(somParameter.Name,
                                                                    parameterType,
                                                                    GetParameterMode(somParameter.ParameterDirection));
                AddOtherContent(somParameter, parameter);

                if (somParameter.Documentation != null)
                {
                    parameter.Documentation = ConvertToDocumentation(somParameter.Documentation);
                }
                parameters.Add(parameter);
            }

            EdmFunction function = new EdmFunction(somFunction.Name,
                functionNamespace,
                GetDataSpace(providerManifest),
                new EdmFunctionPayload
                {
                    Schema = somFunction.DbSchema,
                    StoreFunctionName = somFunction.StoreFunctionName,
                    CommandText = somFunction.CommandText,
                    EntitySets = entitySets,
                    IsAggregate = somFunction.IsAggregate,
                    IsBuiltIn = somFunction.IsBuiltIn,
                    IsNiladic = somFunction.IsNiladicFunction,
                    IsComposable = somFunction.IsComposable,
                    IsFromProviderManifest = areConvertingForProviderManifest,
                    IsFunctionImport = somFunction.IsFunctionImport,
                    ReturnParameters = returnParameters.ToArray(),
                    Parameters = parameters.ToArray(),
                    ParameterTypeSemantics = somFunction.ParameterTypeSemantics,
                });

            // Add this function to new global items, only if it is not a function import
            if (!somFunction.IsFunctionImport)
            {
                newGlobalItems.Add(somFunction, function);
            }

            //Check if we already converted functions since we are loading it from 
            //ssdl we could see functions many times.
            GlobalItem returnFunction = null;
            Debug.Assert(!convertedItemCache.ItemCollection.TryGetValue(function.Identity, false, out returnFunction),
                "Function duplicates must be checked by som");

            // Extract the optional Documentation
            if (somFunction.Documentation != null)
            {
                function.Documentation = ConvertToDocumentation(somFunction.Documentation);
            }
            AddOtherContent(somFunction, function);

            return function;
        }
Exemplo n.º 6
0
 /// <summary>
 /// Converts an SOM Documentation node to a metadata Documentation construct
 /// </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 Documentation object resulting from the convert operation</returns>
 private static Documentation ConvertToDocumentation(Som.DocumentationElement element)
 {
     Debug.Assert(null != element, "ConvertToDocumentation cannot be invoked with a null Som.Documentation element");
     return element.MetadataDocumentation;
 }
Exemplo n.º 7
0
        /// <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(Som.EntityContainer element,
                                                                DbProviderManifest providerManifest,
                                                                ConversionCache convertedItemCache,
                                                                Dictionary<Som.SchemaElement, GlobalItem> newGlobalItems)
        {
            // Creating a new entity container object and populate with converted entity set objects
            EntityContainer entityContainer = new EntityContainer(element.Name, GetDataSpace(providerManifest));
            newGlobalItems.Add(element, entityContainer);

            foreach (Som.EntityContainerEntitySet entitySet in element.EntitySets)
            {
                entityContainer.AddEntitySetBase(ConvertToEntitySet(entitySet,
                                                                      entityContainer.Name,
                                                                      providerManifest,
                                                                      convertedItemCache,
                                                                      newGlobalItems));
            }

            // Populate with converted relationship set objects
            foreach (Som.EntityContainerRelationshipSet 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 (Som.Function 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;
        }
Exemplo n.º 8
0
        /// <summary>
        /// Converts a property from SOM to metadata
        /// </summary>
        /// <param name="somProperty">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 EdmProperty ConvertToProperty(Som.StructuredProperty somProperty,
                                                  DbProviderManifest providerManifest,
                                                  ConversionCache convertedItemCache,
                                                  Dictionary<Som.SchemaElement, GlobalItem> newGlobalItems)
        {
            EdmProperty property;

            // Get the appropriate type object for this type, for primitive and enum types, get the facet values for the type
            // property as a type usage object as well                  
            TypeUsage typeUsage = null;

            Som.ScalarType scalarType = somProperty.Type as Som.ScalarType;

            if (scalarType != null && somProperty.Schema.DataModel != Som.SchemaDataModelOption.EntityDataModel)
            {
                // parsing ssdl
                typeUsage = somProperty.TypeUsage;
                UpdateSentinelValuesInFacets(ref typeUsage);
            }
            else
            {
                EdmType propertyType;

                if (scalarType != null)
                {
                    Debug.Assert(somProperty.TypeUsage.EdmType.BuiltInTypeKind == BuiltInTypeKind.PrimitiveType);
                    // try to get the instance of the primitive type from the item collection so that it back pointer is set.
                    propertyType = convertedItemCache.ItemCollection.GetItem<PrimitiveType>(somProperty.TypeUsage.EdmType.FullName);
                }
                else
                {
                    propertyType = (EdmType)LoadSchemaElement(somProperty.Type, providerManifest, convertedItemCache, newGlobalItems);
                }

                if (somProperty.CollectionKind != CollectionKind.None)
                {
                    typeUsage = TypeUsage.Create(new CollectionType(propertyType));
                }
                else
                {
                    Som.SchemaEnumType enumType = scalarType == null ? somProperty.Type as Som.SchemaEnumType : null;
                    typeUsage = TypeUsage.Create(propertyType);
                    if (enumType != null)
                    {
                        somProperty.EnsureEnumTypeFacets(convertedItemCache, newGlobalItems);
                    }

                    if (somProperty.TypeUsage != null)
                    {
                        ApplyTypePropertyFacets(somProperty.TypeUsage, ref typeUsage);
                    }
                }
            }

            PopulateGeneralFacets(somProperty, providerManifest, ref typeUsage);
            property = new EdmProperty(somProperty.Name, typeUsage);

            // Extract the optional Documentation
            if (somProperty.Documentation != null)
            {
                property.Documentation = ConvertToDocumentation(somProperty.Documentation);
            }
            AddOtherContent(somProperty, property);

            return property;
        }
Exemplo n.º 9
0
        /// <summary>
        /// Get a primitive type when converting a CSDL schema
        /// </summary>
        /// <param name="scalarType">The schema type representing the primitive type</param>
        /// <param name="providerManifest">The provider manifest for retrieving the store types</param>
        private static PrimitiveType GetPrimitiveType(Som.ScalarType scalarType,
                                                          DbProviderManifest providerManifest)
        {
            PrimitiveType returnValue = null;
            string scalarTypeName = scalarType.Name;

            foreach (PrimitiveType primitiveType in providerManifest.GetStoreTypes())
            {
                if (primitiveType.Name == scalarTypeName)
                {
                    returnValue = primitiveType;
                    break;
                }
            }

            Debug.Assert(scalarType != null, "Som scalar type should always resolve to a primitive type");
            return returnValue;
        }
Exemplo n.º 10
0
        /// <summary>
        /// Loads a schema element
        /// </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 item resulting from the load</returns>
        internal static MetadataItem LoadSchemaElement(Som.SchemaType element,
                                              DbProviderManifest providerManifest,
                                              ConversionCache convertedItemCache,
                                              Dictionary<Som.SchemaElement, GlobalItem> newGlobalItems)
        {
            Debug.Assert(providerManifest != null, "This will make the dataspace to be default SSpace");
            // Try to fetch from the collection first
            GlobalItem item;

            Debug.Assert(!convertedItemCache.ItemCollection.TryGetValue(element.FQName, false, out item), "Som should have checked for duplicate items");

            // Try to fetch in our collection of new GlobalItems
            if (newGlobalItems.TryGetValue(element, out item))
            {
                return item;
            }

            Som.EntityContainer entityContainer = element as Som.EntityContainer;
            // Perform different conversion depending on the type of the SOM object
            if (entityContainer != null)
            {
                item = ConvertToEntityContainer(entityContainer,
                                                providerManifest,
                                                convertedItemCache,
                                                newGlobalItems);
            }
            else if (element is Som.SchemaEntityType)
            {
                item = ConvertToEntityType((Som.SchemaEntityType)element,
                                           providerManifest,
                                           convertedItemCache,
                                           newGlobalItems);
            }
            else if (element is Som.Relationship)
            {
                item = ConvertToAssociationType((Som.Relationship)element,
                                                providerManifest,
                                                convertedItemCache,
                                                newGlobalItems);
            }
            else if (element is Som.SchemaComplexType)
            {
                item = ConvertToComplexType((Som.SchemaComplexType)element,
                                            providerManifest,
                                            convertedItemCache,
                                            newGlobalItems);
            }
            else if (element is Som.Function)
            {
                item = ConvertToFunction((Som.Function)element, providerManifest,
                    convertedItemCache, null, newGlobalItems);
            }
            else if (element is Som.SchemaEnumType)
            {
                item = ConvertToEnumType((Som.SchemaEnumType)element, newGlobalItems);
            }
            else
            {
                // the only type we don't handle is the ProviderManifest TypeElement
                // if it is anything else, it is probably a mistake
                Debug.Assert(element is Som.TypeElement &&
                    element.Schema.DataModel == Som.SchemaDataModelOption.ProviderManifestModel,
                    "Unknown Type in somschema");
                return null;
            }

            return item;
        }
Exemplo n.º 11
0
        /// <summary>
        /// Populate the facets on the TypeUsage object for a property
        /// </summary>
        /// <param name="somProperty">The property containing the information</param>
        /// <param name="propertyTypeUsage">The type usage object where to populate facet</param>
        /// <param name="providerManifest">The provider manifest to be used for conversion</param>
        private static void PopulateGeneralFacets(Som.StructuredProperty somProperty,
                                                  DbProviderManifest providerManifest,
                                                  ref TypeUsage propertyTypeUsage)
        {
            bool madeChanges = false;
            Dictionary<string, Facet> facets = propertyTypeUsage.Facets.ToDictionary(f => f.Name);
            if (!somProperty.Nullable)
            {
                facets[DbProviderManifest.NullableFacetName] = Facet.Create(MetadataItem.NullableFacetDescription, false);
                madeChanges = true;
            }

            if (somProperty.Default != null)
            {
                facets[DbProviderManifest.DefaultValueFacetName] = Facet.Create(MetadataItem.DefaultValueFacetDescription, somProperty.DefaultAsObject);
                madeChanges = true;
            }

            //This is not really a general facet
            //If we are dealing with a 1.1 Schema, Add a facet for CollectionKind
            if (somProperty.Schema.SchemaVersion == XmlConstants.EdmVersionForV1_1)
            {
                Facet newFacet = Facet.Create(MetadataItem.CollectionKindFacetDescription, somProperty.CollectionKind);
                facets.Add(newFacet.Name, newFacet);
                madeChanges = true;
            }

            if (madeChanges)
            {
                propertyTypeUsage = TypeUsage.Create(propertyTypeUsage.EdmType, facets.Values);
            }
        }
Exemplo n.º 12
0
        private static void ConvertSchema(Som.Schema somSchema, DbProviderManifest providerManifest,
            ConversionCache convertedItemCache, Dictionary<Som.SchemaElement, GlobalItem> newGlobalItems)
        {
            List<Som.Function> funcsWithUnresolvedTypes = new List<Som.Function>();
            foreach (Som.SchemaType element in somSchema.SchemaTypes)
            {
                if (null == LoadSchemaElement(element, providerManifest, convertedItemCache, newGlobalItems))
                {
                    if (element is Som.Function)
                    {
                        funcsWithUnresolvedTypes.Add(element as Som.Function);
                    }
                }
            }

            foreach (Som.SchemaEntityType element in somSchema.SchemaTypes.OfType<Som.SchemaEntityType>())
            {
                LoadEntityTypePhase2(element, providerManifest, convertedItemCache, newGlobalItems);
            }

            foreach (var function in funcsWithUnresolvedTypes)
            {
                if (null == LoadSchemaElement(function, providerManifest, convertedItemCache, newGlobalItems))
                {
                    Debug.Fail("Could not load model function definition"); //this should never happen.
                }
            }

            if (convertedItemCache.ItemCollection.DataSpace == DataSpace.CSpace)
            {
                EdmItemCollection edmCollection = (EdmItemCollection)convertedItemCache.ItemCollection;
                edmCollection.EdmVersion = somSchema.SchemaVersion;
            }
            else
            {
                Debug.Assert(convertedItemCache.ItemCollection.DataSpace == DataSpace.SSpace, "Did you add a new space?");
                // when converting the ProviderManifest, the DataSpace is SSpace, but the ItemCollection is EmptyItemCollection, 
                // not StoreItemCollection
                StoreItemCollection storeCollection = convertedItemCache.ItemCollection as StoreItemCollection;
                if (storeCollection != null)
                {
                    storeCollection.StoreSchemaVersion = somSchema.SchemaVersion;
                }
            }
        }
Exemplo n.º 13
0
        private static TypeUsage GetFunctionTypeUsage(bool isModelFunction,
                                                      Som.Function somFunction,
                                                      Som.FacetEnabledSchemaElement somParameter,
                                                      DbProviderManifest providerManifest,
                                                      bool areConvertingForProviderManifest,
                                                      Som.SchemaType type,
                                                      CollectionKind collectionKind,
                                                      bool isRefType,
                                                      Som.SchemaElement schemaElement,
                                                      ConversionCache convertedItemCache,
                                                      Dictionary<Som.SchemaElement, GlobalItem> newGlobalItems)
        {
            if (null != somParameter && areConvertingForProviderManifest
                && somParameter.HasUserDefinedFacets)
            {
                return somParameter.TypeUsage;
            }

            if (null == type)
            {
                if (isModelFunction && somParameter != null && somParameter is Som.Parameter)
                {
                    ((Som.Parameter)somParameter).ResolveNestedTypeNames(convertedItemCache, newGlobalItems);
                    return somParameter.TypeUsage;
                }
                else if (somParameter != null && somParameter is Som.ReturnType)
                {
                    ((Som.ReturnType)somParameter).ResolveNestedTypeNames(convertedItemCache, newGlobalItems);
                    return somParameter.TypeUsage;
                }
                else
                {
                    return null;
                }
            }

            EdmType edmType;
            if (!areConvertingForProviderManifest)
            {
                // SOM verifies the type is either scalar, row, or entity
                Som.ScalarType scalarType = type as Som.ScalarType;
                if (null != scalarType)
                {
                    if (isModelFunction && somParameter != null)
                    {
                        if (somParameter.TypeUsage == null)
                        {
                            somParameter.ValidateAndSetTypeUsage(scalarType);
                        }
                        return somParameter.TypeUsage;
                    }
                    else if (isModelFunction)
                    {
                        Som.ModelFunction modelFunction = somFunction as Som.ModelFunction;
                        if (modelFunction.TypeUsage == null)
                        {
                            modelFunction.ValidateAndSetTypeUsage(scalarType);
                        }
                        return modelFunction.TypeUsage;
                    }
                    else if (somParameter != null && somParameter.HasUserDefinedFacets && somFunction.Schema.DataModel == System.Data.EntityModel.SchemaObjectModel.SchemaDataModelOption.ProviderDataModel)
                    {
                        somParameter.ValidateAndSetTypeUsage(scalarType);
                        return somParameter.TypeUsage;
                    }
                    else
                    {
                        edmType = GetPrimitiveType(scalarType, providerManifest);
                    }
                }
                else
                {
                    edmType = (EdmType)LoadSchemaElement(type,
                        providerManifest,
                        convertedItemCache,
                        newGlobalItems);

                    // Neither FunctionImport nor its Parameters can have facets when defined in CSDL so for enums, 
                    // since they are only a CSpace concept, we need to process facets only on model functions 
                    if (isModelFunction && type is Som.SchemaEnumType)
                    {
                        Debug.Assert(somFunction.Schema.DataModel == Som.SchemaDataModelOption.EntityDataModel, "Enums live only in CSpace");

                        if (somParameter != null)
                        {
                            somParameter.ValidateAndSetTypeUsage(edmType);
                            return somParameter.TypeUsage;
                        }
                        else if (somFunction != null)
                        {
                            var modelFunction = ((Som.ModelFunction)somFunction);
                            modelFunction.ValidateAndSetTypeUsage(edmType);
                            return modelFunction.TypeUsage;
                        }
                        else
                        {
                            Debug.Fail("Should never get here.");
                        }
                    }
                }
            }
            else if (type is Som.TypeElement)
            {
                Som.TypeElement typeElement = type as Som.TypeElement;
                edmType = typeElement.PrimitiveType;
            }
            else
            {
                Som.ScalarType typeElement = type as Som.ScalarType;
                edmType = typeElement.Type;
            }

            //Construct type usage
            TypeUsage usage;
            if (collectionKind != CollectionKind.None)
            {
                usage = convertedItemCache.GetCollectionTypeUsageWithNullFacets(edmType);
            }
            else
            {
                if (edmType is EntityType && isRefType)
                {
                    usage = TypeUsage.Create(new RefType(edmType as EntityType));
                }
                else
                {
                    usage = convertedItemCache.GetTypeUsageWithNullFacets(edmType);
                }
            }

            return usage;

        }
Exemplo n.º 14
0
 /// <summary>
 /// Converts an entity set from SOM to metadata
 /// </summary>
 /// <param name="set">The SOM element to process</param>
 /// <param name="container"></param>
 /// <returns>The entity set object resulting from the convert</returns>
 private static EntitySet GetEntitySet(Som.EntityContainerEntitySet set, EntityContainer container)
 {
     return container.GetEntitySetByName(set.Name, false);
 }
Exemplo n.º 15
0
        /// <summary>
        /// Converts an entity type from SOM to metadata
        /// 
        /// This method should only build the internally contained and vertical part of the EntityType (keys, properties, and base types) but not 
        /// sideways parts (NavigationProperties) that go between types or we risk trying to access and EntityTypes keys, from the referential constraint,
        /// before the base type, which has the keys, is setup yet.
        /// </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 type object resulting from the convert</returns>
        private static EntityType ConvertToEntityType(Som.SchemaEntityType element,
                                                      DbProviderManifest providerManifest,
                                                      ConversionCache convertedItemCache,
                                                      Dictionary<Som.SchemaElement, GlobalItem> newGlobalItems)
        {
            string[] keyMembers = null;
            // Check if this type has keys
            if (element.DeclaredKeyProperties.Count != 0)
            {
                keyMembers = new string[element.DeclaredKeyProperties.Count];
                for (int i = 0; i < keyMembers.Length; i++)
                {
                    //Add the name of the key property to the list of
                    //key properties
                    keyMembers[i] = (element.DeclaredKeyProperties[i].Property.Name);
                }
            }

            EdmProperty[] properties = new EdmProperty[element.Properties.Count];
            int index = 0;

            foreach (Som.StructuredProperty somProperty in element.Properties)
            {
                properties[index++] = ConvertToProperty(somProperty,
                                                        providerManifest,
                                                        convertedItemCache,
                                                        newGlobalItems);
            }

            EntityType entityType = new EntityType(element.Name,
                                                   element.Namespace,
                                                   GetDataSpace(providerManifest),
                                                   keyMembers,
                                                   properties);

            if (element.BaseType != null)
            {
                entityType.BaseType = (EdmType)(LoadSchemaElement(element.BaseType,
                                                                  providerManifest,
                                                                  convertedItemCache,
                                                                  newGlobalItems));
            }

            // set the abstract and sealed type values for the entity type
            entityType.Abstract = element.IsAbstract;
            // Extract the optional Documentation
            if (element.Documentation != null)
            {
                entityType.Documentation = ConvertToDocumentation(element.Documentation);
            }
            AddOtherContent(element, entityType);
            newGlobalItems.Add(element, entityType);
            return entityType;
        }
Exemplo n.º 16
0
        /// <summary>
        /// Converts an association set from SOM to metadata
        /// </summary>
        /// <param name="relationshipSet">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>
        /// <param name="container"></param>
        /// <returns>The association set object resulting from the convert</returns>
        private static AssociationSet ConvertToAssociationSet(Som.EntityContainerRelationshipSet relationshipSet,
                                                              DbProviderManifest providerManifest,
                                                              ConversionCache convertedItemCache,
                                                              EntityContainer container,
                                                              Dictionary<Som.SchemaElement, GlobalItem> newGlobalItems)
        {
            Debug.Assert(relationshipSet.Relationship.RelationshipKind == RelationshipKind.Association);

            AssociationType associationType = (AssociationType)LoadSchemaElement((Som.SchemaType)relationshipSet.Relationship,
                                                                                  providerManifest,
                                                                                  convertedItemCache,
                                                                                  newGlobalItems);

            AssociationSet associationSet = new AssociationSet(relationshipSet.Name, associationType);

            foreach (Som.EntityContainerRelationshipSetEnd end in relationshipSet.Ends)
            {
                //-- need the EntityType for the end
                EntityType endEntityType = (EntityType)LoadSchemaElement(end.EntitySet.EntityType,
                                                                         providerManifest,
                                                                         convertedItemCache,
                                                                         newGlobalItems);
                //-- need to get the end member
                AssociationEndMember endMember = (AssociationEndMember)associationType.Members[end.Name];
                //-- create the end
                AssociationSetEnd associationSetEnd = new AssociationSetEnd(GetEntitySet(end.EntitySet, container),
                                                                            associationSet,
                                                                            endMember);

                AddOtherContent(end, associationSetEnd);
                associationSet.AddAssociationSetEnd(associationSetEnd);

                // Extract optional Documentation from the end element
                if (end.Documentation != null)
                {
                    associationSetEnd.Documentation = ConvertToDocumentation(end.Documentation);
                }
            }

            // Extract the optional Documentation
            if (relationshipSet.Documentation != null)
            {
                associationSet.Documentation = ConvertToDocumentation(relationshipSet.Documentation);
            }
            AddOtherContent(relationshipSet, associationSet);

            return associationSet;
        }
Exemplo n.º 17
0
        private static void LoadEntityTypePhase2(Som.SchemaEntityType element,
                                                      DbProviderManifest providerManifest,
                                                      ConversionCache convertedItemCache,
                                                      Dictionary<Som.SchemaElement, GlobalItem> newGlobalItems)
        {
            EntityType entityType = (EntityType)newGlobalItems[element];

            // Since Navigation properties are internal and not part of member collection, we
            // need to initialize the base class first before we start adding the navigation property
            // this will ensure that all the base navigation properties are initialized
            foreach (Som.NavigationProperty somNavigationProperty in element.NavigationProperties)
            {
                entityType.AddMember(ConvertToNavigationProperty(entityType,
                                                                 somNavigationProperty,
                                                                 providerManifest,
                                                                 convertedItemCache,
                                                                 newGlobalItems));
            }
        }
Exemplo n.º 18
0
        /// <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,
                                                                      Som.NavigationProperty somNavigationProperty,
                                                                      DbProviderManifest providerManifest,
                                                                      ConversionCache convertedItemCache,
                                                                      Dictionary<Som.SchemaElement, GlobalItem> newGlobalItems)
        {
            // Navigation properties cannot be primitive types, so we can ignore the possibility of having primitive type
            // facets
            EntityType toEndEntityType = (EntityType)LoadSchemaElement(somNavigationProperty.Type,
                                                      providerManifest,
                                                      convertedItemCache,
                                                      newGlobalItems);

            EdmType edmType = toEndEntityType;

            // Also load the relationship Type that this navigation property represents
            AssociationType relationshipType = (AssociationType)LoadSchemaElement((Som.Relationship)somNavigationProperty.Relationship,
                    providerManifest, convertedItemCache, newGlobalItems);

            Som.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
            NavigationProperty 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;
        }
Exemplo n.º 19
0
        /// <summary>
        /// Converts an complex type 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 complex type object resulting from the convert</returns>
        private static ComplexType ConvertToComplexType(Som.SchemaComplexType element,
                                                        DbProviderManifest providerManifest,
                                                        ConversionCache convertedItemCache,
                                                        Dictionary<Som.SchemaElement, GlobalItem> newGlobalItems)
        {
            ComplexType complexType = new ComplexType(element.Name,
                                                      element.Namespace,
                                                      GetDataSpace(providerManifest));
            newGlobalItems.Add(element, complexType);

            foreach (Som.StructuredProperty somProperty in element.Properties)
            {
                complexType.AddMember(ConvertToProperty(somProperty,
                                                          providerManifest,
                                                          convertedItemCache,
                                                          newGlobalItems));
            }

            // set the abstract and sealed type values for the entity type
            complexType.Abstract = element.IsAbstract;

            if (element.BaseType != null)
            {
                complexType.BaseType = (EdmType)(LoadSchemaElement(element.BaseType,
                                                                  providerManifest,
                                                                  convertedItemCache,
                                                                  newGlobalItems));
            }

            // Extract the optional Documentation
            if (element.Documentation != null)
            {
                complexType.Documentation = ConvertToDocumentation(element.Documentation);
            }
            AddOtherContent(element, complexType);

            return complexType;
        }
Exemplo n.º 20
0
 /// <summary>
 /// Converts a schema from SOM into Metadata
 /// </summary>
 /// <param name="somSchema">The SOM schema to convert</param>
 /// <param name="providerManifest">The provider manifest to be used for conversion</param>
 /// <param name="itemCollection">The item collection for currently existing metadata objects</param>
 internal static IEnumerable<GlobalItem> ConvertSchema(Som.Schema somSchema,
                                                       DbProviderManifest providerManifest,
                                                       ItemCollection itemCollection)
 {
     Dictionary<Som.SchemaElement, GlobalItem> newGlobalItems = new Dictionary<Som.SchemaElement, GlobalItem>();
     ConvertSchema(somSchema, providerManifest, new ConversionCache(itemCollection), newGlobalItems);
     return newGlobalItems.Values;
 }
Exemplo n.º 21
0
        /// <summary>
        /// Converts SchemaEnumType instance to Metadata EnumType.
        /// </summary>
        /// <param name="somEnumType">SchemaEnumType to be covnerted.</param>
        /// <param name="newGlobalItems">Global item objects where newly created Metadata EnumType will be added.</param>
        /// <returns></returns>
        private static EnumType ConvertToEnumType(Som.SchemaEnumType somEnumType, Dictionary<Som.SchemaElement, GlobalItem> newGlobalItems)
        {
            Debug.Assert(somEnumType != null, "somEnumType != null");
            Debug.Assert(newGlobalItems != null, "newGlobalItems != null");
            Debug.Assert(somEnumType.UnderlyingType is Som.ScalarType, "At this point the underlying type should have already been validated and should be ScalarType");

            Som.ScalarType enumUnderlyingType = (Som.ScalarType)somEnumType.UnderlyingType;

            // note that enums don't live in SSpace so there is no need to GetDataSpace() for it.
            EnumType enumType = new EnumType(somEnumType.Name,
                                             somEnumType.Namespace,
                                             enumUnderlyingType.Type,
                                             somEnumType.IsFlags,
                                             DataSpace.CSpace);

            Type clrEnumUnderlyingType = enumUnderlyingType.Type.ClrEquivalentType;

            foreach (var somEnumMember in somEnumType.EnumMembers)
            {
                Debug.Assert(somEnumMember.Value != null, "value must not be null at this point");
                var enumMember = new EnumMember(somEnumMember.Name, Convert.ChangeType(somEnumMember.Value, clrEnumUnderlyingType, CultureInfo.InvariantCulture));

                if (somEnumMember.Documentation != null)
                {
                    enumMember.Documentation = ConvertToDocumentation(somEnumMember.Documentation);
                }

                AddOtherContent(somEnumMember, enumMember);
                enumType.AddMember(enumMember);
            }

            if (somEnumType.Documentation != null)
            {
                enumType.Documentation = ConvertToDocumentation(somEnumType.Documentation);
            }
            AddOtherContent(somEnumType, enumType);

            newGlobalItems.Add(somEnumType, enumType);
            return enumType;
        }