2016-10-04 1 views
1

Я работаю над системой, позволяющей нашим пользователям загружать изображения в базу данных. Загрузка изображения в базу данных, кажется, работает нормально, но я не могу заставить изображение вернуться и отобразить на мой взгляд. Я не получаю сообщений об ошибках, которые изображение просто не отображается. Вот мой код до сих пор.Как получить изображение из базы данных в MVC?

контроллер/Создать метод

[HttpPost] 
    [ValidateAntiForgeryToken] 
    public ActionResult Create(UserAccount userAccount, HttpPostedFileBase upload) 
    { 
     try 
     { 
      if (ModelState.IsValid) 
      { 
       if (upload != null && upload.ContentLength > 0) 
       { 
        var photo = new UserImage 
        { 
         FileName = System.IO.Path.GetFileName(upload.FileName), 
         FileType = FileType.VesselImage, 
         ContentType = upload.ContentType 
        }; 
        using (var reader = new System.IO.BinaryReader(upload.InputStream)) 
        { 
         photo.Content = reader.ReadBytes(upload.ContentLength); 
        } 
        userAccount.UserImages = new List<UserImage> { photo }; 
       } 
       db.UserAccounts.Add(userAccount); 
       db.SaveChanges(); 
       return RedirectToAction("Index"); 
      }//if 
     }//try 
     catch (RetryLimitExceededException /* dex */) 
     { 
      //Log the error (uncomment dex variable name and add a line here to write a log. 
      ModelState.AddModelError("", "Unable to save changes. Try again, and if the problem persists see your system administrator."); 
     } 
     return View(userAccount); 
    } 

Контроллер/Детали Метод Breakpoints показывают, что изображение будет найден и выбран на данном этапе.

public ActionResult Details(int? id) 
    { 
     if (id == null) 
     { 
      return new HttpStatusCodeResult(HttpStatusCode.BadRequest); 
     } 
     UserAccount userAccount = db.UserAccounts 
      .Include(s => s.UserImages) 
      .SingleOrDefault(s => s.userId == id); 
     if (userAccount == null) 
     { 
      return HttpNotFound(); 
     } 
     return View(userAccount); 
    }  

Посмотреть/Детали

@model Multiple_Table_Post.Models.UserAccount 
@{ 
    ViewBag.Title = "Details"; 
} 

<h2>Details</h2> 
<div> 
<h4>UserAccount</h4> 
<hr /> 
<dl class="dl-horizontal"> 
    <dt> 
     @Html.DisplayNameFor(model => model.userName) 
    </dt> 

    <dd> 
     @Html.DisplayFor(model => model.userName) 
    </dd> 

    <dt> 
     @Html.DisplayNameFor(model => model.userLocation) 
    </dt> 

    <dd> 
     @Html.DisplayFor(model => model.userLocation) 
    </dd> 


    @if (Model.UserImages.Any(f => f.FileType == FileType.VesselImage)) 
    { 
     <dt> 
      Image 
     </dt> 
     <dd> 
      <img src="~/[email protected](f => f.FileType == FileType.VesselImage).FileId" alt="avatar" /> 
     </dd> 
    } 

</dl> 
</div> 
<p> 
@Html.ActionLink("Edit", "Edit", new { id = Model.userId }) | 
@Html.ActionLink("Back to List", "Index") 
</p> 

Я думаю, что что-то не так с моим состоянием:

@if (Model.UserImages.Any(f => f.FileType == FileType.VesselImage)) 
    { 
     <dt> 
      Image 
     </dt> 
     <dd> 
      <img src="~/[email protected](f => f.FileType == FileType.VesselImage).FileId" alt="avatar" /> 
     </dd> 
    } 

Если я нарушу в этой точке в пределах зрения я могу видеть, что изображение выбрано, но примечание выводится. Я просто ничего не возвращаю.

Я также включил свои модели в надежде, что смогу дойти до сути этой проблемы. Вот они:

Модель/учетная_запись_пользователя

namespace Multiple_Table_Post.Models 
{ 
using System; 
using System.Collections.Generic; 

public partial class UserAccount 
{   

    public int userId { get; set; } 
    public string userName { get; set; } 
    public string userLocation { get; set; } 


    public virtual ICollection<UserImage> UserImages { get; set; } 
} 
} 

Модель/UserImage пространства имен Multiple_Table_Post.Models { с использованием системы; с использованием System.Collections.Generic;

public partial class UserImage 
{ 
    public int FileId { get; set; } 
    public string FileName { get; set; } 
    public string ContentType { get; set; } 
    public byte[] Content { get; set; } 
    public Nullable<int> PersonId { get; set; } 
    public FileType FileType { get; set; } 

    public virtual UserAccount UserAccount { get; set; } 
} 
} 

Модель/FileType

namespace Multiple_Table_Post.Models 
{ 
public enum FileType 
{ 
    VesselImage = 1, Photo 
} 
} 

Спасибо, если я пропустил что-нибудь, что бы сделать это проще, пожалуйста, дайте мне знать.

Обновление: здесь я включил информацию о контрольной точке о том, что система делает, когда условие попадает и данные могут видеть.

Condition is reached and the system knows there is an image in there enter image description here

+0

Я обычно использую ' jbutler483

+1

Не могли бы вы отобразить код этого вызова '~/File? id = ...' Возможно, этот метод возвращает неправильный заголовок 'Content-Type'? –

ответ

0

Попробуйте это:

<img src="data:image/jpg;base64,[byte array]"/> 

Заменить:

  1. jpg с типом изображения, т.е. FileType
  2. [byte array] с байтовый массив т.е. Content.

Вам необходимо преобразовать Content в base64, если его еще нет.

0

Хорошо, я играл немного больше и заметил что-то в обновлении, которое я разместил. В следующем изображении: enter image description here Вы заметите, что FileType указана как 0, однако в классе FileType я сказал, что это FileType является 1.

public enum FileType 
{ 
    VesselImage = 1, Photo 
} 

Так что условие не выполняется как это не может видеть FileType, равный 0. Изменение VesselImage на 0 в моем классе FileType устраняет проблему. :)

1

Способ, которым я предпочитаю это сделать, - создать ActionResult, который напрямую обслуживает запросы браузера для изображения. Одним из преимуществ этого подхода является то, что если страница содержит изображение более одного раза, браузер автоматически делится ресурсом. Это позволяет сэкономить базы данных, перевести данные и максимизировать возможности кэширования.

public ActionResult Portrait(int id) 
{ 
    vPhotos p = sdb.vPhotos.Where(e => e.ID == id).SingleOrDefault(); 
    byte[] photoArray = new byte[] { }; 
    return File(smallPhotoArray, "image/png"); 
} 

Теперь на ваш взгляд, просто вызовите ActionMethod в качестве ссылки IMG SRC:

<img src="@Url.Action("Portrait", "MyController" , new { id = id })" /> 
Смежные вопросы