Asp.net-Mvc

上傳包含在 MVC 模型中的圖像

  • December 8, 2018

我有以下模型:

public class Photo
{
   public int PhotoId { get; set; }
   public byte[] ImageData { get; set; }
   public DateTime DateUploaded { get; set; }
   public string Description { get; set; }
   public bool IsActive { get; set; }

}

我希望使用者能夠輸入照片的詳細資訊,然後將模型發佈到控制器。我的控制器動作如下:

[HttpPost]
   public ActionResult Create(WilhanWebsite.DomainClasses.Photo photo)
   {
       if (ModelState.IsValid)
       {
           photo.DateUploaded = DateTime.Now;
           _context.Photos.Add(photo);
           _context.SaveChanges();

           return RedirectToAction("Index");
       }
       //we only get here if there was a problem
       return View(photo);
   }

我的看法如下:

@using (Html.BeginForm()) 
{
@Html.AntiForgeryToken()

<div class="form-horizontal">
   <h4>Photo</h4>
   <hr />
   @Html.ValidationSummary(true)

   <div class="form-group">
       @Html.LabelFor(model => model.ImageData, new { @class = "control-label col-md-2" })
       <div class="col-md-10">
           <input type="file" name="uploadImages" class="input-files" />
       </div>
   </div>

   <div class="form-group">
       @Html.LabelFor(model => model.DateUploaded, new { @class = "control-label col-md-2" })
       <div class="col-md-10">
           @Html.EditorFor(model => model.DateUploaded)
           @Html.ValidationMessageFor(model => model.DateUploaded)
       </div>
   </div>

   <div class="form-group">
       @Html.LabelFor(model => model.Description, new { @class = "control-label col-md-2" })
       <div class="col-md-10">
           @Html.EditorFor(model => model.Description)
           @Html.ValidationMessageFor(model => model.Description)
       </div>
   </div>

   <div class="form-group">
       @Html.LabelFor(model => model.IsActive, new { @class = "control-label col-md-2" })
       <div class="col-md-10">
           @Html.EditorFor(model => model.IsActive)
           @Html.ValidationMessageFor(model => model.IsActive)
       </div>
   </div>

   <div class="form-group">
       <div class="col-md-offset-2 col-md-10">
           <input type="submit" value="Create" class="btn btn-default" />
       </div>
   </div>
</div>
}

該視圖顯示正常,並允許使用者從本地磁碟中選擇一個文件並輸入其他模型詳細資訊。我的問題是,雖然模型已發佈到控制器上,但描述、日期和 IsActive 標誌已填充好 - 圖像數據為空。

誰能讓我知道我需要更改什麼,以便照片的字節數組包含在發佈到控制器的模型中?

您視圖中的文件輸入有一個名稱uploadImages。我在您的視圖模型中看不到具有此名稱的屬性。您似乎有一些ImageData屬性是字節數組,但在您的視圖中似乎沒有具有此名稱的相應輸入欄位。

這解釋了為什麼你會得到空值。您可以通過遵守約定來完成這項工作。例如,如果您打算在視圖中有這樣一個輸入欄位:

<input type="file" name="uploadImages" class="input-files" />

然後確保您的視圖模型上有一個同名的屬性。當然還有 type HttpPostedFileBase

public HttpPostedFileBase UploadImages { get; set; }

同樣在您看來,請確保您設置了正確的內容類型multipart/form-data

@using (Html.BeginForm(null, null, FormMethod.Post, new { enctype = "multipart/form-data" }))
{
   ...
}

您可能希望通過閱讀following blog post來更好地熟悉在 ASP.NET MVC 中文件上傳工作的基礎知識。我還寫了一個similar answer here你可以參考的。

因此,一旦您在視圖模型中添加HttpPostedFileBase具有名稱的屬性,UploadImages您就可以調整控制器操作以讀取字節數組並將其儲存為您的ImageData屬性:

[HttpPost]
public ActionResult Create(WilhanWebsite.DomainClasses.Photo photo)
{
   if (ModelState.IsValid)
   {
       photo.DateUploaded = DateTime.Now;
       photo.ImageData = new byte[photo.UploadImages.ContentLength];
       photo.UploadImages.Read(photo.ImageData, 0, photo.ImageData.Length);

       _context.Photos.Add(photo);
       _context.SaveChanges();

       return RedirectToAction("Index");
   }

   //we only get here if there was a problem
   return View(photo);
}

現在請記住,這是一個絕對糟糕的解決方案。永遠不要在現實世界的應用程序中這樣做。在正確設計的應用程序中,您將擁有一個視圖模型,您的控制器操作將作為參數。您永遠不會直接使用自動生成的 EF 模型作為控制器操作的參數。您將擁有一個具有屬性的視圖模型,該HttpPostedFileBase屬性將映射到您的域模型。

因此,在正確設計的應用程序中,您將擁有一個PhotoViewModel控制器操作將執行的視圖模型類。

引用自:https://stackoverflow.com/questions/20446580