MVC Controller View Javascript and passing values - javascript

I have a view that displays both the search screen and the results list. To start the results list is hidden.
On clicking the search button, instead of the view posting back to the controller using a Html.BeginForm, it has a JavaScript event handler which is called.
The Handler passes over a complex object, in the form of:
{ "searchData":
{ "ticketNumberCompare":0,
"ticketSearchTextFrom":"0",
"ticketSearchTextTo":null,
"ticketDateCompare":1,
"startDate":"2017-01-06T00:00:00",
"endDate":"2017-01-13T00:00:00",
...
etc
...
},
"searchMode":
{ "mode":2,
"pageNumber":1,
"pageSize":5,
"sortDirection":"desc",
...
etc
...
"ValidationErrorMessages":null
}
}
By using Json.Stringify, I have got the above structure to be converted for use by a function within the c# MVC 5 controller, defined as follows.
[HttpPost]
public JsonResult GetSearchResultsJson(ComplexObject searchCriteria, int? page)
{
}
This function returns back html which is rendered from a Razor view using a model that contains the results from the database.
When I click on the submit button for the initial search all works and I get a partial view of five records displayed with the correct pageList values displayed.
When I click on the pageList items I get a page not found error.
On checking the ajax call for the initial load it is passing over the Json.Stringify of the structure at the top of this question. But the pageList items are not, they just pass over the page
Addendum:
Oh I forgot to mention that I have upgraded this function to use an object instead of the four string that used to be passed, because a new super search now has around 30 properties. Before the change the code worked fine.

Related

MVC 5 PartialView update with AJAX not updating View?

I'm in the process of getting my head wrapped around using AJAX to update a portion of an MVC View using some conditional logic. I posted the question earlier and was pointed to using PartialView to build out the whole HTML table and then pass that back to the View.
That lead me to use this article and an example.
https://www.red-gate.com/simple-talk/dotnet/asp-net/revisiting-partial-view-rendering-in-asp-net-mvc/
I then pulled out my table code and put it in a Partial View. All that worked just fine. However, now I'm trying to update with AJAX and the actual updating of the database is working but the updating of the View is not.
In other words, when I click on the "Test" button in the code below I can see it going to the HttpPost in the controller as well as seeing the database being updated. However, the page doesn't get updated. I have to refresh the page again to see the change.
I'm betting it has to do with the #Html.Partial call in the View but I'm not figuring out what I need to do to fix it.
From what I've read it sounds as though when I make the AJAX call and it returns the HTML it should replace everything in side of my DIV.
Here is what I have in my View. Upon initially viewing the page the #Html.Partial is populating the table as expected.
<div id="exceptionTable">
#Html.Partial("_DailyLogExceptionsTable", Model.listExceptions)
</div>
Here is my AJAX call. I can see the values coming through. The RID is the record ID and the arg would be a static value of either "A" or "D" depending on which button they will click.
function ApproveDeny(rid, arg) {
var url = "/Exception/ExceptionApproveDeny/";
$.post(url, {rid:rid, arg:arg})
.done(function (response) {
$("#exceptionTable").html(response);
})
};
This is my ActionResult which updates the database through the DAL. Then I create a new ViewModel, call get the new list of Exceptions, and then call the PartialView again passing it the new list of exceptions.
public ActionResult ExceptionApproveDeny(int rid, string arg, string shift)
{
try
{
DAL.ExceptionApproveDeny(rid, arg);
var vm = new ExceptionLogDailyTableViewModel();
vm.listExceptions = DAL.GetEmployeeExceptionsByDate(CurrentEmployeeId, DateTime.Parse(shift));
return PartialView("_DailyLogExceptionsTable", vm);
}
catch (Exception ex)
{
//error code
}
}

$.post always returns initiated view from mvc

from my razor edit view I'm hitting mvc controller action where I'm returning ActionResult View.
$.post('/products/details/', { id: someId });
public ActionResult Details(id)
{
...
return View();// in breakpoint this is hitted but never returned as this view.
}
It's always returns me on page where jquery post is initated.
$.post without a callback is like ordering a Pizza then going to bed and forgetting about it. The delivery guy leaves it on the doorstep, where it then gets dragged away by dogs and you never see it :)
Basically: The result of an Ajax post is ignored unless you do something with it.
e.g.
$.post('/products/details/', { id: someId }, function(htmlReturned){
// Do something with the page HTML returned
$('body').html(htmlReturned); // e.g. replace the entire page!
});

Kendo edit template array

