[英]EF Core seeding data in Sqlite and WPF with relational model - unable to create an object of type DbContext error
I'm creating a WPF app in .NET 6 with Entity Framework Core and Sqlite.我正在使用 Entity Framework Core 和 Sqlite 在 .NET 6 中创建一个 WPF 应用程序。
I have the following relational model (note some nullable fields are omitted for the sake of brevity):我有以下关系 model(请注意,为简洁起见,省略了一些可为空的字段):
[Table("Contacts")]
public class Contact
{
public Guid Id { get; set; }
[Required]
public string Title { get; set; }
[Required]
public string FirstName { get; set; }
[Required]
public string LastName { get; set; }
public ContactGroup? Parent { get; set; }
public Guid? ParentId { get; set; }
}
[Table("ContactGroups")]
public class ContactGroup
{
public Guid Id { get; set; }
[Required]
public string Name { get; set; }
public ContactGroup? Parent { get; set; }
public Guid? ParentId { get; set; }
public ObservableCollection<ContactGroup> SubGroups { get; set; } = new ObservableCollection<ContactGroup>();
public ObservableCollection<Contact> Contacts { get; set; } = new ObservableCollection<Contact>();
}//class
That is, a ContactGroup
can have zero or more Contact
s.也就是说,一个
ContactGroup
可以有零个或多个Contact
。
I want to seed some data to the Sqlite database, with one of the contacts belonging to a contact group, and one contact without a parent, like so:我想将一些数据播种到 Sqlite 数据库,其中一个联系人属于一个联系人组,另一个联系人没有父级,如下所示:
public class ContactsContext : DbContext
{
public DbSet<Contact> Contacts => Set<Contact>();
public DbSet<ContactGroup> ContactGroups => Set<ContactGroup>();
public ContactsContext()
{
Database.EnsureDeleted();
Database.EnsureCreated();
}
protected override void OnConfiguring(DbContextOptionsBuilder optionsBuilder)
{
optionsBuilder.UseSqlite("Data Source=contacts.db");
}
protected override void OnModelCreating(ModelBuilder modelBuilder)
{
modelBuilder.Entity<ContactGroup>(entity =>
{
entity.HasKey(x => x.Id);
entity.Property(x => x.Name);
entity.HasOne(x => x.Parent)
.WithMany(x => x.SubGroups)
.HasForeignKey(x => x.ParentId)
.IsRequired(false)
.OnDelete(DeleteBehavior.Cascade);
entity.HasMany(x => x.Contacts);
});
Contact c1 = new Contact { Id = Guid.NewGuid(), Title = "Mr", FirstName = "John", LastName = "Smith" };
Contact c2 = new Contact { Id = Guid.NewGuid(), Title = "Mrs", FirstName = "Jane", LastName = "Doe" };
ContactGroup g1 = new ContactGroup { Id = Guid.NewGuid(), Name = "Social" };
g1.Contacts.Add(c1);
c1.Parent = g1;
c1.ParentId = g1.Id;
modelBuilder.Entity<ContactGroup>().HasData(
g1
);
modelBuilder.Entity<Contact>().HasData(
c1,
c2
);
}
}//class
When trying to create a migration from this, I get the following error:尝试从中创建迁移时,出现以下错误:
Unable to create an object of type 'ContactsContext'
无法创建类型为“ContactsContext”的 object
What could be causing this and how to fix it?是什么原因造成的以及如何解决?
Maybe it's not a good idea to call EnsureCreated and EnsureDeleted in the constructor.在构造函数中调用 EnsureCreated 和 EnsureDeleted 可能不是一个好主意。 In my opinion that should be outside in some kind of Startup.cs file.
在我看来,应该在某种 Startup.cs 文件之外。 Just move it outside... This way, it's probably causing your problem.
把它移到外面......这样,它可能会导致你的问题。
Database.EnsureDeleted()
and Database.EnsureCreated()
should not be called from inside the constructor but should be called in a method that should be run on start up. Database.EnsureDeleted()
和Database.EnsureCreated()
不应从构造函数内部调用,而应在应在启动时运行的方法中调用。
This is the typical way of using the methods:这是使用这些方法的典型方式:
public static void SetupContactsContext()
{
using (var context = new ContactsContext())
{
context.Database.EnsureDeleted();
context.Database.EnsureCreated();
}
}
The above method should be called on start-up.上面的方法应该在启动时调用。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.