C# MVC4-使用实体框架更新模型-传递httpPost参数的Null异常

C# MVC4-使用实体框架更新模型-传递httpPost参数的Null异常,c#,entity-framework,asp.net-mvc-4,nullreferenceexception,C#,Entity Framework,Asp.net Mvc 4,Nullreferenceexception,我正在学习MVC,并试图创建一个简单的表单,允许用户更新模型的描述 问题是我得到了一个空异常 参数字典包含参数的空条目 方法的“System.Int32”类型不可为null的“ThreatID” 中的“System.Web.Mvc.ActionResult GetThreat(Int32)” '风险评估应用程序.控制器.威胁控制器'。可选的 参数必须是引用类型、可为null的类型或声明为 可选参数。参数名称:参数 表单的Get方法似乎按预期工作,但是id没有被传递回HttpPost方法参数,我无

我正在学习MVC,并试图创建一个简单的表单,允许用户更新模型的描述

问题是我得到了一个空异常

参数字典包含参数的空条目 方法的“System.Int32”类型不可为null的“ThreatID” 中的“System.Web.Mvc.ActionResult GetThreat(Int32)” '风险评估应用程序.控制器.威胁控制器'。可选的 参数必须是引用类型、可为null的类型或声明为 可选参数。参数名称:参数

表单的Get方法似乎按预期工作,但是id没有被传递回HttpPost方法参数,我无法确定应该如何传递它。我运行了一个搜索,看到了一些关于使用
@hiddenfor
助手的信息,但它对我不起作用

以下是我的方法

 public ActionResult GetThreat(int ThreatID)
        {
            // ViewModel.Threat = repository.GetThreat(ThreatID);
            RiskAssessmentApplicationEntities _DBContext = new RiskAssessmentApplicationEntities();
            ThreatWithSecurityEventAndISOControlViewModel ViewModel = new ThreatWithSecurityEventAndISOControlViewModel();
            ViewModel.Threat = _DBContext.Threats.Single(x => x.ID == ThreatID);
            ViewModel.SecurityEvents = _DBContext
                                        .ThreatHasSecurityEvents
                                        .Include("ThreatHasSecurityEvent.SecurityEvent")
                                        .Where(x => x.ThreatID == ThreatID)
                                        .Select(x => x.SecurityEvent);

            return View(ViewModel);                                   
        }

[HttpGet]
public ViewResult EditThreat(int ThreatID)
{
    Threat Threat = repository.Threats.FirstOrDefault(x => x.ID == ThreatID);
    return View(Threat);
}

[HttpPost]
public ActionResult EditThreat(Threat Threat)
{
    if (ModelState.IsValid)
    {
        repository.SaveThreat(Threat);
        TempData["message"] = string.Format("{0} new description has been saved", Threat.Description);
        return RedirectToAction("GetThreat");
    }
    else
    {
        // something is incorrect!
        return View(Threat);
    }
}
这是我的看法

@model RiskAssesmentApplication.Threat
@using RiskAssesmentApplication;
@{
    ViewBag.Title = "EditThreat";
}
<div style="font-family: Calibri">
    <fieldset>
        <legend>Edit Threat Description</legend>
        @using (Html.BeginForm())
        {
            @Html.HiddenFor(model => model.ID);
            <div class="editor-label">
                @Html.LabelFor(model => @Model.Description, "Threat Description")
            </div>
            <div class="editor-field">
                @Html.EditorFor(model => @Model.Description)
                @Html.ValidationMessageFor(model => @Model.Description )
            </div> 
            <p>
                <input type="submit" value="Save Changes" />
            </p>
        }
    </fieldset>
</div>
@model risksassessmentapplication.Threat
@使用风险评估应用程序;
@{
ViewBag.Title=“EditThreat”;
}
编辑威胁描述
@使用(Html.BeginForm())
{
@HiddenFor(model=>model.ID);
@Html.LabelFor(model=>@model.Description,“威胁描述”)
@Html.EditorFor(model=>@model.Description)
@Html.ValidationMessageFor(model=>@model.Description)

}
这是我的模型

public class ThreatWithSecurityEventAndISOControlViewModel
    {
        public Threat Threat { get; set; }
        public SecurityEvent SecurityEvent { get; set; }
        public IEnumerable<ISOControl> ISOControls { get; set; }
        public IEnumerable<SecurityEvent> SecurityEvents { get; set; }
公共类ThreatWithSecurityEventandIsControl视图模型
{
公共威胁{get;set;}
public SecurityEvent SecurityEvent{get;set;}
公共IEnumerable等控件{get;set;}
公共IEnumerable SecurityEvents{get;set;}

我真的很难理解这一点,因此任何帮助都将得到感谢,因为没有看到代码的其余部分,这很难说清楚,但听起来您使用的是一个断开连接的实体。仅仅因为您使用的实体模型具有数据库中的行ID,并不意味着它已连接到您的数据上下文。请使用我使用的模型在post中传回以查找连接的版本。示例:

[HttpPost]
public void Whatever(Threat model)
{
    var connectedModel = context.Threats.FirstOrDefault(x => x.ID == model.ID);
    connectedModel.SomeProperty = model.SomeProperty; //or use AutoMapper
    context.SaveChanges();   
}

将您的
重定向到操作
替换为:

return RedirectToAction("EditThreat", new { ThreatID = 99 });
您的
GetThreat()
方法期望参数
int ThreatID
(不可为空),但在
EditThreat()
方法中,重定向时不传递值。更改

return RedirectToAction("GetThreat");


错误消息与控制器方法
GetThreat()
有关,但您所显示的只是
EditThreat()
methodsSumming
GetThreat()
具有参数
int ThreatID
,然后它需要类似于
返回重定向到操作(“GetThreat”,new{ThreatID=Threat.ID})
-但是你需要展示你的方法和模型来确定。嗨,谢谢你的回复,这就成功了,我仍然会发布GetThreat()方法+模型以澄清问题。谢谢,这就是它的原貌。
return RedirectToAction("GetThreat", new { ThreatID = Threat.ID });