我的MVC3应用程序中有以下模型,我首先使用实体框架4.1代码。
public class Movie
{
public int Id { get; set; }
[Required]
public string Title { get; set; }
[Required]
public string Director { get; set; }
[CustomValidation(typeof(MovieValidator), "ValidateReleaseDate")]
public DateTime ReleaseDate { get; set; }
}
Noe,如果我从Title和Director中删除Required属性并使它们在数据库中可以为空(这是由上述模型中的EF代码自动创建的),我会收到以下错误:
支持'MoviesDB'的模型 自数据库以来,上下文已经改变 创建了。手动 删除/更新数据库,或者调用 Database.SetInitializer with IDatabaseInitializer实例。对于 例如, DropCreateDatabaseIfModelChanges 策略会自动删除和 重新创建数据库,也可以选择 用新数据播种。
我已经读过要解决这个问题,我必须做以下事情之一:
1)删除db以便EF可以重新创建它
2)在上下文类中添加以下行:(这不适用于EF 4.1的上下文,我在application_start中添加了它的工作原理。为什么它现在不能在上下文中运行?)
Database.SetInitializer<MoviesDB>(
new DropCreateDatabaseIfModelChanges<MoviesDB>());
3)匹配表与模型(我的模型与表完全相同,为什么我仍然会收到此错误?)
请提出第2点和第3点中提到的问题的答案。
感谢。
答案 0 :(得分:3)
设置初始化程序应该在上下文的构造函数中起作用,但是每次初始化上下文时都不需要调用 - 只需要执行一次,因此在应用程序启动期间调用它是一种很好的方法。
如果使用自动更改检测(默认行为),则无法更新数据库。当上下文创建模型时,它会根据此模型计算哈希值,并将其与存储在EdmMetadata
表中的值进行比较(表格是在EF创建数据库时首次创建的)。如果从数据库加载的值不同,EF将启动数据库重新创建(如果已配置初始化程序)或抛出您看到的异常。手动更改数据库不会修改存储在EdmMetadata
中的哈希值,因此模型仍会认为数据库未更改。
删除IncludeMetadataConvention
:
protected override void OnModelCreating(DbModelBuilder modelBuilder)
{
base.OnModelCreating(modelBuilder);
model.Conventions.Remove<IncludeMetadataConvention>();
}
删除此约定后,EF将不使用EdmMetadata
表,也不会检查模型中的更改。更新数据库完全取决于您。