EntityFramework代码第一个中的DateTime列未按预期工作
本文关键字:工作 DateTime 代码 第一个 EntityFramework | 更新日期: 2023-09-27 18:21:35
我有基本型号User
和两个附加型号UserCreateModel
和UserEditModel
。UserCreateModel
工作得很好,创建了用户,但当我尝试编辑用户时,它会给我错误。
我不明白他为什么在datetime上操作,因为数据库中已经有了有效的datetime属性。我只想更新Name
属性。我在这里做错了什么?
错误
将datetime2数据类型转换为datetime数据类型导致值超出范围。语句已终止。
控制器
public HttpResponseMessage PutUser(int id, UserEditModel user)
{
if (!ModelState.IsValid)
{
return Request.CreateErrorResponse(HttpStatusCode.BadRequest, ModelState);
}
if (id != user.Id)
{
return Request.CreateResponse(HttpStatusCode.BadRequest);
}
db.Entry(user).State = EntityState.Modified;
try
{
db.SaveChanges(); // Exception here, all validation passed with success
}
catch (DbUpdateConcurrencyException ex)
{
return Request.CreateErrorResponse(HttpStatusCode.NotFound, ex);
}
return Request.CreateResponse(HttpStatusCode.OK);
}
型号
public class User
{
public int Id { get; set; }
public virtual DateTime CreatedDateTime { get; set; }
public virtual string Username { get; set; }
public virtual string Password { get; set; }
public virtual string PasswordSalt { get; set; }
public virtual string AccessToken { get; set; }
public virtual string Name { get; set; }
}
public class UserEditModel : User
{
[Required]
public override string Name { get; set; }
}
当您将实体映射到数据库时,您需要告诉实体框架使用正确的列类型。
如果你正在使用流利的API,你可以这样做:
Property(p => p.CreatedDateTime).HasColumnType("datetime2");
或者如果您喜欢直接在POCO:上使用列属性
public class User
{
public int Id { get; set; }
[Column(TypeName = "DateTime2")]
public virtual DateTime CreatedDateTime { get; set; }
public virtual string Username { get; set; }
public virtual string Password { get; set; }
public virtual string PasswordSalt { get; set; }
public virtual string AccessToken { get; set; }
public virtual string Name { get; set; }
}
小心;根据您配置实体框架的方式,您现有的数据库可能会被删除并重新创建以说明更改
有关更多信息,请参阅以下博客文章:
- 使用Fluent API配置/映射属性和类型
- 使用数据注释配置/映射特性和类型
通过设置db.Entry(user).State = EntityState.Modified;
,您告诉EF您想要更新user
的所有属性。并且由于您的UserEditModel
派生自User
实体,EF将尝试更新所有实体属性。
我不知道为什么从实体派生编辑模型,但它会在您的场景中引发问题。我更喜欢从Db加载用户,更新你想要的属性并保存它:
var dbUser = db.Users.Find(user.Id);
dbUser.Username = user.Name;
db.SaveChanges();
一般来说,你可以更新多个属性,比如:
var dbUser = db.Users.Find(user.Id);
db.Entry(dbUser).CurrentValues.SetValues(user);
db.SaveChanges();
但它要求编辑模型中的特性与实体特性具有相同的名称(并且编辑模型不是从实体派生的)。