简体   繁体   中英

Can't upload or download files into database

I have an ASP.NET Core 3.1 project, and I am trying to upload files into my database and displaying their URL so I can download them again. But when I press upload, I get an error in the index view referring to this line

@foreach (var item in Model)

Error Message:

NullReferenceException: Object reference not set to an instance of an object. AspNetCore.Views_Demo_Index.ExecuteAsync() in Index.cshtml, line 25 @foreach (var item in Model)

Here is my model class:

public class Files
{
    [Key]
    public int DocumentId { get; set; }
    public string Name { get; set; }
    public string FileType { get; set; }
    public byte[] DataFiles { get; set; }
}

This is my controller:

using Info.Data;
using Info.Models;
using Microsoft.AspNetCore.Http;
using Microsoft.AspNetCore.Mvc;
using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Threading.Tasks;

namespace Info.Controllers
{
    public class DemoController : Controller
    {
        private readonly ApplicationDbContext _context;

        public DemoController(ApplicationDbContext context)
        {
            _context = context;
        }

        public IActionResult Index()
        {
            var result = _context.Files.ToList();
            return View(result);
        }

        [HttpPost]
        public IActionResult Index(IFormFile files)
        {
            if (files != null)
            {
                if (files.Length > 0)
                {
                    //Getting FileName
                    var fileName = Path.GetFileName(files.FileName);
                    //Getting file Extension
                    var fileExtension = Path.GetExtension(fileName);
                    // concatenating  FileName + FileExtension
                    var newFileName = String.Concat(Convert.ToString(Guid.NewGuid()), fileExtension);

                    var objfiles = new Files()
                    {
                        DocumentId = 0,
                        Name = newFileName,
                        FileType = fileExtension,
                    };

                    using (var target = new MemoryStream())
                    {
                        files.CopyTo(target);
                        objfiles.DataFiles = target.ToArray();
                    }

                    _context.Files.Add(objfiles);
                    _context.SaveChanges();
                }
            }

            return View();
        }

        public IActionResult DownloadImage(int id)
        {
            byte[] bytes;
            string fileName, contentType;

            var item = _context.Files.FirstOrDefault(c => c.DocumentId == id);

            if (item != null)
            {
                fileName = item.Name;

                contentType = item.FileType;
                bytes = item.DataFiles;

                return File(bytes, contentType, fileName);
            }

            return Ok("Can't find the File");
        }      
    }
}

Here is the view

@model List<Info.Models.Files>
@{
    ViewData["Title"] = "Index";
}

<h1>Index</h1>
<div class="row">
    <div class="col-md-5">
        <form method="post" enctype="multipart/form-data" asp-controller="Demo" asp-action="Index">
            <div class="form-group">
                <div class="col-md-10">
                    <p>Upload file</p>
                    <input class="form-control" name="files" type="file" />
                </div>
            </div>
            <div class="form-group">
                <div class="col-md-10">
                    <input class="btn btn-success" type="submit" value="Upload" />
                </div>
            </div>
        </form>
    </div>
</div>
<ul>
    @foreach (var item in Model)
    {
        <li>
            <a asp-action="DownloadImage"
               asp-route-filename="@item.Name">
                @item.Name
            </a>
        </li>
    }
</ul>

I can't upload or download.

@hhaannyy.

Your index view code is:

@model List<Info.Models.Files>
 ...............

<ul>
    @foreach (var item in Model)
    {
        <li>
            <a asp-action="DownloadImage"
               asp-route-filename="@item.Name">
                @item.Name
            </a>
        </li>
    }
</ul>

When you load your index view, You need to pass a list of Info.Models.Files from controller to view and use @foreach(xxx) to show them right?

In your get action, you use:

public IActionResult Index()
{
      var result = _context.Files.ToList();
      return View(result);
}

to pass _context.Files.ToList(); to the view, @foreach(xxx) can work successfully. But in your HttpPost action, After you upload file and save it in db, you just return View(); , You don't pass any value to the view, The model is null in your View, So @foreach (var item in Model) will show NullReferenceException. You can use this code to solve this error:

   [HttpPost]
    public IActionResult Index(IFormFile files)
    {
        //...............

        return RedirectToAction("Index");
    }

please check your dB Context connection string and appsetting.json also did you run the migration and db update command? Here is a guid about dbcontext

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM