簡體   English   中英

C# ASP.NET MVC 返回上一頁

[英]C# ASP.NET MVC Return to Previous Page

我的控制器中有一個基本的 Edit 方法,當編輯成功時,它會重定向回頂級列表(“索引”)。 MVC 腳手架后的標准行為。

我正在嘗試更改此 Edit 方法以重定向回上一頁(而不是 Index)。 由於我的 Edit 方法沒有使用默認的映射輸入參數“id”,我首先嘗試使用它來傳遞前一個 URL。

在我的 Edit “get” 方法中,我使用這一行來獲取以前的 URL,它工作正常:

ViewBag.ReturnUrl = Request.UrlReferrer;

然后我使用我的表單標簽將這個返回 URL 發送到 Edit “post” 方法,如下所示:

@using (Html.BeginForm(new { id = ViewBag.ReturnUrl }))

現在這是輪子掉下來的地方。 我無法從 id 參數正確解析出 URL。

*** 更新:已解決 ** *

使用 Garry 的示例作為指導,我將參數從“id”更改為“returnUrl”並使用隱藏字段來傳遞我的參數(而不是表單標簽)。 經驗教訓:僅使用“id”參數的預期用途並保持簡單。 它現在有效。 這是我帶注釋的更新代碼:

首先,我像第一次一樣使用 Request.UrlReferrer 獲取前一個 URL。

    //
    // GET: /Question/Edit/5

    public ActionResult Edit(int id)
    {
        Question question = db.Questions.Find(id);
        ViewBag.DomainId = new SelectList(db.Domains, "DomainId", "Name", question.DomainId);
        ViewBag.Answers = db.Questions
                            .AsEnumerable()
                            .Select(d => new SelectListItem
                            {
                                Text = d.Text,
                                Value = d.QuestionId.ToString(),
                                Selected = question.QuestionId == d.QuestionId
                            });
        // Grab the previous URL and add it to the Model using ViewData or ViewBag
        ViewBag.returnUrl = Request.UrlReferrer;
        ViewBag.ExamId = db.Domains.Find(question.DomainId).ExamId;
        ViewBag.IndexByQuestion = string.Format("IndexByQuestion/{0}", question.QuestionId);
        return View(question);
    }

我現在使用表單中的隱藏字段將模型中的 returnUrl 參數傳遞給 [HttpPost] 方法:

@using (Html.BeginForm())
{
    <input type="hidden" name="returnUrl" value="@ViewBag.returnUrl" />
    ...

在 [HttpPost] 方法中,我們從隱藏字段中提取參數並重定向到它......

    //
    // POST: /Question/Edit/5

    [HttpPost]
    public ActionResult Edit(Question question, string returnUrl) // Add parameter
    {
        int ExamId = db.Domains.Find(question.DomainId).ExamId;
        if (ModelState.IsValid)
        {
            db.Entry(question).State = EntityState.Modified;
            db.SaveChanges();
            //return RedirectToAction("Index");
            return Redirect(returnUrl);
        }
        ViewBag.DomainId = new SelectList(db.Domains, "DomainId", "Name", question.DomainId);
        return View(question);
    }

我假設(如果我錯了,請糾正我)如果編輯失敗,您想重新顯示編輯頁面,為此您正在使用重定向。

通過再次返回視圖而不是嘗試重定向用戶,您可能會更幸運,這樣您也可以使用 ModelState 輸出任何錯誤。

編輯:

根據反饋更新。 您可以將之前的 URL 放在 viewModel 中,將其添加到隱藏字段,然后在保存編輯的操作中再次使用它。

例如:

public ActionResult Index()
{
    return View();
}

[HttpGet] // This isn't required
public ActionResult Edit(int id)
{
   // load object and return in view
   ViewModel viewModel = Load(id);

   // get the previous url and store it with view model
   viewModel.PreviousUrl = System.Web.HttpContext.Current.Request.UrlReferrer;

   return View(viewModel);
}

[HttpPost]
public ActionResult Edit(ViewModel viewModel)
{
   // Attempt to save the posted object if it works, return index if not return the Edit view again

   bool success = Save(viewModel);
   if (success)
   {
       return Redirect(viewModel.PreviousUrl);
   }
   else
   {
      ModelState.AddModelError("There was an error");
      return View(viewModel);
   }
}

您的視圖的 BeginForm 方法也不需要使用此返回 URL,您應該能夠逃脫:

@model ViewModel

@using (Html.BeginForm())
{
    ...
    <input type="hidden" name="PreviousUrl" value="@Model.PreviousUrl" />
}

回到發布到錯誤 URL 的表單操作,這是因為您將 URL 作為 'id' 參數傳遞,因此路由會自動使用返回路徑格式化您的 URL。

這將不起作用,因為您的表單將發布到不知道如何保存編輯的控制器操作。 您需要先發布到您的保存操作,然后處理其中的重定向。

對於ASP.NET Core,您可以使用 asp-route-* 屬性:

<form asp-action="Login" asp-route-previous="@Model.ReturnUrl">

一個例子:假設你有一個帶有動作的 Vehicle Controller

指數

細節

編輯

並且您可以從索引或詳細信息編輯任何車輛,因此如果您單擊從索引編輯,則必須在編輯后返回索引,如果單擊從詳細信息編輯,則必須在編輯后返回詳細信息。

//In your viewmodel add the ReturnUrl Property
public class VehicleViewModel
{
     ..............
     ..............
     public string ReturnUrl {get;set;}
}



Details.cshtml
<a asp-action="Edit" asp-route-previous="Details" asp-route-id="@Model.CarId">Edit</a>

Index.cshtml
<a asp-action="Edit" asp-route-previous="Index" asp-route-id="@item.CarId">Edit</a>

Edit.cshtml
<form asp-action="Edit" asp-route-previous="@Model.ReturnUrl" class="form-horizontal">
        <div class="box-footer">
            <a asp-action="@Model.ReturnUrl" class="btn btn-default">Back to List</a>
            <button type="submit" value="Save" class="btn btn-warning pull-right">Save</button>
        </div>
    </form>

在您的控制器中:

// GET: Vehicle/Edit/5
    public ActionResult Edit(int id,string previous)
    {
            var model = this.UnitOfWork.CarsRepository.GetAllByCarId(id).FirstOrDefault();
            var viewModel = this.Mapper.Map<VehicleViewModel>(model);//if you using automapper
    //or by this code if you are not use automapper
    var viewModel = new VehicleViewModel();

    if (!string.IsNullOrWhiteSpace(previous)
                viewModel.ReturnUrl = previous;
            else
                viewModel.ReturnUrl = "Index";
            return View(viewModel);
        }



[HttpPost]
    public IActionResult Edit(VehicleViewModel model, string previous)
    {
            if (!string.IsNullOrWhiteSpace(previous))
                model.ReturnUrl = previous;
            else
                model.ReturnUrl = "Index";
            ............. 
            .............
            return RedirectToAction(model.ReturnUrl);
    }

我知道這已經很晚了,但也許這會對其他人有所幫助。

我使用取消按鈕返回到引用 url。 在視圖中,嘗試添加以下內容:

@{
  ViewBag.Title = "Page title";
  Layout = "~/Views/Shared/_Layout.cshtml";

  if (Request.UrlReferrer != null)
  {
    string returnURL = Request.UrlReferrer.ToString();
    ViewBag.ReturnURL = returnURL;
  }
}

然后你可以像這樣設置你的按鈕 href:

<a href="@ViewBag.ReturnURL" class="btn btn-danger">Cancel</a>

除此之外,Jason Enochs 的更新效果很好!

這只是您可以申請 ASP NET MVC 的另一個選項。

通常你應該為每個Controller類使用BaseController類。

所以在它的構造函數方法內部執行以下操作。

public class BaseController : Controller
{
        public BaseController()
        {
            // get the previous url and store it with view model
            ViewBag.PreviousUrl = System.Web.HttpContext.Current.Request.UrlReferrer;
        }
}

現在在任何視圖中你都可以這樣做

<button class="btn btn-success mr-auto" onclick="  window.location.href = '@ViewBag.PreviousUrl'; " style="width:2.5em;"><i class="fa fa-angle-left"></i></button>

享受!

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM