Warning: file_get_contents(/data/phpspider/zhask/data//catemap/1/cocoa/3.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# 使用RedirectToAction通过无效状态_C#_Asp.net Mvc_Asp.net Mvc 5 - Fatal编程技术网

C# 使用RedirectToAction通过无效状态

C# 使用RedirectToAction通过无效状态,c#,asp.net-mvc,asp.net-mvc-5,C#,Asp.net Mvc,Asp.net Mvc 5,我在我的数据层进行了并发检查,当条件发生时,该检查将抛出一个自定义异常(ConcurrencyValidationException)。我正试图在ValidationSummary对象中将其显示为友好的错误消息,就像其他验证错误一样 问题是,在使用RedirectToAction时,我会丢失无效状态。我尝试过将ViewData状态作为TempData传递,但它似乎不起作用 以下是我的控制器中的两个操作: public ActionResult Details(int? id) {

我在我的数据层进行了并发检查,当条件发生时,该检查将抛出一个自定义异常(ConcurrencyValidationException)。我正试图在ValidationSummary对象中将其显示为友好的错误消息,就像其他验证错误一样

问题是,在使用RedirectToAction时,我会丢失无效状态。我尝试过将ViewData状态作为TempData传递,但它似乎不起作用

以下是我的控制器中的两个操作:

    public ActionResult Details(int? id)
    {
        StudentRepository studentRepository = StudentRepository();
        Student student = new Student();
        ActionResult result;

        if (TempData["Student"] != null)
        {
            student = TempData["Student"] as Student;
            TempData["Student"] = student; // needed to survive a browser refresh
        }            
        else if (id != null)
            student = studentRepository.GetById((int)id);

        if (student != null)
            result = View(student);
        else
            result = RedirectToAction("Index");

        return result;
    }

    [HttpPut]
    public ActionResult Upsert(Student model)
    {
        StudentRepository studentRepository = StudentRepository();
        int studentId= 0;

        try
        {
            if (model.IsValid() && model.Id == null)
            {
                studentId = studentRepository.Add(model);
            }
            else if (model.IsValid() && model.Id != null)
            {
                studentRepository.Update(model);
                studentId = (int)model.Id;
            }
        }
        catch (ConcurrencyValidationException exception)
        {
            ModelState.AddModelError("ConcurrencyUniqueID", exception);
            TempData["Student"] = model;

            if (model.Id != null)
                studentId = (int)model.Id;
        }

        return RedirectToAction("Details", new { id = studentId });
    }
加载详细信息视图时,不会显示任何错误,错误将丢失。顺便说一句,我使用RedirectToAction而不在Upsert()中显示调用视图的原因是我不希望URL是/Upsert,我希望它是/Details/[id]

更新:
我可以看到学生被正确地保存,但是添加的模型验证没有。TempData只对一次访问有效,然后删除它的内容。因此,这段代码是您的主要问题:

if (TempData["Student"] != null)  // data is accessed and deleted
{
    // oopss.. nothing in TempData now
    student = TempData["Student"] as Student;
    TempData["Student"] = student; // needed to survive a browser refresh
} 
因此,您需要首先获取TempData并将其分配给某个对象,然后检查该变量:

var student = TempData["Student"] as Student;
if (student != null)  // we're ok now
{
    //....
}

可能重复我在那篇文章中更新了它,但错误仍然没有出现在页面上。我将在这个问题中更新我的示例,以便它与该示例保持一致,以防我遗漏了什么。@GSerg,第二个问题(未接受的问题)会让我更走运。因此,我需要弄清楚如何将其显示在验证摘要中,目前我必须将其与表单上显示的属性相关联。有趣的观察结果是,我最终使用了第二个答案,将填充TempData的逻辑移动到属性。有一件事我不明白,似乎即使在从TempData获得ID后根据ID填充Student,它仍然有效。看来我不需要我的if/else。我不确定为什么第二次填充Student不会覆盖从TempData中获取设置的内容。