You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
My db context describes the nature of the relationship, basically a Person to Contact is 1-1, and Contact to Entity is 1-Many. An Entity is required to have a contact.
I would expect this to model a Contact table and an Entity table with a discriminator and a ContactId column, and populate Contact.Person and Contact.Entities if Included (with a shared object between those two properties if a Person was associated with the Contact).
However, running the reproduction code results in an InvalidOperationException instead:
System.InvalidOperationException: 'Cannot create a relationship between 'Contact.Person' and 'Person.Contact' because a relationship already exists between 'Contact.Entities' and 'Entity.Contact'. Navigation properties can only participate in a single relationship. If you want to override an existing relationship call 'Ignore' on the navigation 'Person.Contact' first in 'OnModelCreating'.'
I was able to hack around this restriction by mapping one of the relationships to a second ContactId column on Entity and then setting up a database trigger that makes the columns mirror each other, updating each other if one is updated.
CREATE TRIGGER [dbo].[TR_ContactId_Mirror] ON [dbo].[Entity]
AFTER INSERT, UPDATEASBEGINSET NOCOUNT ON;
IF (UPDATE([ContactId]))
BEGINUPDATE E
SET [ContactId_Mirror] = inserted.[ContactId]
FROM [dbo].[Entity] E
INNER JOIN inserted ON E.[Id] = inserted.[Id]
END
ELSE IF (UPDATE([ContactId_Mirror]))
BEGINUPDATE E
SET [ContactId] = inserted.[ContactId_Mirror]
FROM [dbo].[Entity] E
INNER JOIN inserted ON E.[Id] = inserted.[Id]
END
END
I think it goes without saying that this is very much not an ideal workaround, but I think it demonstrates that what I'm trying to do here is at the very least a valid relational database configuration.
Did I configure something incorrectly, or is this just an unsupported use of EF Core I'm trying to accomplish here?
EF Core version:
Database provider: Microsoft.EntityFrameworkCore.SqlServer
Target framework: .NET 5.0
Operating system: Windows 10
IDE: Visual Studio 2019 16.10.2
Error Stack Trace
at Microsoft.EntityFrameworkCore.Metadata.Internal.InternalForeignKeyBuilder.ThrowForConflictingNavigation(IForeignKey foreignKey, IEntityType principalEntityType, IEntityType dependentEntityType, String navigationToDependent, String navigationToPrincipal)
at Microsoft.EntityFrameworkCore.Metadata.Internal.InternalForeignKeyBuilder.GetOrCreateRelationshipBuilder(EntityType principalEntityType, EntityType dependentEntityType, Nullable`1 navigationToPrincipal, Nullable`1 navigationToDependent, IReadOnlyList`1 dependentProperties, IReadOnlyList`1 oldNameDependentProperties, IReadOnlyList`1 principalProperties, Nullable`1 isRequired, Boolean removeCurrent, Nullable`1 principalEndConfigurationSource, Nullable`1 configurationSource, Nullable`1& existingRelationshipInverted)
at Microsoft.EntityFrameworkCore.Metadata.Internal.InternalForeignKeyBuilder.ReplaceForeignKey(InternalEntityTypeBuilder principalEntityTypeBuilder, InternalEntityTypeBuilder dependentEntityTypeBuilder, Nullable`1 navigationToPrincipal, Nullable`1 navigationToDependent, IReadOnlyList`1 dependentProperties, IReadOnlyList`1 oldNameDependentProperties, IReadOnlyList`1 principalProperties, Nullable`1 isUnique, Nullable`1 isRequired, Nullable`1 isRequiredDependent, Nullable`1 isOwnership, Nullable`1 deleteBehavior, Boolean removeCurrent, Boolean oldRelationshipInverted, Nullable`1 principalEndConfigurationSource, ConfigurationSource configurationSource)
at Microsoft.EntityFrameworkCore.Metadata.Internal.InternalForeignKeyBuilder.ReplaceForeignKey(ConfigurationSource configurationSource, InternalEntityTypeBuilder principalEntityTypeBuilder, InternalEntityTypeBuilder dependentEntityTypeBuilder, Nullable`1 navigationToPrincipal, Nullable`1 navigationToDependent, IReadOnlyList`1 dependentProperties, IReadOnlyList`1 oldNameDependentProperties, IReadOnlyList`1 principalProperties, Nullable`1 isUnique, Nullable`1 isRequired, Nullable`1 isRequiredDependent, Nullable`1 isOwnership, Nullable`1 deleteBehavior, Boolean removeCurrent, Nullable`1 principalEndConfigurationSource, Boolean oldRelationshipInverted)
at Microsoft.EntityFrameworkCore.Metadata.Internal.InternalForeignKeyBuilder.HasNavigations(Nullable`1 navigationToPrincipal, Nullable`1 navigationToDependent, EntityType principalEntityType, EntityType dependentEntityType, ConfigurationSource configurationSource)
at Microsoft.EntityFrameworkCore.Metadata.Internal.InternalForeignKeyBuilder.HasNavigations(MemberInfo navigationToPrincipal, MemberInfo navigationToDependent, EntityType principalEntityType, EntityType dependentEntityType, ConfigurationSource configurationSource)
at Microsoft.EntityFrameworkCore.Metadata.Builders.ReferenceNavigationBuilder.WithOneBuilder(MemberIdentity reference)
at Microsoft.EntityFrameworkCore.Metadata.Builders.ReferenceNavigationBuilder.WithOneBuilder(MemberInfo navigationMemberInfo)
at Microsoft.EntityFrameworkCore.Metadata.Builders.ReferenceNavigationBuilder`2.WithOne(Expression`1 navigationExpression)
at TBHRepro.Data.ApplicationDbContext.<>c.<OnModelCreating>b__13_0(EntityTypeBuilder`1 eb) in C:\Users\Jason\source\repos\TPHRepro\TPHRepro\Data\ApplicationDbContext.cs:line 29
at Microsoft.EntityFrameworkCore.ModelBuilder.Entity[TEntity](Action`1 buildAction)
at TBHRepro.Data.ApplicationDbContext.OnModelCreating(ModelBuilder modelBuilder) in C:\Users\Jason\source\repos\TPHRepro\TPHRepro\Data\ApplicationDbContext.cs:line 22
at Microsoft.EntityFrameworkCore.Infrastructure.ModelCustomizer.Customize(ModelBuilder modelBuilder, DbContext context)
at Microsoft.EntityFrameworkCore.Infrastructure.ModelSource.CreateModel(DbContext context, IConventionSetBuilder conventionSetBuilder, ModelDependencies modelDependencies)
at Microsoft.EntityFrameworkCore.Infrastructure.ModelSource.GetModel(DbContext context, IConventionSetBuilder conventionSetBuilder, ModelDependencies modelDependencies)
at Microsoft.EntityFrameworkCore.Internal.DbContextServices.CreateModel()
at Microsoft.EntityFrameworkCore.Internal.DbContextServices.get_Model()
at Microsoft.EntityFrameworkCore.Infrastructure.EntityFrameworkServicesBuilder.<>c.<TryAddCoreServices>b__7_3(IServiceProvider p)
at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteRuntimeResolver.VisitFactory(FactoryCallSite factoryCallSite, RuntimeResolverContext context)
at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteVisitor`2.VisitCallSiteMain(ServiceCallSite callSite, TArgument argument)
at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteRuntimeResolver.VisitCache(ServiceCallSite callSite, RuntimeResolverContext context, ServiceProviderEngineScope serviceProviderEngine, RuntimeResolverLock lockType)
at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteRuntimeResolver.VisitScopeCache(ServiceCallSite singletonCallSite, RuntimeResolverContext context)
at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteVisitor`2.VisitCallSite(ServiceCallSite callSite, TArgument argument)
at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteRuntimeResolver.VisitConstructor(ConstructorCallSite constructorCallSite, RuntimeResolverContext context)
at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteVisitor`2.VisitCallSiteMain(ServiceCallSite callSite, TArgument argument)
at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteRuntimeResolver.VisitCache(ServiceCallSite callSite, RuntimeResolverContext context, ServiceProviderEngineScope serviceProviderEngine, RuntimeResolverLock lockType)
at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteRuntimeResolver.VisitScopeCache(ServiceCallSite singletonCallSite, RuntimeResolverContext context)
at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteVisitor`2.VisitCallSite(ServiceCallSite callSite, TArgument argument)
at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteRuntimeResolver.Resolve(ServiceCallSite callSite, ServiceProviderEngineScope scope)
at Microsoft.Extensions.DependencyInjection.ServiceLookup.DynamicServiceProviderEngine.<>c__DisplayClass1_0.<RealizeService>b__0(ServiceProviderEngineScope scope)
at Microsoft.Extensions.DependencyInjection.ServiceLookup.ServiceProviderEngine.GetService(Type serviceType, ServiceProviderEngineScope serviceProviderEngineScope)
at Microsoft.Extensions.DependencyInjection.ServiceLookup.ServiceProviderEngineScope.GetService(Type serviceType)
at Microsoft.Extensions.DependencyInjection.ServiceProviderServiceExtensions.GetRequiredService(IServiceProvider provider, Type serviceType)
at Microsoft.Extensions.DependencyInjection.ServiceProviderServiceExtensions.GetRequiredService[T](IServiceProvider provider)
at Microsoft.EntityFrameworkCore.DbContext.get_DbContextDependencies()
at Microsoft.EntityFrameworkCore.DbContext.get_InternalServiceProvider()
at Microsoft.EntityFrameworkCore.DbContext.get_DbContextDependencies()
at Microsoft.EntityFrameworkCore.DbContext.get_Model()
at Microsoft.EntityFrameworkCore.Internal.InternalDbSet`1.get_EntityType()
at Microsoft.EntityFrameworkCore.Internal.InternalDbSet`1.CheckState()
at Microsoft.EntityFrameworkCore.Internal.InternalDbSet`1.get_EntityQueryable()
at Microsoft.EntityFrameworkCore.Internal.InternalDbSet`1.System.Linq.IQueryable.get_Provider()
at System.Linq.Queryable.FirstOrDefault[TSource](IQueryable`1 source)
at TBHRepro.Pages.IndexModel.OnGet() in TPHRepro\TPHRepro\Pages\Index.cshtml.cs:line 25
at Microsoft.AspNetCore.Mvc.RazorPages.Infrastructure.ExecutorFactory.VoidHandlerMethod.Execute(Object receiver, Object[] arguments)
at Microsoft.AspNetCore.Mvc.RazorPages.Infrastructure.PageActionInvoker.<InvokeHandlerMethodAsync>d__30.MoveNext()
The text was updated successfully, but these errors were encountered:
I'm using TPH in my application and trying to get multiple navigations on various entities in the hierarchy. I've created a repo to demonstrate the issue I'm facing.
I have 4 entities in my context:
Entity
Person
Business
Contact
My db context describes the nature of the relationship, basically a Person to Contact is 1-1, and Contact to Entity is 1-Many. An Entity is required to have a contact.
AppliocationDbContext
I would expect this to model a Contact table and an
Entity
table with a discriminator and a ContactId column, and populateContact.Person
andContact.Entities
if Included (with a shared object between those two properties if a Person was associated with the Contact).However, running the reproduction code results in an
InvalidOperationException
instead:I was able to hack around this restriction by mapping one of the relationships to a second ContactId column on Entity and then setting up a database trigger that makes the columns mirror each other, updating each other if one is updated.
I think it goes without saying that this is very much not an ideal workaround, but I think it demonstrates that what I'm trying to do here is at the very least a valid relational database configuration.
Did I configure something incorrectly, or is this just an unsupported use of EF Core I'm trying to accomplish here?
EF Core version:
Database provider: Microsoft.EntityFrameworkCore.SqlServer
Target framework: .NET 5.0
Operating system: Windows 10
IDE: Visual Studio 2019 16.10.2
Error Stack Trace
The text was updated successfully, but these errors were encountered: