private EntityContainerEntitySet InferEntitySet( IRelationshipEnd relationshipEnd) { List <EntityContainerEntitySet> containerEntitySetList = new List <EntityContainerEntitySet>(); foreach (EntityContainerEntitySet entitySet in this.ParentElement.EntitySets) { if (relationshipEnd.Type.IsOfType((StructuredType)entitySet.EntityType)) { containerEntitySetList.Add(entitySet); } } if (containerEntitySetList.Count == 1) { return(containerEntitySetList[0]); } if (containerEntitySetList.Count == 0) { this.AddError(ErrorCode.MissingExtentEntityContainerEnd, EdmSchemaErrorSeverity.Error, (object)Strings.MissingEntityContainerEnd((object)relationshipEnd.Name, (object)this.FQName)); } else { this.AddError(ErrorCode.AmbiguousEntityContainerEnd, EdmSchemaErrorSeverity.Error, (object)Strings.AmbiguousEntityContainerEnd((object)relationshipEnd.Name, (object)this.FQName)); } return((EntityContainerEntitySet)null); }
/// <summary> /// For the given relationship end, find the EntityContainer Property that will work for the extent /// </summary> /// <param name="relationshipEnd">The relationship end of the RelationshipSet that needs and extent</param> /// <returns>Null is none could be found, or the EntityContainerProperty that is the valid extent</returns> private EntityContainerEntitySet InferEntitySet(IRelationshipEnd relationshipEnd) { Debug.Assert(relationshipEnd != null, "relationshipEnd parameter is null"); List <EntityContainerEntitySet> possibleExtents = new List <EntityContainerEntitySet>(); foreach (EntityContainerEntitySet set in ParentElement.EntitySets) { if (relationshipEnd.Type.IsOfType(set.EntityType)) { possibleExtents.Add(set); } } if (possibleExtents.Count == 1) { return(possibleExtents[0]); } else if (possibleExtents.Count == 0) { // no matchs AddError(ErrorCode.MissingExtentEntityContainerEnd, EdmSchemaErrorSeverity.Error, System.Data.Entity.Strings.MissingEntityContainerEnd(relationshipEnd.Name, FQName)); } else { // abmigous AddError(ErrorCode.AmbiguousEntityContainerEnd, EdmSchemaErrorSeverity.Error, System.Data.Entity.Strings.AmbiguousEntityContainerEnd(relationshipEnd.Name, FQName)); } return(null); }
/// <summary> /// For the given relationship end, find the EntityContainer Property that will work for the extent /// </summary> /// <param name="relationshipEnd"> The relationship end of the RelationshipSet that needs and extent </param> /// <returns> Null is none could be found, or the EntityContainerProperty that is the valid extent </returns> private EntityContainerEntitySet InferEntitySet(IRelationshipEnd relationshipEnd) { DebugCheck.NotNull(relationshipEnd); var possibleExtents = new List <EntityContainerEntitySet>(); foreach (var set in ParentElement.EntitySets) { if (relationshipEnd.Type.IsOfType(set.EntityType)) { possibleExtents.Add(set); } } if (possibleExtents.Count == 1) { return(possibleExtents[0]); } else if (possibleExtents.Count == 0) { // no matchs AddError( ErrorCode.MissingExtentEntityContainerEnd, EdmSchemaErrorSeverity.Error, Strings.MissingEntityContainerEnd(relationshipEnd.Name, FQName)); } else { // abmigous AddError( ErrorCode.AmbiguousEntityContainerEnd, EdmSchemaErrorSeverity.Error, Strings.AmbiguousEntityContainerEnd(relationshipEnd.Name, FQName)); } return(null); }
private static AssociationEndMember InitializeAssociationEndMember( AssociationType associationType, IRelationshipEnd end, EntityType endMemberType) { EdmMember edmMember; AssociationEndMember associationEndMember; if (!associationType.Members.TryGetValue(end.Name, false, out edmMember)) { associationEndMember = new AssociationEndMember(end.Name, endMemberType.GetReferenceType(), end.Multiplicity.Value); associationType.AddKeyMember((EdmMember)associationEndMember); } else { associationEndMember = (AssociationEndMember)edmMember; } RelationshipEnd relationshipEnd = end as RelationshipEnd; if (relationshipEnd != null && relationshipEnd.Documentation != null) { associationEndMember.Documentation = Converter.ConvertToDocumentation(relationshipEnd.Documentation); } return(associationEndMember); }
public override IRelationship CreateRelationship( IRelationshipEnd rel1, IRelationshipEnd rel2) { ISheet sheet = rel1.OwnedSheet; IRelationship rel = CreateRelationship(); rel.End1 = rel1; rel.End2 = rel2; sheet.AddRelationship(rel); return(rel); }
protected override void AddEnd( IRelationshipEnd relationshipEnd, EntityContainerEntitySet entitySet) { EntityContainerAssociationSetEnd associationSetEnd = new EntityContainerAssociationSetEnd(this); associationSetEnd.Role = relationshipEnd.Name; associationSetEnd.RelationshipEnd = relationshipEnd; associationSetEnd.EntitySet = entitySet; if (associationSetEnd.EntitySet == null) { return; } this._relationshipEnds.Add(associationSetEnd.Role, associationSetEnd); }
// <summary> // Create and add a EntityContainerEnd from the IRelationshipEnd provided // </summary> // <param name="relationshipEnd"> The relationship end of the end to add. </param> // <param name="entitySet"> The entitySet to associate with the relationship end. </param> protected override void AddEnd(IRelationshipEnd relationshipEnd, EntityContainerEntitySet entitySet) { DebugCheck.NotNull(relationshipEnd); Debug.Assert(!_relationshipEnds.ContainsKey(relationshipEnd.Name)); // we expect set to be null sometimes var end = new EntityContainerAssociationSetEnd(this); end.Role = relationshipEnd.Name; end.RelationshipEnd = relationshipEnd; end.EntitySet = entitySet; if (end.EntitySet != null) { _relationshipEnds.Add(end.Role, end); } }
private static NavigationProperty ConvertToNavigationProperty( EntityType declaringEntityType, System.Data.Entity.Core.SchemaObjectModel.NavigationProperty somNavigationProperty, DbProviderManifest providerManifest, Converter.ConversionCache convertedItemCache, Dictionary <SchemaElement, GlobalItem> newGlobalItems) { EntityType endMemberType = (EntityType)Converter.LoadSchemaElement(somNavigationProperty.Type, providerManifest, convertedItemCache, newGlobalItems); AssociationType associationType = (AssociationType)Converter.LoadSchemaElement((System.Data.Entity.Core.SchemaObjectModel.SchemaType)somNavigationProperty.Relationship, providerManifest, convertedItemCache, newGlobalItems); IRelationshipEnd end = (IRelationshipEnd)null; somNavigationProperty.Relationship.TryGetEnd(somNavigationProperty.ToEnd.Name, out end); RelationshipMultiplicity?multiplicity1 = end.Multiplicity; EdmType edmType = (multiplicity1.GetValueOrDefault() != RelationshipMultiplicity.Many ? 0 : (multiplicity1.HasValue ? 1 : 0)) == 0 ? (EdmType)endMemberType : (EdmType)endMemberType.GetCollectionType(); RelationshipMultiplicity?multiplicity2 = end.Multiplicity; TypeUsage typeUsage; if ((multiplicity2.GetValueOrDefault() != RelationshipMultiplicity.One ? 0 : (multiplicity2.HasValue ? 1 : 0)) != 0) { typeUsage = TypeUsage.Create(edmType, new FacetValues() { Nullable = (FacetValueContainer <bool?>) new bool?(false) }); } else { typeUsage = TypeUsage.Create(edmType); } Converter.InitializeAssociationEndMember(associationType, somNavigationProperty.ToEnd, endMemberType); Converter.InitializeAssociationEndMember(associationType, somNavigationProperty.FromEnd, declaringEntityType); NavigationProperty navigationProperty = new NavigationProperty(somNavigationProperty.Name, typeUsage); navigationProperty.RelationshipType = (RelationshipType)associationType; navigationProperty.ToEndMember = (RelationshipEndMember)associationType.Members[somNavigationProperty.ToEnd.Name]; navigationProperty.FromEndMember = (RelationshipEndMember)associationType.Members[somNavigationProperty.FromEnd.Name]; if (somNavigationProperty.Documentation != null) { navigationProperty.Documentation = Converter.ConvertToDocumentation(somNavigationProperty.Documentation); } Converter.AddOtherContent((SchemaElement)somNavigationProperty, (MetadataItem)navigationProperty); return(navigationProperty); }
public bool TryGetEnd(string roleName, out IRelationshipEnd end) { return(_ends.TryGetEnd(roleName, out end)); }
protected abstract void AddEnd(IRelationshipEnd relationshipEnd, EntityContainerEntitySet entitySet);
/// <summary> /// Create and add a EntityContainerEnd from the IRelationshipEnd provided /// </summary> /// <param name="relationshipEnd">The relationship end of the end to add.</param> /// <param name="entitySet">The entitySet to associate with the relationship end.</param> protected override void AddEnd(IRelationshipEnd relationshipEnd, EntityContainerEntitySet entitySet) { Debug.Assert(relationshipEnd != null); Debug.Assert(!_relationshipEnds.ContainsKey(relationshipEnd.Name)); // we expect set to be null sometimes var end = new EntityContainerAssociationSetEnd(this); end.Role = relationshipEnd.Name; end.RelationshipEnd = relationshipEnd; end.EntitySet = entitySet; if (end.EntitySet != null) { _relationshipEnds.Add(end.Role, end); } }
/// <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, 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 var relationshipEnd = end as RelationshipEnd; if (relationshipEnd != null && (relationshipEnd.Documentation != null)) { associationEnd.Documentation = ConvertToDocumentation(relationshipEnd.Documentation); } return associationEnd; }
internal override void Validate() { base.Validate(); this._principalRole.Validate(); this._dependentRole.Validate(); if (!ReferentialConstraint.ReadyForFurtherValidation(this._principalRole) || !ReferentialConstraint.ReadyForFurtherValidation(this._dependentRole)) { return; } IRelationshipEnd end1 = this._principalRole.End; IRelationshipEnd end2 = this._dependentRole.End; if (this._principalRole.Name == this._dependentRole.Name) { this.AddError(ErrorCode.SameRoleReferredInReferentialConstraint, EdmSchemaErrorSeverity.Error, (object)Strings.SameRoleReferredInReferentialConstraint((object)this.ParentElement.Name)); } bool isKeyProperty1; bool areAllPropertiesNullable1; bool isAnyPropertyNullable1; bool isSubsetOfKeyProperties1; ReferentialConstraint.IsKeyProperty(this._dependentRole, end2.Type, out isKeyProperty1, out areAllPropertiesNullable1, out isAnyPropertyNullable1, out isSubsetOfKeyProperties1); bool isKeyProperty2; bool areAllPropertiesNullable2; bool isAnyPropertyNullable2; bool isSubsetOfKeyProperties2; ReferentialConstraint.IsKeyProperty(this._principalRole, end1.Type, out isKeyProperty2, out areAllPropertiesNullable2, out isAnyPropertyNullable2, out isSubsetOfKeyProperties2); if (!isKeyProperty2) { this.AddError(ErrorCode.InvalidPropertyInRelationshipConstraint, EdmSchemaErrorSeverity.Error, (object)Strings.InvalidFromPropertyInRelationshipConstraint((object)this.PrincipalRole.Name, (object)end1.Type.FQName, (object)this.ParentElement.FQName)); } else { bool flag = this.Schema.SchemaVersion <= 1.1; RelationshipMultiplicity relationshipMultiplicity1 = (flag ? (areAllPropertiesNullable2 ? 1 : 0) : (isAnyPropertyNullable2 ? 1 : 0)) != 0 ? RelationshipMultiplicity.ZeroOrOne : RelationshipMultiplicity.One; RelationshipMultiplicity relationshipMultiplicity2 = (flag ? (areAllPropertiesNullable1 ? 1 : 0) : (isAnyPropertyNullable1 ? 1 : 0)) != 0 ? RelationshipMultiplicity.ZeroOrOne : RelationshipMultiplicity.Many; IRelationshipEnd relationshipEnd1 = end1; RelationshipMultiplicity?multiplicity1 = end1.Multiplicity; RelationshipMultiplicity?nullable1 = new RelationshipMultiplicity?(multiplicity1.HasValue ? multiplicity1.GetValueOrDefault() : relationshipMultiplicity1); relationshipEnd1.Multiplicity = nullable1; IRelationshipEnd relationshipEnd2 = end2; RelationshipMultiplicity?multiplicity2 = end2.Multiplicity; RelationshipMultiplicity?nullable2 = new RelationshipMultiplicity?(multiplicity2.HasValue ? multiplicity2.GetValueOrDefault() : relationshipMultiplicity2); relationshipEnd2.Multiplicity = nullable2; RelationshipMultiplicity?multiplicity3 = end1.Multiplicity; if ((multiplicity3.GetValueOrDefault() != RelationshipMultiplicity.Many ? 0 : (multiplicity3.HasValue ? 1 : 0)) != 0) { this.AddError(ErrorCode.InvalidMultiplicityInRoleInRelationshipConstraint, EdmSchemaErrorSeverity.Error, (object)Strings.InvalidMultiplicityFromRoleUpperBoundMustBeOne((object)this._principalRole.Name, (object)this.ParentElement.Name)); } else { if (areAllPropertiesNullable1) { RelationshipMultiplicity?multiplicity4 = end1.Multiplicity; if ((multiplicity4.GetValueOrDefault() != RelationshipMultiplicity.One ? 0 : (multiplicity4.HasValue ? 1 : 0)) != 0) { this.AddError(ErrorCode.InvalidMultiplicityInRoleInRelationshipConstraint, EdmSchemaErrorSeverity.Error, (object)Strings.InvalidMultiplicityFromRoleToPropertyNullableV1((object)this._principalRole.Name, (object)this.ParentElement.Name)); goto label_13; } } if (flag && !areAllPropertiesNullable1 || !flag && !isAnyPropertyNullable1) { RelationshipMultiplicity?multiplicity4 = end1.Multiplicity; if ((multiplicity4.GetValueOrDefault() != RelationshipMultiplicity.One ? 1 : (!multiplicity4.HasValue ? 1 : 0)) != 0) { this.AddError(ErrorCode.InvalidMultiplicityInRoleInRelationshipConstraint, EdmSchemaErrorSeverity.Error, !flag ? (object)Strings.InvalidMultiplicityFromRoleToPropertyNonNullableV2((object)this._principalRole.Name, (object)this.ParentElement.Name) : (object)Strings.InvalidMultiplicityFromRoleToPropertyNonNullableV1((object)this._principalRole.Name, (object)this.ParentElement.Name)); } } } label_13: RelationshipMultiplicity? multiplicity5 = end2.Multiplicity; if ((multiplicity5.GetValueOrDefault() != RelationshipMultiplicity.One ? 0 : (multiplicity5.HasValue ? 1 : 0)) != 0 && this.Schema.DataModel == SchemaDataModelOption.ProviderDataModel) { this.AddError(ErrorCode.InvalidMultiplicityInRoleInRelationshipConstraint, EdmSchemaErrorSeverity.Error, (object)Strings.InvalidMultiplicityToRoleLowerBoundMustBeZero((object)this._dependentRole.Name, (object)this.ParentElement.Name)); } if (!isSubsetOfKeyProperties1 && !this.ParentElement.IsForeignKey && this.Schema.DataModel == SchemaDataModelOption.EntityDataModel) { this.AddError(ErrorCode.InvalidPropertyInRelationshipConstraint, EdmSchemaErrorSeverity.Error, (object)Strings.InvalidToPropertyInRelationshipConstraint((object)this.DependentRole.Name, (object)end2.Type.FQName, (object)this.ParentElement.FQName)); } if (isKeyProperty1) { RelationshipMultiplicity?multiplicity4 = end2.Multiplicity; if ((multiplicity4.GetValueOrDefault() != RelationshipMultiplicity.Many ? 0 : (multiplicity4.HasValue ? 1 : 0)) != 0) { this.AddError(ErrorCode.InvalidMultiplicityInRoleInRelationshipConstraint, EdmSchemaErrorSeverity.Error, (object)Strings.InvalidMultiplicityToRoleUpperBoundMustBeOne((object)end2.Name, (object)this.ParentElement.Name)); } } else { RelationshipMultiplicity?multiplicity4 = end2.Multiplicity; if ((multiplicity4.GetValueOrDefault() != RelationshipMultiplicity.Many ? 1 : (!multiplicity4.HasValue ? 1 : 0)) != 0) { this.AddError(ErrorCode.InvalidMultiplicityInRoleInRelationshipConstraint, EdmSchemaErrorSeverity.Error, (object)Strings.InvalidMultiplicityToRoleUpperBoundMustBeMany((object)end2.Name, (object)this.ParentElement.Name)); } } if (this._dependentRole.RoleProperties.Count != this._principalRole.RoleProperties.Count) { this.AddError(ErrorCode.MismatchNumberOfPropertiesInRelationshipConstraint, EdmSchemaErrorSeverity.Error, (object)Strings.MismatchNumberOfPropertiesinRelationshipConstraint); } else { for (int index = 0; index < this._dependentRole.RoleProperties.Count; ++index) { if (this._dependentRole.RoleProperties[index].Property.Type != this._principalRole.RoleProperties[index].Property.Type) { this.AddError(ErrorCode.TypeMismatchRelationshipConstraint, EdmSchemaErrorSeverity.Error, (object)Strings.TypeMismatchRelationshipConstraint((object)this._dependentRole.RoleProperties[index].Name, (object)this._dependentRole.End.Type.Identity, (object)this._principalRole.RoleProperties[index].Name, (object)this._principalRole.End.Type.Identity, (object)this.ParentElement.Name)); } } } } }
public bool TryGetEnd( string roleName, out IRelationshipEnd end ) { return _ends.TryGetEnd( roleName, out end ); }
public abstract IRelationship CreateRelationship(IRelationshipEnd rel1, IRelationshipEnd rel2);
// <summary> // For the given relationship end, find the EntityContainer Property that will work for the extent // </summary> // <param name="relationshipEnd"> The relationship end of the RelationshipSet that needs and extent </param> // <returns> Null is none could be found, or the EntityContainerProperty that is the valid extent </returns> private EntityContainerEntitySet InferEntitySet(IRelationshipEnd relationshipEnd) { DebugCheck.NotNull(relationshipEnd); var possibleExtents = new List<EntityContainerEntitySet>(); foreach (var set in ParentElement.EntitySets) { if (relationshipEnd.Type.IsOfType(set.EntityType)) { possibleExtents.Add(set); } } if (possibleExtents.Count == 1) { return possibleExtents[0]; } else if (possibleExtents.Count == 0) { // no matchs AddError( ErrorCode.MissingExtentEntityContainerEnd, EdmSchemaErrorSeverity.Error, Strings.MissingEntityContainerEnd(relationshipEnd.Name, FQName)); } else { // abmigous AddError( ErrorCode.AmbiguousEntityContainerEnd, EdmSchemaErrorSeverity.Error, Strings.AmbiguousEntityContainerEnd(relationshipEnd.Name, FQName)); } return null; }
/// <summary> /// Validate this referential constraint /// </summary> internal override void Validate() { base.Validate(); _principalRole.Validate(); _dependentRole.Validate(); if (ReadyForFurtherValidation(_principalRole) && ReadyForFurtherValidation(_dependentRole)) { // Validate the to end and from end of the referential constraint IRelationshipEnd principalRoleEnd = _principalRole.End; IRelationshipEnd dependentRoleEnd = _dependentRole.End; bool isPrinicipalRoleKeyProperty, isDependentRoleKeyProperty; bool areAllPrinicipalRolePropertiesNullable, areAllDependentRolePropertiesNullable; bool isDependentRolePropertiesSubsetofKeyProperties, isPrinicipalRolePropertiesSubsetofKeyProperties; bool isAnyPrinicipalRolePropertyNullable, isAnyDependentRolePropertyNullable; // Validate the role name to be different if (_principalRole.Name == _dependentRole.Name) { AddError(ErrorCode.SameRoleReferredInReferentialConstraint, EdmSchemaErrorSeverity.Error, System.Data.Entity.Strings.SameRoleReferredInReferentialConstraint(this.ParentElement.Name)); } // Resolve all the property in the ToProperty attribute. Also checks whether this is nullable or not and // whether the properties are the keys for the type in the ToRole IsKeyProperty(_dependentRole, dependentRoleEnd.Type, out isPrinicipalRoleKeyProperty, out areAllDependentRolePropertiesNullable, out isAnyDependentRolePropertyNullable, out isDependentRolePropertiesSubsetofKeyProperties); // Resolve all the property in the ToProperty attribute. Also checks whether this is nullable or not and // whether the properties are the keys for the type in the ToRole IsKeyProperty(_principalRole, principalRoleEnd.Type, out isDependentRoleKeyProperty, out areAllPrinicipalRolePropertiesNullable, out isAnyPrinicipalRolePropertyNullable, out isPrinicipalRolePropertiesSubsetofKeyProperties); Debug.Assert(_principalRole.RoleProperties.Count != 0, "There should be some ref properties in Principal Role"); Debug.Assert(_dependentRole.RoleProperties.Count != 0, "There should be some ref properties in Dependent Role"); // The properties in the PrincipalRole must be the key of the Entity type referred to by the principal role if (!isDependentRoleKeyProperty) { AddError(ErrorCode.InvalidPropertyInRelationshipConstraint, EdmSchemaErrorSeverity.Error, System.Data.Entity.Strings.InvalidFromPropertyInRelationshipConstraint( PrincipalRole.Name, principalRoleEnd.Type.FQName, this.ParentElement.FQName)); } else { bool v1Behavior = Schema.SchemaVersion <= XmlConstants.EdmVersionForV1_1; // Determine expected multiplicities RelationshipMultiplicity expectedPrincipalMultiplicity = (v1Behavior ? areAllPrinicipalRolePropertiesNullable : isAnyPrinicipalRolePropertyNullable) ? RelationshipMultiplicity.ZeroOrOne : RelationshipMultiplicity.One; RelationshipMultiplicity expectedDependentMultiplicity = (v1Behavior ? areAllDependentRolePropertiesNullable : isAnyDependentRolePropertyNullable) ? RelationshipMultiplicity.ZeroOrOne : RelationshipMultiplicity.Many; principalRoleEnd.Multiplicity = principalRoleEnd.Multiplicity ?? expectedPrincipalMultiplicity; dependentRoleEnd.Multiplicity = dependentRoleEnd.Multiplicity ?? expectedDependentMultiplicity; // Since the FromProperty must be the key of the FromRole, the FromRole cannot be '*' as multiplicity // Also the lower bound of multiplicity of FromRole can be zero if and only if all the properties in // ToProperties are nullable // for v2+ if (principalRoleEnd.Multiplicity == RelationshipMultiplicity.Many) { AddError(ErrorCode.InvalidMultiplicityInRoleInRelationshipConstraint, EdmSchemaErrorSeverity.Error, System.Data.Entity.Strings.InvalidMultiplicityFromRoleUpperBoundMustBeOne(_principalRole.Name, this.ParentElement.Name)); } else if (areAllDependentRolePropertiesNullable && principalRoleEnd.Multiplicity == RelationshipMultiplicity.One) { string message = System.Data.Entity.Strings.InvalidMultiplicityFromRoleToPropertyNullableV1(_principalRole.Name, this.ParentElement.Name); AddError(ErrorCode.InvalidMultiplicityInRoleInRelationshipConstraint, EdmSchemaErrorSeverity.Error, message); } else if (( (v1Behavior && !areAllDependentRolePropertiesNullable) || (!v1Behavior && !isAnyDependentRolePropertyNullable) ) && principalRoleEnd.Multiplicity != RelationshipMultiplicity.One) { string message; if (v1Behavior) { message = System.Data.Entity.Strings.InvalidMultiplicityFromRoleToPropertyNonNullableV1(_principalRole.Name, this.ParentElement.Name); } else { message = System.Data.Entity.Strings.InvalidMultiplicityFromRoleToPropertyNonNullableV2(_principalRole.Name, this.ParentElement.Name); } AddError(ErrorCode.InvalidMultiplicityInRoleInRelationshipConstraint, EdmSchemaErrorSeverity.Error, message); } // If the ToProperties form the key of the type in ToRole, then the upper bound of the multiplicity // of the ToRole must be '1'. The lower bound must always be zero since there can be entries in the from // column which are not related to child columns. if (dependentRoleEnd.Multiplicity == RelationshipMultiplicity.One && Schema.DataModel == SchemaDataModelOption.ProviderDataModel) { AddError(ErrorCode.InvalidMultiplicityInRoleInRelationshipConstraint, EdmSchemaErrorSeverity.Error, System.Data.Entity.Strings.InvalidMultiplicityToRoleLowerBoundMustBeZero(_dependentRole.Name, this.ParentElement.Name)); } // Need to constrain the dependent role in CSDL to Key properties if this is not a IsForeignKey // relationship. if ((!isDependentRolePropertiesSubsetofKeyProperties) && (!this.ParentElement.IsForeignKey) && (Schema.DataModel == SchemaDataModelOption.EntityDataModel)) { AddError(ErrorCode.InvalidPropertyInRelationshipConstraint, EdmSchemaErrorSeverity.Error, System.Data.Entity.Strings.InvalidToPropertyInRelationshipConstraint( DependentRole.Name, dependentRoleEnd.Type.FQName, this.ParentElement.FQName)); } // If the ToProperty is a key property, then the upper bound must be 1 i.e. every parent (from property) can // have exactly one child if (isPrinicipalRoleKeyProperty) { if (dependentRoleEnd.Multiplicity == RelationshipMultiplicity.Many) { AddError(ErrorCode.InvalidMultiplicityInRoleInRelationshipConstraint, EdmSchemaErrorSeverity.Error, System.Data.Entity.Strings.InvalidMultiplicityToRoleUpperBoundMustBeOne(dependentRoleEnd.Name, this.ParentElement.Name)); } } // if the ToProperty is not the key, then the upper bound must be many i.e every parent (from property) can // be related to many childs else if (dependentRoleEnd.Multiplicity != RelationshipMultiplicity.Many) { AddError(ErrorCode.InvalidMultiplicityInRoleInRelationshipConstraint, EdmSchemaErrorSeverity.Error, System.Data.Entity.Strings.InvalidMultiplicityToRoleUpperBoundMustBeMany(dependentRoleEnd.Name, this.ParentElement.Name)); } if (_dependentRole.RoleProperties.Count != _principalRole.RoleProperties.Count) { AddError(ErrorCode.MismatchNumberOfPropertiesInRelationshipConstraint, EdmSchemaErrorSeverity.Error, System.Data.Entity.Strings.MismatchNumberOfPropertiesinRelationshipConstraint); } else { for (int i = 0; i < _dependentRole.RoleProperties.Count; i++) { if (_dependentRole.RoleProperties[i].Property.Type != _principalRole.RoleProperties[i].Property.Type) { AddError(ErrorCode.TypeMismatchRelationshipConstaint, EdmSchemaErrorSeverity.Error, System.Data.Entity.Strings.TypeMismatchRelationshipConstaint( _dependentRole.RoleProperties[i].Name, _dependentRole.End.Type.Identity, _principalRole.RoleProperties[i].Name, _principalRole.End.Type.Identity, this.ParentElement.Name )); } } } } } }
/// <summary> /// For the given relationship end, find the EntityContainer Property that will work for the extent /// </summary> /// <param name="relationshipEnd">The relationship end of the RelationshipSet that needs and extent</param> /// <returns>Null is none could be found, or the EntityContainerProperty that is the valid extent</returns> private EntityContainerEntitySet InferEntitySet( IRelationshipEnd relationshipEnd ) { Debug.Assert(relationshipEnd != null, "relationshipEnd parameter is null"); List<EntityContainerEntitySet> possibleExtents = new List<EntityContainerEntitySet>(); foreach ( EntityContainerEntitySet set in ParentElement.EntitySets ) { if ( relationshipEnd.Type.IsOfType( set.EntityType ) ) { possibleExtents.Add( set ); } } if ( possibleExtents.Count == 1 ) { return possibleExtents[0]; } else if ( possibleExtents.Count == 0 ) { // no matchs AddError( ErrorCode.MissingExtentEntityContainerEnd, EdmSchemaErrorSeverity.Error, System.Data.Entity.Strings.MissingEntityContainerEnd(relationshipEnd.Name, FQName ) ); } else { // abmigous AddError( ErrorCode.AmbiguousEntityContainerEnd, EdmSchemaErrorSeverity.Error, System.Data.Entity.Strings.AmbiguousEntityContainerEnd(relationshipEnd.Name, FQName ) ); } return null; }