/// <summary>
 ///     Merge the discriminatorMap info we just found with what we've already found.
 ///     In practice, if either the current or the new map is from an OfTypeOnly view, we
 ///     have to avoid the optimizations.
 ///     If we have a new map that is a superset of the current map, then we can just swap
 ///     the new map for the current one.
 ///     If the current map is tha super set of the new one ther's nothing to do.
 ///     (Of course, if neither has changed, then we really don't need to look)
 /// </summary>
 internal void Merge(EntityTypeBase neededRootEntityType, bool includesSubtypes, ExplicitDiscriminatorMap discriminatorMap)
 {
     // If what we've found doesn't exactly match what we are looking for we have more work to do
     if (RootEntityType != neededRootEntityType
         || IncludesSubTypes != includesSubtypes)
     {
         if (!IncludesSubTypes
             || !includesSubtypes)
         {
             // If either the original or the new map is from an of-type-only view we can't
             // merge, we just have to not optimize this case.
             DiscriminatorMap = null;
         }
         if (TypeSemantics.IsSubTypeOf(RootEntityType, neededRootEntityType))
         {
             // we're asking for a super type of existing type, and what we had is a proper 
             // subset of it -we can replace the existing item.
             RootEntityType = neededRootEntityType;
             DiscriminatorMap = discriminatorMap;
         }
         if (!TypeSemantics.IsSubTypeOf(neededRootEntityType, RootEntityType))
         {
             // If either the original or the new map is from an of-type-only view we can't
             // merge, we just have to not optimize this case.
             DiscriminatorMap = null;
         }
     }
 }
Example #2
0
 internal DiscriminatedNewEntityOp(
     TypeUsage type, ExplicitDiscriminatorMap discriminatorMap,
     EntitySet entitySet, List <RelProperty> relProperties)
     : base(OpType.DiscriminatedNewEntity, type, true, entitySet, relProperties)
 {
     DebugCheck.NotNull(discriminatorMap);
     m_discriminatorMap = discriminatorMap;
 }
Example #3
0
 internal virtual DiscriminatedNewEntityOp CreateDiscriminatedNewEntityOp(
     TypeUsage type,
     ExplicitDiscriminatorMap discriminatorMap,
     EntitySet entitySet,
     List <RelProperty> relProperties)
 {
     return(new DiscriminatedNewEntityOp(type, discriminatorMap, entitySet, relProperties));
 }
