有使用 ASP.NET MVC 的朋友們一定多多少少有聽過 TryUpdateModel,之前就看了很多有關它的文章,但在專案實務上都未曾實際使用過,而 TryUpdateModel 不僅能利用 Metadata 來做欄位驗證確保資料正確性,也可以指定更新的條件或是指定某幾個欄位不更新,這幾天剛好有時間就寫了簡單的範例,來看看它到底有什麼神奇魔力吧。
前言
有使用 ASP.NET MVC 的朋友們一定多多少少有聽過 TryUpdateModel,之前就看了很多有關它的文章,但在專案實務上都未曾實際使用過,而 TryUpdateModel 不僅能利用 Metadata 來做欄位驗證確保資料正確性,也可以指定更新的條件或是指定某幾個欄位不更新,這幾天剛好有時間就寫了簡單的範例,來看看它到底有什麼神奇魔力吧。
說明
首先我們先定義一個 Model 如下:
一般透過 TryUpdateModel 來做資料更新,最簡單的寫法如下 :
[HttpPost]
[ValidateAntiForgeryToken]
public ActionResult Edit(int Id)
{
Product product = db.Product.Where(p => p.Id.Equals(Id)).FirstOrDefault();
if (TryUpdateModel(product, new string[] { "Name", "Ename", "ModifyUid" }))
{
db.SaveChanges();
return RedirectToAction("Index");
}
return View(product);
}
在 TryUpdateModel 裡的第一個參數為要被更新的資料,而第二個參數則是我們要細節的資料,這時候可能會有個疑問,那它細節的資料是從哪邊而來的?「其實就跟 Model Binding 的機制很像,TryUpdateModel 會透過你從表單回傳的資料,只要名稱一樣就會自己繫節上去囉。」
所以透過上面的程式碼,只會更新 Name、Ename、ModifyUid 這三個欄位,其他欄位的資料是不會做更新的。
但如果今天我們頁面上的欄位有十幾二十個的的話,若使用上面的方法光打欄位名稱可能就會花費許多時間!
此時我們可以利用 FormCollection 來接收 View 傳來的資料來做欄位更新,所以可以改成以下寫法:
[HttpPost]
[ValidateAntiForgeryToken]
public ActionResult Edit(int Id, FormCollection FromValue)
{
Product product = db.Product.Where(p => p.Id.Equals(Id)).FirstOrDefault();
if (TryUpdateModel(product, FromValue.AllKeys) && ModelState.IsValid)
{
db.SaveChanges();
return RedirectToAction("Index");
}
return View(product);
}
但問題又來了,一般情況下總是會有某些欄位是不希望使用者去做更新的,則透過 TryUpdateModel 的多載來達到排除欄位的效果,如下:
[HttpPost]
[ValidateAntiForgeryToken]
public ActionResult Edit(int Id, FormCollection FromValue)
{
Product product = db.Product.Where(p => p.Id.Equals(Id)).FirstOrDefault();
if (TryUpdateModel(product, "", FromValue.AllKeys, new string[] { "ModifyUid" }))
{
db.SaveChanges();
return RedirectToAction("Index");
}
return View(product);
}
如上面的程式片段,我們可以排除更新 ModifyUid 的欄位。
總結
TryUpdateModel 擁有了10個多載的方法,所以它可以應用的範圍也非常廣,但在使用上也有需要注意的地方,像是其第一個多載方法就存在著「安全性問題」,因為預設是接收 View 所傳來的資料來做資料繫結,只要是符合的欄位就會直接寫入 Model 中,所以當你有某些欄位是不想給使用者更新時,請務必設定「白名單」或「黑名單」!
參考資料
新手發文,如有錯誤煩請告知,感謝。
如果喜歡我的文章請按推薦,有任何問題歡迎下面留言~~~
簽名:
學習這條路很廣,喜歡什麼技術不重要,重要的是你肯花時間去學習