Return 到倒数第二个 URL 在 MVC 中(return 查看应用了以前的过滤条件)?

Return to second to last URL in MVC (return View with previous filter conditions applied)?

我正在开发 MVC5 应用程序。主屏幕上有一个网格,允许用户查看数据并转移到多个视图以对每条记录执行各种操作。其中之一是 [EDIT].

我遇到的问题如下:由于数据量大,可以方便地向下过滤数据(比如特定位置),然后从那里编辑记录。此网格上的过滤器(来自 CodePlex 的 Grid.MVC)通过修改 URL(http://homeURL/?grid-filter=Location.DEPT__1__accounting)执行部分过滤,例如 1 为 Equals,2 为 Cotains,3 为 StartsWith,4 为 EndsWith然后在接下来的 2 个下划线之后是搜索条件。

这个功能很好,但是在 [POST] return 从编辑中用户当前 returned 到主索引视图,过滤条件仍然设置(强制他们一遍又一遍地添加过滤条件,然后再对具有相同条件的记录执行类似的编辑。

我的 POST-EDIT 方法当前设置为包括:

        if (ModelState.IsValid)
        {
            collection.MODIFIED_DATE = DateTime.Now;
            collection.MODIFIED_BY = System.Environment.UserName;

            db.Entry(collection).State = EntityState.Modified;
            await db.SaveChangesAsync();
            return RedirectToAction("Index", "Home");
        }

对于我的尝试,我首先想到的是 return 具有更新集合的视图 (return View(collection)) 但这当然只会让我回到 EDIT 视图,而不是主视图数据网格按先前指定的方式过滤。我考虑过在数据库中添加一个字段,例如 LAST_FILTERED_URL,但这感觉就像一个长得太大的创可贴。

有人知道解决这个问题的干净方法吗?


编辑:

我很早就想过按照 Andrea 的建议做一些类似的事情,但没有想到用重定向中传递的 url-filter 的参数进行显式重定向。下面是我当前的 GET/POST Edit:

代码
    // GET: ENITTY_Collection/Edit/5
    public async Task<ActionResult> Edit(int id)
    {
        if (id == null)
        {
            return new HttpStatusCodeResult(HttpStatusCode.BadRequest);
        }
        ENTITY_COLLECTION entity_Collection = await db.ENTITY_COLLECTION.FindAsync(id);
        if (entity_Collection == null)
        {
            return HttpNotFound();
        }

        // Other code for Controls on the View

        return View(entity_Collection);
    }

        // POST: ENTITY_Collection/Edit/5
        // To protect from overposting attacks, please enable the specific properties you want to bind to, for 
        // more details see http://go.microsoft.com/fwlink/?LinkId=317598.
        [HttpPost]
        [ValidateAntiForgeryToken]
        public async Task<ActionResult> Edit([Bind(Include = "Id,One_Id,Two_Id,Three_Id,Four_Id,Five_Id,Six_Id,field7,field8,field9,...field18,created_date,created_by,modified_date,modified_by")] ENTITY_COLLECTION entity_Collection)
        {
            if (ModelState.IsValid)
            {
                entity_Collection.MODIFIED_DATE = DateTime.Now;
                entity_Collection.MODIFIED_BY = System.Environment.UserName;

                db.Entry(entity_Collection).State = EntityState.Modified;
                await db.SaveChangesAsync();
                //return RedirectToAction("Index", "Home");
                return View(entity_Collection);
            }

            // Other code for if Model is Invalid before returning to View.

            return View(entity_Collection);
        }

我喜欢 Andrea 的建议,但我仍然需要一种好的方法来存储用户在首次导航到 GET-Edit View 时拥有的 URL,然后使用过滤后的 URL当 POST-Edit 完成并且更改已保存时,return 用户到先前位置和过滤器选项的值。

有什么想法吗?

您是否尝试过将当前过滤器的传递更改为重定向到操作,如下所示? 注意:我假设:

  1. 您正在重定向到同一个控制器
  2. 您有一个名为 currentFilterValue

    的控制器参数

    RedirectToAction("Index", "Home",new { grid-filter = currentFilterValue });

Microsoft MVC 项目的默认 LoginController 包括一组使用 returnUrl 参数的方法。使用这种做法,您可以在打开编辑器时包含一个 return URL,当编辑完成时,return 会让用户返回到过滤器完好无损的前一个屏幕(假设它们是在 URL).

我的视图模型基础 class 有一个 属性 用于存储 ReturnURL,然后将其存储为隐藏项(如果已设置)。

@Html.HiddenFor(model => model.ReturnUrl)

我从编辑中发布的操作具有以下逻辑:

if (viewModel.ReturnUrl.IsNotNullOrEmptyTrimmed())
{
    return RedirectToLocal(viewModel.ReturnUrl, "ActionName", "ControllerName");
}
else
{
    // Default hard coded redirect
}

为了防止某些注入,您需要这样的验证方法(上面调用)以确保 URL 有效:

protected ActionResult RedirectToLocal(string returnUrl, string defaultAction, string defaultController)
{
    try
    {
        if (returnUrl.IsNullOrEmptyTrimmed())
            return RedirectToAction(defaultAction, defaultController);

        if (Url.IsLocalUrl(returnUrl))
            return Redirect(returnUrl);

        Uri returnUri = new Uri(returnUrl);
        if (Url.IsLocalUrl(returnUri.AbsolutePath))
        {
            return Redirect(returnUrl);
        }
    }
    catch
    {
    }

    return RedirectToAction(defaultAction, defaultController);
}

希望这能为您带来一些想法并走上正确的道路。

我不确定这是否是我所追求的最正确的方法,但似乎对我有用的是使用 Session 值。

在我的 GET 方法中,我存储 URL:

Session["returnURL"] = Request.UrlReferrer.AbsoluteUri;

然后在我的 POST 中,我在 Redirect() 中使用这个值保存对记录的更改:

var returnURL = (Session["returnURL"] != null) ? Session["returnURL"].ToString() : Url.Action("Index", "Home");
return Redirect(returnURL);

到目前为止,所有初始测试都导致 return 到主视图,所有 sorting/filtering 条件都已到位,然后才输入记录进行更新。