Example #4
0
        internal RootTypeInfo(TypeUsage type, ExplicitDiscriminatorMap discriminatorMap)
            : base(type, null)
        {
            PlanCompiler.Assert(type.EdmType.BaseType == null, "only root types allowed here");

            m_propertyMap = new Dictionary<PropertyRef, EdmProperty>();
            m_propertyRefList = new List<PropertyRef>();
            m_discriminatorMap = discriminatorMap;
            TypeIdKind = TypeIdKind.Generated;
        }
        private readonly RootTypeInfo m_rootType; // the top-most type in this types type hierarchy

        #endregion

        #region Constructors and factory methods

        /// <summary>
        ///     Creates type information for a type
        /// </summary>
        /// <param name="type"> </param>
        /// <param name="superTypeInfo"> </param>
        /// <returns> </returns>
        internal static TypeInfo Create(md.TypeUsage type, TypeInfo superTypeInfo, ExplicitDiscriminatorMap discriminatorMap)
        {
            TypeInfo result;
            if (superTypeInfo == null)
            {
                result = new RootTypeInfo(type, discriminatorMap);
            }
            else
            {
                result = new TypeInfo(type, superTypeInfo);
            }
            return result;
        }
 internal DiscriminatorMapInfo(EntityTypeBase rootEntityType, bool includesSubTypes, ExplicitDiscriminatorMap discriminatorMap)
 {
     RootEntityType = rootEntityType;
     IncludesSubTypes = includesSubTypes;
     DiscriminatorMap = discriminatorMap;
 }
        private TypeInfo CreateTypeInfoForStructuredType(md.TypeUsage type, ExplicitDiscriminatorMap discriminatorMap)
        {
            TypeInfo typeInfo;

            PlanCompiler.Assert(TypeUtils.IsStructuredType(type), "expected structured type. Found " + type);

            // Return existing entry, if one is available
            typeInfo = GetTypeInfo(type);
            if (typeInfo != null)
            {
                return typeInfo;
            }

            // Ensure that my supertype has been added to the map. 
            TypeInfo superTypeInfo = null;
            md.RefType refType;
            if (type.EdmType.BaseType != null)
            {
                superTypeInfo = CreateTypeInfoForStructuredType(md.TypeUsage.Create(type.EdmType.BaseType), discriminatorMap);
            }
            // 
            // Handle Ref types also in a similar fashion
            //
            else if (TypeHelpers.TryGetEdmType(type, out refType))
            {
                var entityType = refType.ElementType as md.EntityType;
                if (entityType != null
                    && entityType.BaseType != null)
                {
                    var baseRefType = TypeHelpers.CreateReferenceTypeUsage(entityType.BaseType as md.EntityType);
                    superTypeInfo = CreateTypeInfoForStructuredType(baseRefType, discriminatorMap);
                }
            }

            //
            // Add the types of my properties to the TypeInfo map
            // 
            foreach (md.EdmMember m in TypeHelpers.GetDeclaredStructuralMembers(type))
            {
                CreateTypeInfoForType(m.TypeUsage);
            }

            // 
            // Get the types of the rel properties also
            //
            {
                md.EntityTypeBase entityType;
                if (TypeHelpers.TryGetEdmType(type, out entityType))
                {
                    foreach (var p in m_relPropertyHelper.GetDeclaredOnlyRelProperties(entityType))
                    {
                        CreateTypeInfoForType(p.ToEnd.TypeUsage);
                    }
                }
            }

            // Now add myself to the map
            typeInfo = TypeInfo.Create(type, superTypeInfo, discriminatorMap);
            m_typeInfoMap.Add(type, typeInfo);

            return typeInfo;
        }
        // <summary>
        // Tries to lookup custom discriminator map for the given type (applies to EntitySets with
        // TPH discrimination pattern)
        // </summary>
        private bool TryGetDiscriminatorMap(md.EdmType type, out ExplicitDiscriminatorMap discriminatorMap)
        {
            discriminatorMap = null;

            // check that there are actually discriminator maps available
            if (null == m_discriminatorMaps)
            {
                return false;
            }

            // must be an entity type...
            if (type.BuiltInTypeKind
                != md.BuiltInTypeKind.EntityType)
            {
                return false;
            }

            // get root entity type (discriminator maps are mapped from the root)
            var rootEntityType = GetRootType((md.EntityType)type);

            // find entity set
            md.EntitySet entitySet;
            if (!m_entityTypeToEntitySetMap.TryGetValue(rootEntityType, out entitySet))
            {
                return false;
            }

            // free floating entity constructors are stored with a null EntitySet
            if (entitySet == null)
            {
                return false;
            }

            // look for discriminator map
            return m_discriminatorMaps.TryGetValue(entitySet, out discriminatorMap);
        }
Example #9
0
 // <summary>
 // Create a discriminated named type constructor
 // </summary>
 // <param name="type"> Type metadata that specifies the type of the instance to construct </param>
 // <param name="discriminatorMap"> Mapping information including discriminator values </param>
 // <param name="entitySet"> the entityset that this instance belongs to </param>
 // <param name="relProperties"> list of rel properties that have corresponding values </param>
 // <returns> A new DiscriminatedNewInstanceOp with the specified result type and discrimination behavior </returns>
 internal virtual DiscriminatedNewEntityOp CreateDiscriminatedNewEntityOp(
     TypeUsage type, ExplicitDiscriminatorMap discriminatorMap,
     EntitySet entitySet, List<RelProperty> relProperties)
 {
     return new DiscriminatedNewEntityOp(type, discriminatorMap, entitySet, relProperties);
 }