如何创建新的实体对象,在SaveChanges()之前在Model中修改它
本文关键字:SaveChanges 修改 Model 对象 创建 何创建 实体 | 更新日期: 2023-09-27 18:04:30
这个问题我已经考虑了好几个小时了,还是没能找到问题所在。我用的是ASP。NET MVC 3与实体框架4.1。我正在从零开始编写帐户管理控制器和模型。我的问题是,每当控制器从视图接收到填充的实体对象并将其发送到模型时,如果我尝试事先修改任何字段,则模型不会保存它。
这是我的模型的相关部分,名为ModelManager.cs:
public class MemberManager
{
private DAL db = new DAL();
public void Add(Member member)
{
member.Password = Crypto.HashPassword(member.Password);
db.Members.Add(member);
db.SaveChanges();
}
该模型从控制器获得作为参数的Member member
实体对象,其相关部分如下:
[HttpPost]
public ActionResult Register(Member member)
{
try
{
if (ModelState.IsValid)
{
MemberManager memberManager = new MemberManager();
if (!memberManager.UsernameExist(member.Username))
{
memberManager.Add(member);
FormsAuthentication.SetAuthCookie(member.FirstName, false);
return RedirectToAction("Welcome", "Home");
}
else
{
ModelState.AddModelError("", "Username already taken.");
}
}
}
catch
{
ModelState.AddModelError("", "Could not complete account creation. Please try again.");
}
return View(member);
}
如果我删除对模型中实体对象的任何属性的任何修改,代码工作(即我删除了我Crypto.HashPassword
实体对象的密码字段的行)。起初,我认为问题是与HashPassword,但如果我改变这一行,只是改变成员。密码为字符串"1",它也不会工作。
那么,我做错了什么?我对编程完全陌生,所以如果这个问题很明显,请原谅我。是不是有可能在创建帐户时从视图创建实体对象,将其发送给控制器,然后将其传递给模型,该模型在保存之前修改密码以散列它?
BTW,引发的异常错误是:
System.Data.Entity.Validation。DbEntityValidationException:一个或多个实体验证失败。查看'EntityValidationErrors'属性了解更多细节。at System.Data.Entity.Internal.LazyInternalContext.SaveChanges() at System.Data.Entity.DbContext.SaveChanges() at Politiq.Models.ObjectManager.MemberManager。在c:' users ' c中添加(Member Member)Yehia'Documents'Visual Studio 2010'Projects'Politiq2'Models'ObjectManager'MemberManager.cs:在Politiq.Controllers.AccountController. cs第21行。注册(Member Member)在c:' users ' cYehia'Documents'Visual Studio 2010'Projects'Politiq2'Controllers'AccountController.cs:line 39
我看到你的成员实例是由一个模型绑定器(即不在你的代码)创建的,但我没有看到它实际上被添加到表中。你错过db.Members.Add()
的电话了吗?
Member
实例,而是自己创建它。原因是这种方法是不安全的,因为默认情况下绑定器会尝试将每个HTML输入字段分配给一个匹配的属性,所以黑客可以在你的对象中注入Id
值,这将导致异常(可能还有一些其他讨厌的事情)。
当然,你可以使用[Bind(Exclude="ID")]
,这样它就不会尝试填充ID,但我仍然会将数据库实体和用户输入分开:
MemberController
public ActionResult Register(RegistrationForm form)
MemberManager
public Member RegisterMember(RegistrationForm form)