internal override void Configure( EdmAssociationType associationType, EdmAssociationEnd dependentEnd, EntityTypeConfiguration entityTypeConfiguration) { //Contract.Requires(associationType != null); //Contract.Requires(dependentEnd != null); //Contract.Requires(entityTypeConfiguration != null); }
public static EdmAssociationEnd GetOtherEnd( this EdmAssociationType associationType, EdmAssociationEnd associationEnd) { Contract.Requires(associationType != null); Contract.Requires(associationEnd != null); return associationEnd == associationType.SourceEnd ? associationType.TargetEnd : associationType.SourceEnd; }
private void ConfigureDeleteAction(EdmAssociationEnd principalEnd) { //Contract.Requires(principalEnd != null); if (DeleteAction != null) { principalEnd.DeleteAction = DeleteAction.Value; } }
private void ConfigureConstraint( EdmAssociationType associationType, EdmAssociationEnd dependentEnd, EntityTypeConfiguration entityTypeConfiguration) { //Contract.Requires(associationType != null); //Contract.Requires(dependentEnd != null); //Contract.Requires(entityTypeConfiguration != null); if (_constraint != null) { _constraint.Configure(associationType, dependentEnd, entityTypeConfiguration); var associationConstraint = associationType.Constraint; if ((associationConstraint != null) && associationConstraint.DependentProperties .SequenceEqual(associationConstraint.DependentEnd.EntityType.DeclaredKeyProperties)) { // The dependent FK is also the PK. We need to adjust the multiplicity // when it has not been explicity configured because the default is *:0..1 if ((_inverseEndKind == null) && associationType.SourceEnd.IsMany()) { associationType.SourceEnd.EndKind = EdmAssociationEndKind.Optional; associationType.TargetEnd.EndKind = EdmAssociationEndKind.Required; } } } }
public void IsMany_should_return_true_when_end_kind_is_many() { var associationEnd = new EdmAssociationEnd { EndKind = EdmAssociationEndKind.Many }; Assert.True(associationEnd.IsMany()); }
public void IsRequired_should_return_true_when_end_kind_is_required() { var associationEnd = new EdmAssociationEnd { EndKind = EdmAssociationEndKind.Required }; Assert.True(associationEnd.IsRequired()); }
public void IsOptional_should_return_true_when_end_kind_is_optional() { var associationEnd = new EdmAssociationEnd { EndKind = EdmAssociationEndKind.Optional }; Assert.True(associationEnd.IsOptional()); }
internal override void Configure( EdmAssociationType associationType, EdmAssociationEnd dependentEnd, EntityTypeConfiguration entityTypeConfiguration) { associationType.MarkIndependent(); }
internal override void Configure( EdmAssociationType associationType, EdmAssociationEnd dependentEnd, EntityTypeConfiguration entityTypeConfiguration) { if (!_dependentProperties.Any()) { return; } var associationConstraint = new EdmAssociationConstraint { DependentEnd = dependentEnd }; var dependentProperties = _dependentProperties.AsEnumerable(); if (!IsFullySpecified) { var foreignKeys = from p in _dependentProperties select new { PropertyInfo = p, entityTypeConfiguration.Property(new PropertyPath(p)).ColumnOrder }; if ((_dependentProperties.Count > 1) && foreignKeys.Any(p => !p.ColumnOrder.HasValue)) { var dependentKeys = dependentEnd.EntityType.DeclaredKeyProperties; if ((dependentKeys.Count == _dependentProperties.Count) && foreignKeys.All(fk => dependentKeys.Any(p => p.GetClrPropertyInfo().IsSameAs(fk.PropertyInfo)))) { // The FK and PK sets are equal, we know the order dependentProperties = dependentKeys.Select(p => p.GetClrPropertyInfo()); } else { throw Error.ForeignKeyAttributeConvention_OrderRequired(entityTypeConfiguration.ClrType); } } else { dependentProperties = foreignKeys.OrderBy(p => p.ColumnOrder).Select(p => p.PropertyInfo); } } foreach (var dependentProperty in dependentProperties) { var property = associationConstraint .DependentEnd .EntityType .GetDeclaredPrimitiveProperty(dependentProperty); if (property == null) { throw Error.ForeignKeyPropertyNotFound( dependentProperty.Name, associationConstraint.DependentEnd.EntityType.Name); } associationConstraint.DependentProperties.Add(property); } associationType.Constraint = associationConstraint; var principalEnd = associationType.GetOtherEnd(dependentEnd); if (principalEnd.IsRequired()) { associationType.Constraint.DependentProperties.Each(p => p.PropertyType.IsNullable = false); } }
/// <summary> /// Attempt to determine the principal and dependent ends of this association. /// /// The following table illustrates the solution space. /// /// Source | Target || Prin | Dep | /// -------|--------||-------|-------| /// 1 | 1 || - | - | /// 1 | 0..1 || Sr | Ta | /// 1 | * || Sr | Ta | /// 0..1 | 1 || Ta | Sr | /// 0..1 | 0..1 || - | - | /// 0..1 | * || Sr | Ta | /// * | 1 || Ta | Sr | /// * | 0..1 || Ta | Sr | /// * | * || - | - | /// </summary> public static bool TryGuessPrincipalAndDependentEnds( this EdmAssociationType associationType, out EdmAssociationEnd principalEnd, out EdmAssociationEnd dependentEnd) { Contract.Requires(associationType != null); Contract.Assert(associationType.SourceEnd != null); Contract.Assert(associationType.TargetEnd != null); principalEnd = dependentEnd = null; var sourceEnd = associationType.SourceEnd; var targetEnd = associationType.TargetEnd; if (sourceEnd.EndKind != targetEnd.EndKind) { principalEnd = (sourceEnd.IsRequired() || (sourceEnd.IsOptional() && targetEnd.IsMany())) ? sourceEnd : targetEnd; dependentEnd = (principalEnd == sourceEnd) ? targetEnd : sourceEnd; } return (principalEnd != null); }
internal abstract void Configure( EdmAssociationType associationType, EdmAssociationEnd dependentEnd, EntityTypeConfiguration entityTypeConfiguration);
private void GenerateIndependentForeignKeyConstraint( DbDatabaseMapping databaseMapping, EdmEntityType principalEntityType, EdmEntityType dependentEntityType, DbTableMetadata dependentTable, DbAssociationSetMapping associationSetMapping, DbAssociationEndMapping associationEndMapping, string name, EdmAssociationEnd principalEnd, bool isPrimaryKeyColumn = false) { //Contract.Requires(databaseMapping != null); //Contract.Requires(principalEntityType != null); //Contract.Requires(dependentTable != null); //Contract.Requires(associationEndMapping != null); //Contract.Requires(!string.IsNullOrWhiteSpace(name)); var principalTable = GetEntityTypeMappingInHierarchy(databaseMapping, principalEntityType) .TypeMappingFragments .Single() .Table; var foreignKeyConstraint = new DbForeignKeyConstraintMetadata { Name = name, PrincipalTable = principalTable, DeleteAction = associationEndMapping.AssociationEnd.DeleteAction.HasValue ? (DbOperationAction) associationEndMapping.AssociationEnd.DeleteAction. Value : DbOperationAction.None }; var principalNavigationProperty = databaseMapping.Model.GetEntityTypes() .SelectMany(e => e.DeclaredNavigationProperties) .SingleOrDefault(n => n.ResultEnd == principalEnd); GenerateIndependentForeignKeyColumns( principalEntityType, dependentEntityType, associationSetMapping, associationEndMapping, dependentTable, foreignKeyConstraint, isPrimaryKeyColumn, principalNavigationProperty); dependentTable.ForeignKeyConstraints.Add(foreignKeyConstraint); }
private static DbAssociationSetMapping GenerateAssociationSetMapping( EdmAssociationType associationType, DbDatabaseMapping databaseMapping, EdmAssociationEnd principalEnd, EdmAssociationEnd dependentEnd, DbTableMetadata dependentTable) { //Contract.Requires(associationType != null); //Contract.Requires(databaseMapping != null); //Contract.Requires(principalEnd != null); //Contract.Requires(dependentEnd != null); //Contract.Requires(dependentTable != null); var associationSetMapping = databaseMapping.AddAssociationSetMapping( databaseMapping.Model.GetAssociationSet(associationType)); associationSetMapping.Table = dependentTable; associationSetMapping.SourceEndMapping.AssociationEnd = principalEnd; associationSetMapping.TargetEndMapping.AssociationEnd = dependentEnd; return associationSetMapping; }