PageData fails to pass data in WebMatrix - c#

I am building a website with WebMatrix. I would like users to enter their name in the main page and after redirection their name will be shown in the results of another form. But my code is not working.
This is a snippet of the main page:
#{
if (IsPost) {
PageData["fullname"] = String.Format("{0} {1}", Request.Form["mainForename"], Request.Form["mainSurname"]);
PageData["redir"] = Request.Form["goTo"];
}
}
<form name="mainForm" id="mainForm" method="post" action="foo.cshtml" onsubmit="return mainValid(this);">
<h2>Please enter your name:</h2>
<label for="mainForename" class="label">Forename:</label>
<input type="text" name="mainForename" id="mainForename">
<label for="mainSurname" class="label">Surname:</label>
<input type="text" name="mainSurname" id="mainSurname">
<input type="submit" name="goTo" value="Go to Form 1">
<input type="submit" name="goTo" value="Go to Form 2">
</form>
This is a snippet of the page that the main page directs to:
#{
if (IsPost) {
var display = PageData["fullname"];
}
}
<form name="form1" id="form1" method="post" onsubmit="return Valid(this);">
<!-- some HTML code -->
<input type="submit" name="submit" value="Get results">
<p>#Html.Raw(display)</p>
</form>
But whatever value I have submitted in the mainForm, PageData["fullname"] and PageData["redir"] seem to have no values. What is the problem?
Any help would be appreciated.

I think PageData is only useful when combining subpages into a single page.
Instead, try the Session object where you are using PageData. Session will be available for all that user's pages.
So where you have PageData["fullname"] use Session["fullname"]
For more details, see http://www.mikesdotnetting.com/article/192/transferring-data-between-asp-net-web-pages

I find something that's not quite good in your code:
Why your form action is set to a cshtml file? It has to be an action in a controler;
Why are you using "hardcoded" form tag? Use #using(#Html.BeginForm('name', 'action', 'controller'...)
Why do you need WebMatrix? 1st - its pretty old, 2nd it for grids - you have a form.
Use a model, and use #Html.TextBoxFor(x=>x.UserName) inside the #Html.BeginForm.
Then post the form in the action you are posting to redirect to another page that contains the 2nd Form, and have a model. The post action should look somehow like this
[HttpPost]
public ActionResult RedirectToAnotherForm(MyModel model)
{
return View('SecondFormView', new SecondFormModel{
userName = model.name
})
}

Related

How to post to the controller?

I am trying to post data from web form to the controller in my asp.net application so that I can authenticate the credentials which the user has enterted.
My code for the web form looks like this at the bottom of this code there is a submit button.
<form action="~/Controller" method="post">
<fieldset>
<legend> Enter your details</legend>
<div>
<label for="name ">name </label>
<input type="text" name="name" value=""/>
When I run the code and then press the submit button I get an error 405 which is because a HTTP method is not allowed. This is code I have in the controller file. Is the error because I have made a mistake in the web forms of its it because of a error in the controller file.
[HttpPost]
public void MyAction(string telephone, string emailadress, string name )
{
}
You can use tag-helpers, like seen below. documentation: https://learn.microsoft.com/en-us/aspnet/core/mvc/views/working-with-forms?view=aspnetcore-5.0
<form asp-controller="Home" asp-action="MyAction" method="post">
<!-- Input and Submit elements -->
</form>

Antiforgerytoken MVC C# search form

I have a search box on my site.
The controller looks like this:
[HttpPost]
[ValidateAntiForgeryToken]
public ActionResult SearchResults(SearchModel model)
{
View:
<div class="siteSearch clearfix" role="search">
<form id="HeaderSearchForm">
#Html.AntiForgeryToken()
<label for="tbSiteSearch">Search:</label>
<input type="text" id="tbSiteSearch" name="tbSiteSearch" class="text" />
<button type="submit" class="btn submit">
<i class="icon-search"></i>
</button>
</form>
</div>
So when I do a search, I can see the hidden label with the Anti Forgery Token present. This all works as expected because if I take a blank html page, copy the form code and leave the '__RequestVerificationToken' blank, I get told that the token hasn't been set and the search doesn't run. Which is what I would expect.
The issue I have is if I submit a search, copy the token from my site and place it in to my blank html page e.g.
<html>
<body>
<script>history.pushState('', '', '/')</script>
<form action="https://www.adomainname.co.uk/Search/SearchResults/" method="POST">
<input type="hidden" name="SearchTerm" value="testing" />
<input type="hidden" name="__RequestVerificationToken" value="theverificationtokengoeshere" />
<input type="submit" value="Submit request" />
</form>
</body>
</html>
The request is submitted - even if I am running the above code on localhost. I would have expected the form to not submit as it was coming from a different domain. Am I misunderstanding how this should work?
If I refresh the page and resubmit Im obviously allocated a new AFT and so the submit fails again but this doesn't feel right.
Ideally I would prefer the form action to only run on the domain it's on and not be able to execute the action from another site. I thought using AntiForgeryToken prevent Cross-Site Request Forgery.
If any of this is unclear, please let me know and I'll explain more.

ASP.NET MVC Alternate #URIaction methods in controller linked to radio button

I have two methods in my asp.net mvc controller which search the google maps Places API to perform an autocomplete action as the user types in text.
In the background I understand that the data-otf-autocomplete function uses JQUERY UI autocomplete in the background to call these methods on the form. I have to be honest and admit I don't fully understand the JQUERY UI piece as I have adapted it from another the OdetoCode sample from the AJAX lesson on Scott Allen's excellent Pluralsight course Building Applications with ASP.NET MVC4 (Great course btw). The original code from Scott's course linked to a local database to return JSON to complete an autocomplete function which I've adapted to connect to the Google MAPS Places API.
Right now I have two search boxes each linked to a different methods on the controller. One uses the locality search (best suited to approximate addresses, most rural addresses here in Ireland fall into that category) while another is suitable for exact street addresses.
Is it possible to wire these two up to a radio button control in my view so you have a single search box and depending on the radio button option selected (say locality/address) it automatically routes the request to the associated method controller
#model IPagedList<RestaurantListViewModel>
#{
ViewBag.Title = "Home Page";
}
<form method="get" action="#Url.Action("Index")"
data-otf-ajax="true" data-otf-target="#List">
<input type="search" name="searchTerm" data-otf-autocomplete="#Url.Action("Autocomplete_Address")" />
</form>
<form method="get" action="#Url.Action("Index")"
data-otf-ajax="true" data-otf-target="#List">
<input type="search" name="searchTerm" data-otf-autocomplete="#Url.Action("Autocomplete_Locality")" />
</form>
#Html.Partial("_Restaurants", Model)
Cant you just have the search box and 2 radio buttons beside it one for each search option.
<input type="radio" name="SearchType" value="local" checked>Locality
<input type="radio" name="SearchType" value="exact">Exact Address
You just need one form then, posting to a method in the controller, in the method check for the value of the radio button and run your logic based on this.
UPDATE
Razor View:
#using (Html.BeginForm("ControllerMethod", "YourController", null, FormMethod.Post))
{
<input type="radio" name="SearchType" value="local" checked>Locality
<input type="radio" name="SearchType" value="exact">Exact Address
}
ControllerMethod
[HttpPost]
public ActionResult ControllerMethod(FormCollection form)
{
var SearchType = form["SearchType"];
........
}
Fully working code using Stephen Muecke's suggestion
#model IPagedList<RestaurantListViewModel>
#{
ViewBag.Title = "Home Page";
}
<script type = "text/javascript" >
function ShowHideDiv() {
var chkAddress = document.getElementById("chkAddress");
var inputAddbox = document.getElementById("inputAddress");
inputAddbox.style.display = chkAddress.checked ? "block" : "none";
var chkLocality = document.getElementById("chkLocality");
var inputLocality = document.getElementById("inputLocality");
inputLocality.style.display = chkLocality.checked ? "block" : "none";
}
</script>
<form method="get" action="#Url.Action("Index")"
data-otf-ajax="true" data-otf-target="#restaurantList">
<div>
<input type="search" id="inputAddress" name="searchTerm" data-otf-autocomplete="#Url.Action("Autocomplete_Address")" checked/>
<input type="search" id="inputLocality" name="searchTerm" data-otf-autocomplete="#Url.Action("Autocomplete_Locality")" />
</div>
<label for="chkAddress">
<input type="radio" id="chkAddress" name="chkType" onclick="ShowHideDiv()" />
Search by Address
</label>
<label for="chkLocality">
<input type="radio" id="chkLocality" name="chkType" onclick="ShowHideDiv()" />
Search by Location
</label>
</form>
#section Scripts {
#Scripts.Render("~/bundles/jqueryval")
<script language="javascript">
$(document).ready(function () {
$("#inputLocality").hide();
$("#chkAddress").prop('checked', true);
});
</script>
}

Can't get input type="text" value in action on form submit?

In a Razor view I have input type="text", a hidden field and a button. I can access hidden field from Form collection but its weird I cant access input type="text" value inside my action. I am not sure if my understanding is correct or not but I was thinking as all fields inside form should be available inside action.
Below is my code please:
#using (Html.BeginForm())
{
<div style="margin-top: 40px;">
<input id="txtDateFrom" class="span2" size="16" value="#Model.StartDate.ToString("dd/MM/yyyy") " readonly="readonly" type="text">
#Html.Hidden("currencyCode", (object)ViewBag.currencyCode)
</div>
<button onclick="#Url.Action("ExchangeRateDetails", "ExchangeRate")" class="btn btn-lg span2 ARML50px">
}
I highly appreciate your time, guidance and help.
The reason your hidden input works is that you render this with help from the Html helper #Html.Hidden. This helper render the input field with the name attribute.
Your <input type="text"> is missing the name attribute. So try writing like this:
<input id="txtDateFrom" name="txtDateFrom" class="span2" size="16" value="#Model.StartDate.ToString("dd/MM/yyyy") " readonly="readonly" type="text" />
The name="txtDateFrom" will make the value appear in your FormCollection.
Try this way
You don't need onclick="#Url.Action("ExchangeRateDetails", "ExchangeRate")" to the button
Change your button for below way
<button type="submit" class="btn btn-lg span2 ARML50px">
And Now your controller can get the input text
[HttpPost]
Public ActionResult ExchangeRateDetails(YourmodelClass xxx)
{
string dates=Model.StartDate;
}
This website have lot and lot of answers for how to send a model values from view to controllers by see the Related discussion on this page right corner .

MVC3 Ajax.BeginForm OnSuccess Doesn't Run in Firefox

