make action method only accessible through redirect - asp.net

I'm trying to submit a form. When the form is submitted I want the form to dissapear and the text Thanks for your support. An e-mail will be sent to you as soon as possible. to show.
I think the most logical way to go by this is by making the form submit to the action SaveMessage() that redirects to the action RedirectToAction("MessageSaved") that returns the view with the message. If it isn't, please say so. This is for practice.
The problem is that the message can be viewed as well by going to /Support/MessageSaved. How do I prevent users from accessing it by url, but make the action accessible by redirectToAction()?

Set a value in TempData before the redirect. In the MessageSaved action method, check for that value before showing the form. Otherwise, redirect to another page.

Related

Back Button History: Skipping Page After POST

Move backward through history skipping the same page with different query string
The above is similar to my question, but I'll be more specific as mine concerns POSTs:
Scenario:
User is on Product Listing page. (Shorts.aspx)
User picks a product and navigates to product detail page (Best-Cargo-Shorts.aspx)
User clicks add to cart which performs postback (POST) of form to same page. (Best-Cargo-Shorts.aspx) -- this now shows Details page again, but with an Added TO Cart message at the top.
Current Behavior:
After the Add TO Cart form post; when the user clicks the Back button they navigate back to the "pre-post" version of the same page.
Desire:
When a user clicks the BACK button, I'd like it to go to Shorts.aspx, NOT Best-Cargo-Shorts.aspx, effectively Skipping the "pre-POST" page, or more accurately NOT STORING the 2nd POSTed page (Best-Cargo-Shorts.aspx).
Furthermore, I always want to avoid that "Page Content Expired" message. I just never want the POSTed version of the page in history. In this way, the following could also be true.
Shorts.aspx > Best-Cargo-Shorts.aspx > Best-Cargo-Shorts.aspx [POST] > Cart.aspx
If on cart and BACK button is pressed, I want the browser to navigate to Best-Cargo-Shorts.aspx (without the POST).
Is this possible with C#? Furthermore, is there a non-javascript solution?
Thanks.
One common way of handling this is the Post-Redirect-Get pattern.
In essence, the target of a POST request always responds with a 303 See Other (if HTTP 1.1) or 302 Moved Temporarily (if HTTP 1.0) status code redirecting the request as a GET, and usually eliminating the expired POST page from history. Potential downsides include the form parameters possibly remaining attached to the GET as a query string, and I've no clue how well it would (or wouldn't) integrate with ASP.Net Forms, MVC, or other web frameworks.
Generally, you should be using the post-redirect-get pattern, i.e. after the user adds the item to the card using POST, redirect him to Best-Cargo-Shorts.aspx with 302.
Now to your question, I would use Ajax for the post. I cannot think of a cross-browser way to achieve the desired behaviour using only server side code.

Drupal: send output to user in form's submit handler, instead of redirecting

I have this basic Drupal scenario and question:
I have a form which accepts some input from user, and a submit handler which should process data and show the result to user. In other words, I don't write anything in database or set e variables etc., just show some output to user.
I was wondering how I can do this, because a submit handler redirects the flow to another menu item -which the form values ($form_state) are not available anymore. Redirecting form to itself is not useful, because I just receive the raw posted inputs -not processed $form_state.
How can I prevent the redirection and just show some output to user in submit handler?
Thank you.
When you are building your form you want to set re-direct to false:
$form['#redirect'] = FALSE;
There is more on redirect here: http://api.drupal.org/api/drupal/developer--topics--forms_api_reference.html/6#redirect
If I have understood your question correctly this is what you are after.

ASP.NET page redirection / crosspost

I have 3 asp.net pages: Search.aspx, Results.aspx and Login.aspx.
Now I want anonymous users to be able to search, so everyone can use search.aspx. This page calls
Server.Transfer(Results.aspx)
and therefore shows the results. Now when the user is not logged in, a link to the login page is displayed on the Results page. The problem is:
After the login, I want the user to be redirected automatically to the Results page. However I do not succeed so, as the PreviousPage property of Login.aspx is always null. And when I use
Request.UrlReferrer.LocalPath
it's the link to Search.aspx but not Results.aspx.
Also, when the user is on the Results page, how do I enable him to go back by clicking a link and all his search input criteria (like in textboxes) on the Search.aspx is still there so he can refine the search after having seen the results? Whenever I send the user back, all user input is lost.
I still haven't figured out if I should use a normal hyperlink, a linkbutton and how to retrieve the previous page url or preserve the input data.
I can use AJAX if that is any help, but a "pure" asp.net solution would be preferred.
When you do a Server.Transfer it is a serverside redirect...meaning the client still sees the original URL. You need to post the search criteria to the results page, store them locally, show the login link. When they are logged in you can redirect to the results page and rehydrate the search critera and show the results.
Try using Response.Redirect("url") instead of Server.Transfer. When you use Server.Transfer, the url on the client will remain the Search page and not actually redirect to the Results.
You can use User.Identity.IsAuthenticated to check if the user is logged in and show/hide the login button based on that.
To keep values for the page, you could store them in Session, then have the Search page look for them and, if they exist, place them in the controls.
You can also embed the URL you want to return to after login into the querystring if you want.

