Comment rediriger vers l'action précédente dans ASP.NET MVC?

122

Supposons que j'ai quelques pages

  • some.web/articles/details/5
  • some.web/users/info/bob
  • some.web/foo/bar/7

qui peut appeler un contrôleur d'utilité commun comme

locale/change/es ou authorization/login

Comment puis-je obtenir ces méthodes ( change, login) pour redirigent aux actions précédentes ( details, info, bar) en passant les paramètres précédents pour les ( 5, bob, 7)?

En bref: comment rediriger vers la page que je viens de visiter après avoir effectué une action dans un autre contrôleur?

adolfojp
la source

Réponses:

156

essayer:

public ActionResult MyNextAction()
{
    return Redirect(Request.UrlReferrer.ToString());
}

Sinon, en touchant à ce que dit Darin, essayez ceci:

public ActionResult MyFirstAction()
{
    return RedirectToAction("MyNextAction",
        new { r = Request.Url.ToString() });
}

puis:

public ActionResult MyNextAction()
{
    return Redirect(Request.QueryString["r"]);
}
Nathan Ridley
la source
Juste une suggestion: vous pouvez utiliser "Redirect" explicitement, c'est plus difficile de tester unitaire votre contrôleur. Vous feriez mieux d'utiliser un "RedirectToAction" à la place.
Syd
Je vous recommande d' utiliser Request.Url.AbsolutePath.ToString()comme AccountControllerde » LogOnla méthode contient des contrôles pour le début de l' URL avec '/', etc.
fulvio
1
@gotnull Request.Url.AbsolutePath redirigera vers la même action. Ce qui n'est pas la sortie souhaitée. Nous devons revenir à l'avant-dernière action. Pour cela, nous pourrions écrire: return Redirect (ControllerContext.HttpContext.Request.UrlReferrer.ToString ());
Rahatur
22
@nathanridley: cela ne fonctionne pas pour les requêtes POST. Dites que l'utilisateur est GET Indexalors GET Edit. L'URL de référence est alors, Indexmais lorsque l'utilisateur le fait, POST Editle référent provient désormais Editde la requête GET précédente. Comment puis-je m'assurer de POST Editconnaître l'URL à laquelle l'utilisateur a référé GET Edit?
one.beat.consumer
UrlReferrer est NULL lorsque j'étais dans une page et que je veux voir une erreur que je sais avoir simplement en entrant l'URL dans la barre d'adresse. Pourquoi lorsque j'entre une URL dans la barre d'adresse, il ne peut pas déterminer UrlReferrer?
QMaster
46

Si vous souhaitez rediriger à partir d'un bouton dans la vue, vous pouvez utiliser:

@Html.ActionLink("Back to previous page", null, null, null, new { href = Request.UrlReferrer})
Inconnu
la source
28

Si vous n'êtes pas concerné par les tests unitaires, vous pouvez simplement écrire:

return Redirect(ControllerContext.HttpContext.Request.UrlReferrer.ToString());
Rahatur
la source
9

Une suggestion sur la façon de procéder de telle sorte que:

  1. l'url de retour survit à la demande POST d'un formulaire (et à toutes les validations ayant échoué)
  2. l'URL de retour est déterminée à partir de l'URL de référence initiale
  3. sans utiliser TempData [] ou autre état côté serveur
  4. gère la navigation directe vers l'action (en fournissant une redirection par défaut)

.

public ActionResult Create(string returnUrl)
{
    // If no return url supplied, use referrer url.
    // Protect against endless loop by checking for empty referrer.
    if (String.IsNullOrEmpty(returnUrl)
        && Request.UrlReferrer != null
        && Request.UrlReferrer.ToString().Length > 0)
    {
        return RedirectToAction("Create",
            new { returnUrl = Request.UrlReferrer.ToString() });
    }

    // Do stuff...
    MyEntity entity = GetNewEntity();

    return View(entity);
}

[AcceptVerbs(HttpVerbs.Post)]
public ActionResult Create(MyEntity entity, string returnUrl)
{
    try
    {
        // TODO: add create logic here

        // If redirect supplied, then do it, otherwise use a default
        if (!String.IsNullOrEmpty(returnUrl))
            return Redirect(returnUrl);
        else
            return RedirectToAction("Index");
    }
    catch
    {
        return View();  // Reshow this view, with errors
    }
}

Vous pouvez utiliser la redirection dans la vue comme ceci:

<% if (!String.IsNullOrEmpty(Request.QueryString["returnUrl"])) %>
<% { %>
    <a href="<%= Request.QueryString["returnUrl"] %>">Return</a>
<% } %>

la source
9

Dans Mvc en utilisant le html brut dans la page d' affichage avec le script java onclick

<input type="button" value="GO BACK" class="btn btn-primary" 
onclick="location.href='@Request.UrlReferrer'" />

Cela fonctionne très bien. l'espoir aide quelqu'un.

@JuanPieterse a déjà répondu en utilisant @Html.ActionLinkdonc si possible quelqu'un peut commenter ou répondre en utilisant@Url.Action

shaijut
la source
6

Passez un paramètre returnUrl (URL encodée) aux actions de modification et de connexion et redirigez vers l'intérieur de cette returnUrl donnée. Votre action de connexion peut ressembler à ceci:

public ActionResult Login(string returnUrl) 
{
    // Do something...
    return Redirect(returnUrl);
}
Darin Dimitrov
la source
5

J'utilise .Net Core 2 MVC, et celui-ci a fonctionné pour moi, dans l'utilisation du contrôleur HttpContext.Request.Headers["Referer"];

Saad Hasan
la source
1

Vous pouvez revenir à la page précédente en utilisant la ViewBag.ReturnUrlpropriété.

Almaceleste
la source
1

Pour construire dynamiquement le returnUrl dans n'importe quelle vue, essayez ceci:

@{
    var formCollection =
        new FormCollection
            {
                new FormCollection(Request.Form),
                new FormCollection(Request.QueryString)
            };

    var parameters = new RouteValueDictionary();

    formCollection.AllKeys
        .Select(k => new KeyValuePair<string, string>(k, formCollection[k])).ToList()
        .ForEach(p => parameters.Add(p.Key, p.Value));
}

<!-- Option #1 -->
@Html.ActionLink("Option #1", "Action", "Controller", parameters, null)

<!-- Option #2 -->
<a href="/Controller/Action/@[email protected](ViewContext.RouteData.Values["action"].ToString(), ViewContext.RouteData.Values["controller"].ToString(), parameters)">Option #2</a>

<!-- Option #3 -->
<a href="@Url.Action("Action", "Controller", new { object.ID, returnUrl = Url.Action(ViewContext.RouteData.Values["action"].ToString(), ViewContext.RouteData.Values["controller"].ToString(), parameters) }, null)">Option #3</a>

Cela fonctionne également dans les pages de mise en page, les vues partielles et les aides Html

Connexes: URL de retour dynamique MVC3 (identique mais à partir de n'importe quel contrôleur / action)

Matthew Hudson
la source
0

Pour ASP.NET Core, vous pouvez utiliser l'attribut asp-route- *:

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

Autre exemple en détails: imaginez que vous avez un contrôleur de véhicule avec des actions

Indice

Détails

Éditer

et vous pouvez modifier n'importe quel véhicule à partir de l'index ou des détails, donc si vous avez cliqué sur modifier à partir de l'index, vous devez revenir à l'index après la modification et si vous avez cliqué sur modifier à partir des détails, vous devez revenir aux détails après la modification.

//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>

Dans votre contrôleur:

// 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);
    }
Mohamed Elamin
la source