我不确定发生了什么变化,但是现在我收到一条错误消息:“ 实体类型'GroupSubscriber'需要定义主键。”但是,我确实有一个复合键在EF配置中定义,我已确认确实执行。此外,我能够创建迁移并更新数据库,这将导致数据库具有复合主键。
Web api项目可以成功构建并且可以运行,但是当我调用任何路由时,即使根本没有访问此对象,也会出现此错误。
正如我提到的,这一切都很好,但是似乎当我为不相关的东西调用路线时,它给了我这个错误。奇怪的是,.HasConversion曾经可以正常工作,但现在也出现了其他错误。我已通过变通办法克服了这些错误,但由于无法更改数据库架构,因此无法对复合键进行变通。
如果您有兴趣,这是我收到的完整错误:
{
"error": [
"The entity type 'GroupSubscriber' requires a primary key to be defined."
],
"stackTrace": " at Microsoft.EntityFrameworkCore.Infrastructure.ModelValidator.ValidateNonNullPrimaryKeys(IModel model)\r\n at Microsoft.EntityFrameworkCore.Infrastructure.ModelValidator.Validate(IModel model)\r\n at Microsoft.EntityFrameworkCore.Infrastructure.RelationalModelValidator.Validate(IModel model)\r\n at Microsoft.EntityFrameworkCore.Internal.SqlServerModelValidator.Validate(IModel model)\r\n at Microsoft.EntityFrameworkCore.Metadata.Conventions.Internal.ValidatingConvention.Apply(InternalModelBuilder modelBuilder)\r\n at Microsoft.EntityFrameworkCore.Metadata.Conventions.Internal.ConventionDispatcher.ImmediateConventionScope.OnModelBuilt(InternalModelBuilder modelBuilder)\r\n at Microsoft.EntityFrameworkCore.Metadata.Conventions.Internal.ConventionDispatcher.OnModelBuilt(InternalModelBuilder modelBuilder)\r\n at Microsoft.EntityFrameworkCore.Metadata.Internal.Model.Validate()\r\n at Microsoft.EntityFrameworkCore.ModelBuilder.FinalizeModel()\r\n at Microsoft.EntityFrameworkCore.Infrastructure.ModelSource.CreateModel(DbContext context, IConventionSetBuilder conventionSetBuilder, IModelValidator validator)\r\n at Microsoft.EntityFrameworkCore.Infrastructure.ModelSource.<>c__DisplayClass5_0.<GetModel>b__1()\r\n at System.Lazy`1.ViaFactory(LazyThreadSafetyMode mode)\r\n at System.Lazy`1.ExecutionAndPublication(LazyHelper executionAndPublication, Boolean useDefaultConstructor)\r\n at System.Lazy`1.CreateValue()\r\n at Microsoft.EntityFrameworkCore.Infrastructure.ModelSource.GetModel(DbContext context, IConventionSetBuilder conventionSetBuilder, IModelValidator validator)\r\n at Microsoft.EntityFrameworkCore.Internal.DbContextServices.CreateModel()\r\n at Microsoft.EntityFrameworkCore.Internal.DbContextServices.get_Model()\r\n at Microsoft.EntityFrameworkCore.Infrastructure.EntityFrameworkServicesBuilder.<>c.<TryAddCoreServices>b__7_2(IServiceProvider p)\r\n at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteRuntimeResolver.VisitFactory(FactoryCallSite factoryCallSite, ServiceProviderEngineScope scope)\r\n at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteVisitor`2.VisitCallSite(IServiceCallSite callSite, TArgument argument)\r\n at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteRuntimeResolver.VisitScoped(ScopedCallSite scopedCallSite, ServiceProviderEngineScope scope)\r\n at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteVisitor`2.VisitCallSite(IServiceCallSite callSite, TArgument argument)\r\n at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteRuntimeResolver.VisitConstructor(ConstructorCallSite constructorCallSite, ServiceProviderEngineScope scope)\r\n at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteVisitor`2.VisitCallSite(IServiceCallSite callSite, TArgument argument)\r\n at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteRuntimeResolver.VisitScoped(ScopedCallSite scopedCallSite, ServiceProviderEngineScope scope)\r\n at Microsoft.Extensions.DependencyInjection.ServiceLookup.CallSiteVisitor`2.VisitCallSite(IServiceCallSite callSite, TArgument argument)\r\n at Microsoft.Extensions.DependencyInjection.ServiceLookup.DynamicServiceProviderEngine.<>c__DisplayClass1_0.<RealizeService>b__0(ServiceProviderEngineScope scope)\r\n at Microsoft.Extensions.DependencyInjection.ServiceLookup.ServiceProviderEngine.GetService(Type serviceType, ServiceProviderEngineScope serviceProviderEngineScope)\r\n at Microsoft.Extensions.DependencyInjection.ServiceLookup.ServiceProviderEngineScope.GetService(Type serviceType)\r\n at Microsoft.Extensions.DependencyInjection.ServiceProviderServiceExtensions.GetRequiredService(IServiceProvider provider, Type serviceType)\r\n at Microsoft.Extensions.DependencyInjection.ServiceProviderServiceExtensions.GetRequiredService[T](IServiceProvider provider)\r\n at Microsoft.EntityFrameworkCore.DbContext.get_DbContextDependencies()\r\n at Microsoft.EntityFrameworkCore.DbContext.get_InternalServiceProvider()\r\n at Microsoft.EntityFrameworkCore.DbContext.get_DbContextDependencies()\r\n at Microsoft.EntityFrameworkCore.DbContext.get_Model()\r\n at Microsoft.EntityFrameworkCore.Internal.InternalDbSet`1.get_EntityType()\r\n at Microsoft.EntityFrameworkCore.Internal.InternalDbSet`1.get_EntityQueryable()\r\n at Microsoft.EntityFrameworkCore.Internal.InternalDbSet`1.System.Linq.IQueryable.get_Provider()\r\n at System.Linq.Queryable.Where[TSource](IQueryable`1 source, Expression`1 predicate)\r\n at Application.Accounts.Queries.GetAll.GetAllAccountsQueryHandler.Handle(GetAllAccountsQuery request, CancellationToken cancellationToken) in C:\\Repos\\API\\Application\\Accounts\\Queries\\GetAll\\GetAllAccountsQueryHandler.cs:line 27\r\n at MediatR.Pipeline.RequestPostProcessorBehavior`2.Handle(TRequest request, CancellationToken cancellationToken, RequestHandlerDelegate`1 next)\r\n at MediatR.Pipeline.RequestPreProcessorBehavior`2.Handle(TRequest request, CancellationToken cancellationToken, RequestHandlerDelegate`1 next)\r\n at m25.Application.Infrastructure.RequestPerformanceBehavior`2.Handle(TRequest request, CancellationToken cancellationToken, RequestHandlerDelegate`1 next) in C:\\Repos\\API\\Application\\Infrastructure\\RequestPerformanceBehavior.cs:line 25\r\n at MediatR.Pipeline.RequestPreProcessorBehavior`2.Handle(TRequest request, CancellationToken cancellationToken, RequestHandlerDelegate`1 next)\r\n at WebApi.Controllers.AccountsController.Get() in C:\\Repos\\API\\WebApi\\Controllers\\AccountsController.cs:line 34\r\n at lambda_method(Closure , Object )\r\n at Microsoft.Extensions.Internal.ObjectMethodExecutorAwaitable.Awaiter.GetResult()\r\n at Microsoft.AspNetCore.Mvc.Internal.ActionMethodExecutor.AwaitableObjectResultExecutor.Execute(IActionResultTypeMapper mapper, ObjectMethodExecutor executor, Object controller, Object[] arguments)\r\n at System.Threading.Tasks.ValueTask`1.get_Result()\r\n at Microsoft.AspNetCore.Mvc.Internal.ControllerActionInvoker.InvokeActionMethodAsync()\r\n at Microsoft.AspNetCore.Mvc.Internal.ControllerActionInvoker.InvokeNextActionFilterAsync()\r\n at Microsoft.AspNetCore.Mvc.Internal.ControllerActionInvoker.Rethrow(ActionExecutedContext context)\r\n at Microsoft.AspNetCore.Mvc.Internal.ControllerActionInvoker.Next(State& next, Scope& scope, Object& state, Boolean& isCompleted)\r\n at Microsoft.AspNetCore.Mvc.Internal.ControllerActionInvoker.InvokeInnerFilterAsync()\r\n at Microsoft.AspNetCore.Mvc.Internal.ResourceInvoker.InvokeNextExceptionFilterAsync()"
}
我尝试将配置移至OnModelCreating函数,而不是使用没有运气的单独类。
我还确认我可以创建迁移并更新数据库。
如果有帮助,我遇到的其他错误是使用HasConversion将ICollection转换为CSV,或从CSV转换为ICollection,这也引起了错误,但我在类中进行了处理(疼痛但可行)。
GroupSubscriber.cs
public class GroupSubscriber
{
public Guid SubscriberId { get; set; }
public Subscriber.Subscriber Subscriber { get; set; }
public Guid GroupId { get; set; }
public Group Group { get; set; }
public long ShardKey { get; set; }
public Guid AccountId { get; set; }
}
GroupSubscriberConfiguration.cs
public class GroupSubscriberConfiguration : IEntityTypeConfiguration<GroupSubscriber>
{
public void Configure(EntityTypeBuilder<GroupSubscriber> builder)
{
builder.ToTable("SubscriberList_Group_Subscriber");
builder.HasKey(gs => new { gs.GroupId, gs.SubscriberId });
builder.Property(e => e.ShardKey).IsRequired();
builder.HasOne(e => e.Subscriber)
.WithMany(s => s.GroupSubscribers)
.HasForeignKey(e => e.SubscriberId)
.HasConstraintName("FK_SubscriberListGroupSubscriber_Subscriber")
.OnDelete(DeleteBehavior.ClientSetNull);
builder.HasOne(e => e.Group)
.WithMany(g => g.GroupSubscribers)
.HasForeignKey(e => e.GroupId)
.HasConstraintName("FK_SubscriberListGroupSubscriber_Group");
}
}
DbContext.cs
//standard DB Context code above but here's the important part
protected override void OnModelCreating(ModelBuilder modelBuilder)
{
modelBuilder.ApplyConfigurationsFromAssembly(typeof(DbContext).Assembly));
}
我希望能够使用Fluent API配置复合主键。