views:

150

answers:

3

I have a shared page in my ASP.NET MVC app that can be accessed from several different pages in my app. If I want the user to return to their original page after they have done their business on the shared page, what's the best way to figure out where the user was, and tell the app to go there?

Note that I'm currently doing this for the Cancel button on the shared page by telling onclick to use the page history:

<input type="button" value="Cancel" onclick="if (history.length == 0) { window.location='<%=Url.Action("Index", "Home") %>' } else {  history.back() }" />

but this won't work for Save if the shared page updates data displayed on the original page.

+1  A: 

try using:

System.Web.HttpContext.Current.Request.UrlReferrer

http://msdn.microsoft.com/en-us/library/system.web.httprequest.urlreferrer.aspx

Josh
I don't this this will work if you have to go back more than one step, i.e. the sub-page redirects to a new page for form validation or there are multiple sub pages to navigate through.
Dana the Sane
you could store it in session when you first load the page.
Josh
+1  A: 

Two ways I can think of are to store the url of the calling page in a hidden input element or as a argument in the current page's address. Both of these will survive refreshes or several steps of navigation, you just have to make sure that the variables are passed on to the next page.

Dana the Sane
A: 

Issues like this are why I'm more and more considering using a BaseViewModel class to inherit all of my view models from to store information that may be useful to have on any given page. I've been trying to come up with a complete class definition lately, but for these purposes it would probably be nice to have the follwing properties (posted part of this in an answer to a different question, I'll find a link in a bit):

public class BaseModel
{
    public string PageTitle { get; set; }
    public string PageDescription { get; set; }
    public string PageKeywords { get; set; } //maybe use a List<string> or string[] here
    public string ReturnPage { get; set; }
    //TBD: any other useful HTML page elements 
}

Then I could create a view model that inherits from this:

public class RandomViewModel : BaseViewModel
{
    RandomViewModel()
    {
        //set page properties
    }
}

Then in a service layer (preferably) or in a controller (may have to do it there, haven't tried this so can't be sure) you would have access to the ReturnPage property when constructing your model (in this example I'll assume you're doing this in the action):

public ActionResult RandomAction()
{
    RandomViewModel model = _serviceLayer.GetRandomViewModel();
    model.ReturnPage = this.HttpContext.Request.UrlReferrer;
    return View(model);  
}

Then in the view you would be able to do this:

<input type="button" value="Cancel" onclick="if (history.length == 0) { window.location='<%= Model.ReturnPage %>' } else {  history.back() }" />

This is all just kind of brainstorming, but I think it would work. The only big issue I'm not sure of is where you would want to set the referrer value. I would also try and get that onclick event out of the element and set it in the header if you can.

Hope this helps.

dhulk