即使操作成功,面向对象引用也未设置异常

时间:2018-05-06 22:27:17

标签: c# asp.net-mvc asp.net-core-2.0 razor-pages

每次尝试进入新课程时,我都会收到以下错误。

  

对象引用未设置为对象的实例。   AspNetCore._Views_Admin_Manage_cshtml + LT; b__23_12> d.MoveNext()   在Manage.cshtml,第34行

这是我的控制器:

using ASP_Project.Data;
using ASP_Project.Models;
using ASP_Project.Services.Interfaces;
using ASP_Project.ViewModels;
using Microsoft.AspNetCore.Authorization;
using Microsoft.AspNetCore.Identity;
using Microsoft.AspNetCore.Mvc;
using System.Collections.Generic;
using System.Linq;
using System.Security.Claims;
using System.Threading.Tasks;

namespace ASP_Project.Controllers
{
    public class AdminController : Controller
    {
        private readonly UserManager<ApplicationUser> _userManager;
        private readonly SchoolContext _schoolContext;
        private readonly IAdminRepository _adminRepos;
        private readonly ITeacherRepository _teacherRepository;

        public AdminController(UserManager<ApplicationUser> userManager,
            SchoolContext schoolContext,
            IAdminRepository adminRepos,
            ITeacherRepository teacherRepository
            )
        {
            _userManager = userManager;
            _schoolContext = schoolContext;
            _adminRepos = adminRepos;
            _teacherRepository = teacherRepository;
        }

        [HttpGet]
        [Authorize(Roles = "Admin")]
        public async Task<IActionResult> Index()
        {
            ClaimsPrincipal currentUser = User;
            var user = await _userManager.GetUserAsync(currentUser);
            var admin = _adminRepos.GetAdminByUser(user);

            return View(new AdminViewModel()
            {
                FirstName = admin.FirstName,
                LastName = admin.LastName,
                MiddleName = admin.MiddleName
            });
        }

        [HttpGet]
        public IActionResult Manage()
        {
            IEnumerable<string> teachers = _teacherRepository.TeacherNames();
            return View(new CourseViewModel()
            {
                Teachers = teachers
            });
        }

        [HttpPost]
        public async Task<IActionResult> Manage(CourseViewModel courseViewModel)
        {
            var teacher = _schoolContext.Teacher.Single(t => t.FirstName == courseViewModel.TeacherName);
            Course course = new Course()
            {
                CodeID = courseViewModel.CodeID,
                Name = courseViewModel.Name,
                NumOfCredits = courseViewModel.NumOfCredits,
                TeacherID = teacher.TeacherID
            };
            await _schoolContext.Course.AddAsync(course);
            if (await _schoolContext.SaveChangesAsync() == 0)
                return RedirectToAction("Index", "Admin");
            return View(courseViewModel);
          }
       }
  }

这是我的观点:

@model ASP_Project.ViewModels.CourseViewModel
@{
    ViewData["Title"] = "Manage";
}

<h2>Manage</h2>

<div class="row">
    <div class="col-md-4">
        <form asp-controller="Admin" asp-action="Manage" method="post" class="form-horizontal" role="form">
            <h4>Create a new Course.</h4>
            <hr />
            <div asp-validation-summary="All" class="text-danger"></div>
            <div class="form-group">
                <label asp-for="CodeID"></label>
                <input asp-for="CodeID" class="form-control" />
                <span asp-validation-for="CodeID" class="text-danger"></span>
            </div>
            <div class="form-group">
                <label asp-for="Name"></label>
                <input asp-for="Name" class="form-control" />
                <span asp-validation-for="Name" class="text-danger"></span>
            </div>
            <div class="form-group">
                <label asp-for="NumOfCredits"></label>
                <input asp-for="NumOfCredits" class="form-control" />
                <span asp-validation-for="NumOfCredits" class="text-danger"></span>
            </div>
            <div>
                <label asp-for="TeacherName" class="col-md-2 control-label"></label>
                <div class="col-md-10">
                    <select asp-for="TeacherName" class="form-control" required>
                        <option value="" disabled selected>Select Teacher</option>
                        @foreach (var teach in Model.Teachers)
                        {
                            <option value="@teach"> @teach </option>
                        }
                    </select>
                    <span asp-validation-for="TeacherName" class="text-danger"></span>
                </div>
            </div>

            <button type="submit" class="btn btn-default">Add</button>
        </form>
    </div>
</div>
@section Scripts {
    @await Html.PartialAsync("_ValidationScriptsPartial")
}

我的CourseViewModel:

using ASP_Project.Models;
using System;
using System.Collections.Generic;
using System.ComponentModel.DataAnnotations;
using System.Linq;
using System.Threading.Tasks;

namespace ASP_Project.ViewModels
{
    public class CourseViewModel
    {
        [Required]
        public string CodeID { get; set; }
        [Required]
        public int NumOfCredits { get; set; }
        [Required]
        public string Name { get; set; }
        [Required]
        public string TeacherName { get; set; }
        public IEnumerable<string> Teachers { get; set; } 
    }
}

最后,函数用于检索教师的姓名:

public IEnumerable<string> TeacherNames() => _schoolContext.Teacher.Select(t => t.FirstName);

我从异常中理解的是,foreach中有一部分需要等待,或者其中一个对象未​​被定义。

请注意,该操作正在成功完成其工作,并且数据正在添加到数据库中,只是这个奇怪的异常不断出现。 编辑:即使@NoCodeFound回答指出我应该调试(以及我做了什么来找到答案)但我还是计划这样做,而且我碰巧发现了真正的原因。

1 个答案:

答案 0 :(得分:0)

原因是我在POST后从Manage操作返回时搞砸了,因为我使用了:

if (await _schoolContext.SaveChangesAsync() == 0)
   return RedirectToAction("Index", "Admin");
return View(courseViewModel);

这让我再次浏览courseViewModel,而不是被重定向到我需要的页面。 所以修复只是:

if (await _schoolContext.SaveChangesAsync() == 0)
                return View(courseViewModel);
return RedirectToAction("Index", "Admin");