开发者

Difference between "normal postback" and "page creation as PreviousPage"

There are two scenarios for an ASP.net webforms page which I would like to differentiate between: "Normal postback" and when a page is created because the next page has called PreviousPage.

  • A normal posback occured for page 1
    • IsPostback is true
    • IsCrossPagePostBack is false

and

  • There was a Server.Transfer("page2.aspx") to page 2, and page 2 uses PreviousPage so page 1 is created virtually. For page 1:
    • IsPostback is true
    • IsCrossPagePostBack is false

You can see tha开发者_JS百科t IsPostBack and IsCrossPagePostBack do not help because they are the same in both cases.

The reason why I am asking this:

I have page 1 which sends data to page 2 via cross-page postback (PostBackUrl="page2.aspx" set in page 1). For all users who have javascript enabled, this works fine.

But I wanted also a fallback for the users who have javascript disabled. For them, a click on the submit button on page 1 does not lead to page 2 but to a postback to page 1. Page 1 could now detect this and do a Server.Transfer("page2.aspx") to page 2. The problem is: When page 2 uses PreviousPage then page 1 is created again and would do a Server.Transfer() again and again and again ...

My workaround for this is to do the Server.Transfer not in the Page_Load event but only in the Page_PreRender event because this event does only occur when it is a normal postback and not when the page is created as PreviousPage.

This workaround works but it is very dirty. If I could differentiate between the two scenarios already in the Page_Load event, it would be much better.

Is this possible?


When you do the HttpServerUtility.Transfer from Page 1 to Page 2, the HttpContext is then shared between Page 1 and Page 2. So normally, one request means one request handler (usually a page) and one request context. But in this case there's two handlers and one (shared) context. You can use the context to share information about the request between the two handlers.

So one solution may be that Page 1 puts all the data that page 2 needs in the HttpContext.Items. Then Page 2 first checks for this data. If present, Page 2 knows that control was transferred by way of Server.Transfer and that it should not call on Page 1 through PreviousPage. Instead it should now get its data from the context.

Page1.aspx

protected void Page_Load(object sender, EventArgs e)
{
    if(IsPostBack && HttpContext.Items.Contains("CrossPagePostBack") == false)
    {
       // Cross page postback did not succeed (JavaScript disabled)
       string name = NameTextBox.Text;
       HttpContext.Items.Add("Name", name);

       HttpContext.Items.Add("Transfer", true);
       Server.Transfer("Page2.aspx");
    }
}

Page2.aspx

protected void Page_Load()
{
    if(IsPostBack)
    {
        string name;
        if(CrossPagePostBack)
        {
            // Cross page postback succeeded (JavaScript was enabled)
            HttpContext.Items.Add("CrossPagePostBack", true);
            name = PreviousPage.NameTextBox.Text;
        }
        else if (HttpContext.Items.Contains("Transfer"))
        {
            // We got transferred to from Page1.aspx
            name = (string)HttpContext.Items["Name"];
        }

        // Do something with Page 1's form value(s)
    }
}

Or you can turn this around and let Page 2 add a mark ("Page 2 was here") to the HttpContext.Items, and then Page 1 checks that mark. If it's present it doesn't need to transfer again (break the loop). I'm not 100% sure if a call to PreviousPage also results in a shared request context.

Page1.aspx

protected void Page_Load(object sender, EventArgs e)
{
    if(IsPostBack && HttpContext.Items.Contains("CrossPagePostBack") == false)
    {
        // Cross page postback did not succeed (JavaScript disabled)
       if(HttpContext.Items.Contains("Transfer"))
       {
           // We did not yet transfer to Page 2
           HttpContext.Items.Add("Transfer", true);
           Server.Transfer("Page2.aspx");
       }
    }
}

Page2.aspx

protected void Page_Load()
{
    if(IsPostBack) 
    {        
        if(CrossPagePostback)
        {
            // Cross page postback succeeded (JavaScript enabled)
            HttpContext.Items.Add("CrossPagePostBack", true);
        }

        string name = PreviousPage.NameTextBox.Text;

        // Do something with Page 1's form value(s)
    }
}

The second method is simpler in implementation, especially if the form on Page 1 is complex. You'd have only one place where you read Page 1's form, and you only add a simple boolean to the HttpContext.Items.

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