FINAL EDIT:
After following the answer from Darin Dimitrov, I have found that the problem ended up being that the AJAX call to the Controller's method UpdateForm() was returning an empty string. This was a modification that I found necessary some time ago after experiencing a different problem. Passing an empty string was causing Firefox's parser to choke (while Chrome and IE didn't care, apparently) so I replaced the empty string with an empty div.
Edit:
Thanks to Darin Dimitrov's suggestions below, I have found that the reason I was having trouble is due to an error being thrown whenever the form in question is being submitted.
The error reads "Node cannot be inserted at the specified point in the heirarchy". This is thrown each and every time the form is submitted. I noticed in the POST data that it seems to think this is an XMLHttpRequest. Is that the cause (the AJAX request in question is just returning HTML)? Here is the POST data from Firebug:
This error reads "XML Parsing Error -- No Element Found".
FYI - the HTML being returned is always an empty string...
I have an MVC3 application running on IIS7. In one of my views, I have a form being built using a Microsoft HTML helper function:
#using (Ajax.BeginForm("UpdateForm", new AjaxOptions { UpdateTargetId = "TargetDiv", InsertionMode = InsertionMode.InsertAfter, OnSuccess = "ClearTextBox" }))
{
#Html.TextArea("txtInput", new { id = "txtInput", cols = "20", rows = "5", wrap = "virtual" })
<input id="send" class="button" type="submit" value="Send"/><br />
}
This generates the following HTML when the Controller provides this view:
<form action="/RootName/ControllerName/UpdateForm" data-ajax="true" data-ajax-mode="after" data-ajax-success="ClearTextBox" data-ajax-update="#TargetDiv" id="form0" method="post">
<textarea cols="20" id="txtInput" name="txtInput" rows="5" wrap="virtual"></textarea>
<input id="send" class="button" type="submit" value="Send"><br>
</form>
What I'm basically trying to do here is take the text inside the TextArea called txtInput and append it to the end of the Div called TargetDiv whenever the Send button above is clicked and clear out the text from txtInput after the appending is complete by means of the ClearTextBox() method (Javascript). The append always works in every browser; and when I run in Internet Explorer or Chrome, the clearing of the text works just fine. However, Firefox doesn't seem to want to call the ClearTextBox() method.
Is Firefox not compatible with this data-ajax-success option in the form signature?
Things I've Tried
I found this guy:
Ajax.BeginForm doesn't call onSuccess
The solution is to add this script:
<script src="#Url.Content("~/Scripts/jquery.unobtrusive-ajax.js")" type="text/javascript"></script>
I am calling this script:
<script src="#Url.Content("~/Scripts/jquery.unobtrusive-ajax.min.js")" type="text/javascript"></script>
...but I tried swapping it out just in case. No joy.
I was asked to try changing the method call to include parentheses by some folks in the C# chat room so that the HTML came out like this:
<form action="/WebChat/TMWC/UpdateForm" data-ajax="true" data-ajax-mode="after" data-ajax-success="ClearTextBox()" data-ajax-update="#chatText" id="form0" method="post">
<textarea cols="20" id="txtInput" name="txtInput" rows="5" wrap="virtual"></textarea>
<input id="send" class="button" type="submit" value="Send"><br>
</form>
But that didn't help.
The folks in C# Chat also suggested I replace the Javascript call with an alert - something like this:
<form action="/WebChat/TMWC/UpdateForm" data-ajax="true" data-ajax-mode="after" data-ajax-success="alert('yo!')" data-ajax-update="#chatText" id="form0" method="post">
<textarea cols="20" id="txtInput" name="txtInput" rows="5" wrap="virtual"></textarea>
<input id="send" class="button" type="submit" value="Send"><br>
</form>
While Chrome pops the message box, Firefox does not!
Status no repro in a newly created ASP.NET MVC 3 application.
Controller:
public class HomeController : Controller
{
public ActionResult Index()
{
return View();
}
[HttpPost]
public ActionResult UpdateForm()
{
return Content(DateTime.Now.ToLongTimeString());
}
}
View (~/Views/Home/Index.cshtml):
<script src="#Url.Content("~/Scripts/jquery.unobtrusive-ajax.js")" type="text/javascript"></script>
<script type="text/javascript">
function ClearTextBox() {
$('textarea').val('');
}
</script>
<form action="/Home/UpdateForm" data-ajax="true" data-ajax-mode="after" data-ajax-success="ClearTextBox" data-ajax-update="#TargetDiv" id="form0" method="post">
<textarea cols="20" id="txtInput" name="txtInput" rows="5" wrap="virtual"></textarea>
<input id="send" class="button" type="submit" value="Send"><br>
</form>
<div id="TargetDiv"></div>
Works perfectly fine in Chrome, FF and IE.
Also you might want to ensure that the Content-Type response HTTP header matches the actual response that you are sending. For example I have seen so many people send the application/json response header with some invalid JSON in the response body which produces the more sensitive parsers to choke.

Categories