I have following kendo example with a custom edit template:
In the example there is a custom edit template, so when you double click on the calendar to make a new event this will show with the custom fields.
There is a custom field for "Contacts" which has an array as data source.
This data source is an array I get from the server (takes 1-2 seconds to get).
The fact that the edit template is prepared with tags makes it not possible to simply create in my success (or done) handler of the ajax call that gets the data.
The only way I see is to have the data ready at page load so that the template picks it up.
I want however to either create the template whenever my data load is done or add my data to it after it is loaded.
To simulate the time the server takes for the data to load I use setTimeout of 1 sec, that way the edit template does not pick up the data.
To recreate:
double click on the calendar to create an event
notice that the contact field is empty (because data is not ready at page load)
Any help appreciated
This has nothing to do with the async delay. Your kontaktdata array is local to the anonymous function you pass to setTimeout, so it simply doesn't exist in the context the template is evaluated in.
Your data has to either be defined on the data model itself or in the global context.
The other problem is that the data structure itself has to exist - either a kendo.data.DataSource or an array, and you need to update it with new data if you want an existing view to be aware of that new data. If you simply replace it, the edit template has no way of picking that up immediately (if you open a new edit dialog, it will also work, of course).
So if you do this, for example, it will work:
var kontaktdata = [];
setTimeout(function(){
kontaktdata.push.apply(kontaktdata, [
{ text: "Demo B Client", value: 1 },
{ text: "Martin", value: 2 },
{ text: "Herbert", value: 3 }]);
}, 4000);

Form data in Codeigniter sent via AJAX to a Controller function that queries a database and returns an array

I have a view called mapsView that contains a map which is generated in a controller function called maps(). In this view I also have a radio button form which is used to filter the markers on the map.
The form is sent via jquery and ajax to another controller function called get_markers() which queries the database successfully and returns an array of values including lng, lat and name which I need to pass back to my view.
The array is called markerDetails and when I do a var_dump($query->result()); I can see that my query was a success.
I am new to using Codeigniter and the problem I have is caused because the form handling and database query are done in a separate controller function to the one that loads the map view. The maps() function creates the maps and get_markers()deals with the database query based on the form data submitted from the mapsView page.
I have tried moving all the code from the get_markers() controller function into the maps() controller function but when I do the var_dump($query->result()); returns everything in the table and not just the results of my query.
My main problem is that I need the results from my database query in the mapsView page but I cant reload the page because I will lose all the settings for my map.
The form is on the mapView page and is a standard radio button form with a hidden field that has a value for the location. on submit the form passes a value for the location and also for a type that has been picked via the radio buttons.
I am unsure how to approach this problem because the MVC method of doing things is new to me and am wondering if someone could point me in the right direction.
What I understood is that you need to pass data retrieved in a Model to a View.
I implement this by keeping data retrieved from Model in an array and and pass it to view as follows
In controller
function map(){
$this->load->model('maps');
$data['marker_details']=$this->maps->get_marker_details();
$this->load->view('map_view',$data);
}
The data passed would be received as a new variable eg $data['abc'] in controller could be accessed as $abc in view
Thus all your markers could be accessed as $marker_details in map_view
Hope this was needed

JSON object from ASP.NET controller to view

I have a situation where a when a web page is accessed a controller action runs which retrieves the data for that page based on a user selection. I am attempting to send the data back to the page as a JSON object, however, the data opens up as one large string in an HTML page. The controller action, in a nutshell, looks like the following snippet:
Public JsonResult MyMethod(string userSelection)
{
string userData = (string) Data;
return Json(userData, “text”, JsonRequestBehavior.AllowGet);
}
I first tried to use the JQuery $.getJson() method but I think this is wrong as I believe it issues another call to the action method for the data, which is not what I want to do. What I want is to access the JSON object in JavaScript code so I can use the property data to populate fields on the web page. The basic question is what must I do in my JavaScript to receive the JSON object when the page is first rendered? I apologize if I am missing something fundamental; this is my first try.
I still had no luck today but when I left work I came up with a strategy walking to my car. A user makes a selection from a page that presents a list prior to entering the page on which I cannot figure out how to work with JsonResult. Part of the problem is the user selection contains a link that calls the controller/action that returns the JsonResult which conflicts with using $.getJson() within the page where I want to work with JsonResult. So here is my strategy: When the user makes the selection that brings them to the (problematic) page, I will call a controller/action that strictly works with (ASP) ViewData, and use the ViewData to initially present that page. Once on the page, the user can change the selection -- I will handle this with a JavaScript event that uses a $.getJason() call to a different controller/action method that works with (ASP) JsonResult. After I try this strategy I shall post my results for whomever is interested.
You want parseJSON not getJSON
http://api.jquery.com/jQuery.parseJSON/
Edit - Oh wait you are pointing your browser at the JsonResult as if it was an ActionResult? That is not going to work.
Render a proper view, and use getJSON to call the JsonResult action.
getJSON is what you are looking for. Call that on the DOM ready event which will executes once the DOM finishes loading.
$(function(){
//This code will be executed on the DOM ready ( when the page is loaded)
$.getJSON("YourControllerName/MyMethod?userSelection=someValue",function(data){
alert(data.FirstName);
alert(data.AnotherPropertyName);
});
});
getJSON is a shorthand of jQuery ajax method with datatype set as json
Assuming your JSON data you are retuning is something like this
{
"FirstName": "Scott",
"AnotherPropertyName": "SomeValue"
}
To return data like above, change your Action method like this
public JsonResult MyMethod(string userSelection)
{
var result=new { FirstName="Scott", AnotherPropertyName="Great"};
return Json(result,JsonRequestBehavior.AllowGet);
}

Categories