ASP.NET MVC partial views and redirecting

I have a partial view called Login.ascx that has my login boxes that I include on a number of pages throughout my site. It works fine when the information is correct but I'm trying to do validation so if the login info is incorrect, I want to redirect the user back to the view they were in before to show them the login errors. What is the correct way of saying, return to the view you came from?
If a login fails from any page, I think I would direct them to a login view for the errors instead of the previous page. A dedicated login page is likely to have more UI space to display errors, etc. than a login control on another page. Having said that, you may want to include a returnUrl parameter to the Login action so that when the login is actually successful, the user is directed back to the place they were (or were attempting to get to).
Sounds like instead of asking how I do this, you should be asking yourself WHY am I doing it this way. Maybe it's a design decision rather than a technical question.
Though if you're really going to have one controller actions for multiple login pages you can try...
return Redirect(Request.UrlReferrer.ToString());
Or keep the route name in TempData and just use a RedirectToRoute(TempData["LoginRoute"]);
Both solutions have a bad code smell though.
Note that if you're not checking for cross-site injections that is just going to refer back to the other site. You may want to do some validation on the referring URL.
For the built-in Login method of the AccountController there is a parameter named returnUrl which you can use like so:
Return Redirect(returnUrl);
or
Return RedirectToAction(returnUrl);
if you specify the returnUrl parameter as a valid actionlink.
I recently had similar problems - you might be able to find something here...

How do I remove a page from the browser history?

I have an have an ASP.Net page which contains a button. This Page contains a ServerSide Paypal button.
When pushed my server does various clever things on the back end and then rewrites the response as a form and some javascript which posts this form to paypal..
This all works great.
However, if the user then elects to click back, they will arrive at my generated self-posting form and that will forward them again to Paypal.
I thought if I could find a way to have my generated form page not exist in the history, then this will solve my problem. but I have no idea how to correct this.
How can I remove my page from the history or just have it never appear?
Update: Thanks to all... Those are some great answers. Upvoted all good ones but went with splattne on account of clever use of hidden field rather than cookies for basis of decision.
window.location.replace(URL);
window.location:
replace(url)
Replace the current document with the
one at the provided URL. The
difference from the assign() method is
that after using replace() the current
page will not be saved in session
history, meaning the user won't be
able to use the Back button to
navigate to it.
I'm not sure if that can be done. But here is an idea how you could prevent that resubmit of the form.
You could insert a hidden input in your form which at the beginning would be empty. On submit you'll write a value in that field and make sure you check on every submit attempt if this field is empty.
If it is not empty on submit you know that the form was previously sent and you could warn the user.
As a web application, you'll never have full control of the user's browser. Even if there was a way to instruct the browser to not store the page in history, which I doubt, you can't be sure it'll work. For example, a clever user could tweak an open-source browser to store every page in history, no matter what.
I think you should try to approach the problem from another angle. You could, for example, detect that it's the same form which is being forwarded and not send it to paypal the second time. The important thing is to do it server-side.
Perhaps you could set a cookie before submitting the form.
When the page is loaded, check for the existence of that cookie (meaning the form was already submitted). If found, instead of automatically submitting the form, automatically go back (window.history.back()) again.
I'm not sure if you can do this easily with PayPal integration, but the
"Post / Redirect / Get" pattern can be used to address this problem
A useful Hint for some might be this...
window.history.go(-2);
particularly in the advent of a load failure warning popup.
You could simply programme your page not to submit, or to do something / navigate somewhere else, if window.referer is the Paypal page you are trying to avoid invoking a second time.
protected void Page_Load(object sender, EventArgs e)
{
Page.RegisterClientScriptBlock("", "<script>if(history.length>0)history.go(+1);</script>");
}

Resources