Reputation: 17156
I have some html form on my view which has to be posted to some external site:
Html form on my view
<form action="http:\\externalsite\external-site-action" method="POST">
<input type="text" name="parameter1" value="someValue1"/>
<input type="text" name="parameter2" value="someValue1"/>
<input type="submit" value="Submit to external site">
</form>
When I post data to external-site-action this action redirects me to some other external site's page so I need user to be stayed there. But before this form is posted I have to perform some action/method in my controller, but this action is just making some changes in database, so I do not need any redirections or action results, otherwise user has to be redirected to external site page, data is posted to. How can I perform database changes in my action and make this form posted programatically to external site and redirect user to this external site (on the same browsers tab) in controllers action like below:
public ActionResult ChangeDBPostAndRedirectToExternal(string parameter1, string parameter2)
{
DoSomeDatabaseStuff();
PostParametersToExternalSiteAndRedirectUserToPageDataPostedTo();
}
I tried Redirect() method, but this method cannot perform post action. So how can I post data via my controller's action to external action and get external action's view result with handled posted data? Or is there some wiser approach to achieve what I need? I have to DoSomeDatabaseStuff();
before POST.
Upvotes: 1
Views: 4634
Reputation: 181
This is done a lot in Single Sign-On Identity Providers, one idea, that involves no-Ajax, it's to make a simple post to your action and make all your business logic, then on the view "activate" a call to a javascript function that make the second post to the external url.
For example:
public ActionResult ChangeDBPostAndRedirectToExternal(string parameter1, string parameter2)
{
DoSomeDatabaseStuff();
ViewBag.PostViaJs = String.Format("post_to_url('{0}','{1}', '{2}');", externalUrl, parameter1, parameter2);
}
Then print this call in the view:
<script type="text/javascript">
function post_to_url(path, parameter1, parameter2) {
var form = document.createElement("form");
form.setAttribute("method", "POST");
form.setAttribute("action", path);
form.setAttribute("target", "_blank");
var hiddenField = document.createElement("input");
hiddenField.setAttribute("type", "hidden");
hiddenField.setAttribute("name", "parameter1");
hiddenField.setAttribute("value", parameter1);
//add another hidden field for parameter2
form.appendChild(hiddenField);
document.body.appendChild(form);
form.submit();
}
@ViewBag.PostViaJs
</script>
Upvotes: 1
Reputation: 77536
You should use JS/AJAX and a normal (non-submit) button. Hook up your button to issue an AJAX call to DoSomeDatabaseStuff
on your own server. Once that ajax call completes, call form.submit()
in Javascript (where form
is a DOM reference to your actual form) to allow the normal POST behavior to proceed (user will end up on the external site).
Here's some contrived sample jQuery code:
$('#your-non-submit-button').click(function() {
$.ajax({
url: '@Url.Action("ChangeDBPost")',
contentType: 'application/json; charset=utf-8',
data: JSON.stringify({ 'parameter1': $('input[name="parameter1"]').val(), ... }),
success: function(result) {
$('form').submit();
}
});
});
Upvotes: 1