Sending data with post ajax to asp.net MVC controller - javascript

I am tried sent a data from view with ajax (POST) to controller in JSON format. From console.log, data is correct but data in controller missing...
Here is controller:
[HttpPost]
public ActionResult SavePermission(TestData testData)
{
return Json("DONE");
}
Here is model:
namespace INTRANETv4.Models
{
public class TestData
{
public string id { get; set; }
public bool read { get; set; }
public bool write { get; set; }
public bool delete { get; set; }
}
}
Here is javascript function from View:
function Save() {
var rows = document.getElementById("userTable").getElementsByTagName("tr");
var output = [];
for (i = 1; i < rows.length; i++) {
output.push({
id: rows[i].id,
read: rows[i].getElementsByTagName("td")[2].getElementsByTagName("input")[0].checked,
write: rows[i].getElementsByTagName("td")[3].getElementsByTagName("input")[0].checked,
delete: rows[i].getElementsByTagName("td")[4].getElementsByTagName("input")[0].checked
});
}
var myJSON = JSON.stringify(output);
console.log(myJSON);
$.ajax({
type: "POST",
contentType: "application/json",
data: myJSON,
url: "/Files/SavePermission",
dataType: "json"
});
}
Here is console.log of myJSON:
And here is content of testData from controller while debugging:
When i used string testData, because i worried about to convert, string was null. Thank you for any advice.

try
you model change to List<TestData> testData
and data change to JSON.stringify({ testData: output }),
$.ajax({
type: "POST",
contentType: "application/json",
data: JSON.stringify({ testData: output }),
url: "/Files/SavePermission",
dataType: "json"
});

Related

How can i send a large array to MVC Controller

I am getting an error when sending an array with a length greater than 250 to MVC controller. It works when array length is less than 250 items.
Client Code
function saveVD() {
var arr = [];
$.each($("#tablevd tbody tr"), function () {
arr.push({
invNo: $(this).find('td:eq(0)').html().trim(),
invDate: $(this).find('td:eq(1)').html().trim()
})
})
$.ajax({
contentType: 'application/json; charset=utf-8',
dataType: 'json',
type: 'POST',
url: "#Url.Action("Absorb","My")",
data: JSON.stringify({ 'arr': arr }),
success: function (result) {
},
error: function () {
}
})
}
Server Code
public class MyController : Controller
{
[HttpPost]
public JsonResult Absorb(CIVM[] arr)
{
return Json(true, JsonRequestBehavior.AllowGet);
}
}
public class CIVM
{
public string invNo { get; set; }
public DateTime invDate { get; set; }
}
Below config changes may help you
<appSettings>
<add key="aspnet:MaxJsonDeserializerMembers" value="150000" />
</appSettings>

Get json data from ajax,process it,return answer

I have some troubles with transfer json data.
I have some dynamic page. I collect data to json object "Filters".
var Filters = { daterange: $('#daterange').val(), shop: val_shop, pr: val_pr, plan: val_plan, TabsList: TabsList }
$.ajax({
url: "/Reports/Report_2",
type: "POST",
contentType: "application/json",
dataType: "json",
data: JSON.stringify(
Filters
)
});
I try get it with JObject.
public IActionResult Report_2() //main Action
{
return View();
}
[HttpPost]
public async Task<IActionResult> Report_2([FromBody]JObject jsonResult)//catch json object
{
//do something
return View(_context.MyDatabase.Result);//return data from database for table(Razor Page)
}
I get Error 415. =(
If I try don't overload Report_2 Action().
$.ajax({
url: "/Reports/Report_2_Filter",
type: "POST",
contentType: "application/json",
dataType: "json",
data: JSON.stringify(
Filters
)
});
[HttpPost]
public async Task<JObject> Report_2_Filter([FromBody]JObject jsonResult)
{
return jsonResult;
}
I don't know how return result on Report_2 page. I need result on Report_2 Action becouse I must fill table on Report_2 page. I'm newbee in web, so I will be greateful for any help.
May be you need write ("");
var Filters = { "daterange": $('#daterange').val(), "shop": val_shop, "pr": val_pr, "plan": val_plan, "TabsList": TabsList }
You can add a function to be executed on success. Try to add the following to your ajax request:
success: function(data){
// Do something here
}
Have a look here to see the ajax events.
My solution:
I create class which stores variables:
public class FilterModel
{
public string var1{ get; set; }
public string var2{ get; set; }
public string var3{ get; set; }
public string var4{ get; set; }
public List<string> var5{ get; set; }
}
[HttpPost]
public IActionResult Report_2(FilterModel filter)
{
FilterLogic filterLogic = new FilterLogic(_context);
var result = filterLogic.GetResult(filter);
return View();
}
In JS I use jQuery function $.post
$.post("/Reports/Report_2", { var1: $('#var1').val(), var2: var2, var3: var3, var4: var4, var5: var5});

Passing Multiple JSON objects via AJAX to ASP.Net PageMethod

I am trying to pass two JSON Objects to my Page Method via AJAX
I created a class in Code Behind and created a JSON Object Array in javascript.
Following are my two classes and Page Method
public class userModel
{
public string userid { get; set; }
public string Name { get; set; }
}
public class companyModel
{
public string companyid { get; set; }
public string Name { get; set; }
}
[WebMethod]
public static string TestJsonMethod(userModel[] users)
{
return "";
}
And Following is my Javascript
function TestJSON() {
//var JSONObject = { a: [], b };
var obj = {users: []};
var user;
for (var i = 0; i < 3; i++) {
user = {
userid: i.toString(),
Name: "User" + i.toString()
}
obj.users.push(user);
}
var company = {companyid: "4", Name:"TEST COMPANY"};
$.ajax({
url: "bulkconsignments.aspx/TestJsonMethod",
type: "POST",
contentType: "application/json; charset=utf-8",
data: JSON.stringify(obj),
async: false,
cache: false,
success: function (msg) {
alert(msg.d);
}
});
}
Up till this point my code is working fine.
What I want to do is to pass the company object to the Page Method as well like this
[WebMethod]
public static string TestJsonMethod(userModel[] users, companyModel company)
{
return "";
}
You could merge the models into one model.
public class TestJsonModel
{
public UserModel UserModel { get; set; }
public CompanyModel CompanyModel { get; set; }
}
Then action looks like;
[WebMethod]
public static string TestJsonMethod(TestJsonModel model)
Also, Ajax request post data looks like;
data: JSON.stringify({UserModel:obj,CompanyModel:company})
I was trying out different ways of doing it and this one worked.
function TestJSON() {
//var JSONObject = { a: [], b };
var obj = {users: [], company: {}};
var user;
for (var i = 0; i < 3; i++) {
user = {
userid: i.toString(),
Name: "User" + i.toString()
}
obj.users.push(user);
}
var company_ = {companyid: "4", Name:"TEST COMPANY"};
obj.company = company_;
$.ajax({
url: "bulkconsignments.aspx/TestJsonMethod",
type: "POST",
contentType: "application/json; charset=utf-8",
data: JSON.stringify(obj),
async: false,
cache: false,
success: function (msg) {
alert(msg.d);
}
});
}
And the Code behind Page Method remains same.
[WebMethod]
public static string TestJsonMethod(userModel[] users, companyModel company)
{
return "";
}

How to create a nested ajax requests?

I have a WEB API that is working fine. I want to call an action that is a part of my API via Ajax request. It seems that it is easy and I had it working for simple requests. However, I tried to put nested calls and for some reason the data that is passed to the second request gets lost. I was wondering if it is a scope problem or something I did wrong in my code.
Here is the javascript code:
$("#submit_request").click(function () {
var firstName = $("#first_name").val();
var lastName = $("#last_name").val();
var faciltiy = $("#facility").val();
// Collecting all the documents into an array of JSON
var documents = [];
var request = JSON.stringify({
"PatientFirstName": firstName,
"PatientLastName": lastName,
"Facility": faciltiy
});
//the first request is working fine and it has a success state
$.ajax({
url: "http://localhost:64611/api/requests/createRequest",
type: "POST",
dataType: 'json',
contentType: 'application/json',
data: request,
success: function (request_id, state) {
for (var i = 0; i < 5; i++) {
var RequestDocument = {
"RequestID": i,
"DocumentID": i+1,
"StartDate": Date(),
"EndDate": Date()
};
documents.push(RequestDocument);
}
console.log(documents); // it is returning a correct object
console.log(typeof (documents)); // type object
$.ajax({
url: "http://localhost:64611/api/requests/addDocumentsOfARequest/",
type: "post",
datatype: 'json',
contenttype: 'application/json',
data: JSON.stringify(documents), ---> this object should be passed to the api action
success: function (response, state) {
},
error: function (err) {
if (err) {
}
}
});
},
error: function (err) {
if (err) {
}
}
});
});
The definition of my api action is like the following
public async Task<IHttpActionResult> addDocumentsOfARequest(RequestDocument[] documents)
The class RequestDocument is like the following:
public class RequestDocument
{
[Required]
public int RequestID { get; set; }
[Required]
public int DocumentID { get; set; }
[Required]
public DateTime StartDate { get; set; }
public DateTime EndDate { get; set; }
}
My WebApiConfig is like the following:
public static class WebApiConfig
{
public static void Register(HttpConfiguration config)
{
config.MapHttpAttributeRoutes();
config.Routes.MapHttpRoute(
name: "defaultApiRoutes",
routeTemplate: "api/{controller}/{action}/{id}",
defaults: new { id = RouteParameter.Optional },
constraints: new { id = #"\d+" } // Only matches if "id" is one or more digits.
);
config.Formatters.JsonFormatter.SupportedMediaTypes.Add(new MediaTypeHeaderValue("text/html"));
}
}
the parameter 'documents' is empty. Any idea?
Thanks!
Here's my exact working code :
Server
public class GamesController : ApiController
{
// GET api/<controller>
[HttpPost]
public async Task<IHttpActionResult> Post(RequestDocument[] document)
{
var req = await Request.Content.ReadAsStringAsync();
return Ok();
}
}
public class RequestDocument
{
[Required]
public int RequestID { get; set; }
[Required]
public int DocumentID { get; set; }
[Required]
public DateTime StartDate { get; set; }
public DateTime EndDate { get; set; }
}
JavaScript
var documents = [];
for (var i = 0; i < 5; i++) {
var RequestDocument = {
"RequestID": i,
"DocumentID": i+1,
"StartDate": Date(),
"EndDate": Date()
};
documents.push(RequestDocument);
}
$.ajax({
url: "http://localhost:1757/api/games",
type: "POST",
dataType: 'json',
contentType: 'application/json',
data: JSON.stringify(documents),
success: function(a, b) {
alert("Done");
}
});
Result
try this,
$.ajax({
url: "http://localhost:1757/api/games",
type: "POST",
dataType: 'json',
contentType: 'application/json',
data: {
document: documents
},
success: function(a, b) {
alert("Done");
}
});

Why is my posted data null in the Controller target of this AJAX call?

I have modeled (no pun intended) my AJAX call on the answer here from logan filley, which seems sensible and likely to work. This is the jquery I have in the View:
$("#btnSaveConfig").click(function () {
var saveConfigModel = {
unit: $('#unitsselect').val(),
scheduleProduceUsage: $('#ckbx_produceusage').checked,
scheduleDeliveryPerformance: $('#ckbx_deliveryperformance').checked,
scheduleFillRate: $('#ckbx_fillratebycustomer_location').checked,
schedulePriceCompliance: $('#ckbx_pricecompliance').checked,
// TODO: Finish this by storing add'l emails in an array along with the three on the page;
recipients: $('#email1').val(),
generationDayOfMonth: $('#dayofmonthselect').val(),
generationOrdinal: $('#ordinalselect').val(),
generationDayOfWeek: $('#dayofweekselect').val(),
generationWeekOrMonth: $('#weekormonthselect').val(),
daterangeFromProduceUsage: $('#produsagefrom').val(),
daterangeToProduceUsage: $('#produsageto').val(),
daterangeFromDeliveryPerformance: $('#delperffrom').val(),
daterangeToDeliveryPerformance: $('#delperfto').val(),
daterangeFromFillRate: $('#fillratefrom').val(),
daterangeToFillRate: $('#fillrateto').val(),
daterangeFromPriceCompliance: $('#pricecompliancefrom').val(),
daterangeToPriceCompliance: $('#pricecomplianceto').val()
}
$.ajax({
type:"POST",
url:'#Url.Action("PostUnitConfig", "SaveConfig")',
async:true,
contentType: 'application/json',
dataType:"json",
data: JSON.stringify(saveConfigModel)
});
}); // $("#btnSaveConfig").click()
...and this is my Model:
public class SaveConfigModel
{
public UnitConfigVals unitConfigVals { get; set; }
public class UnitConfigVals
{
public string unit { get; set; }
public bool scheduleProduceUsage { get; set; }
public bool scheduleDeliveryPerformance { get; set; }
public bool scheduleFillRate { get; set; }
public bool schedulePriceCompliance { get; set; }
public List<string> recipients { get; set; }
public int generationDayOfMonth { get; set; }
public string generationOrdinal { get; set; }
public string generationDayOfWeek { get; set; }
public string generationWeekOrMonth { get; set; }
public int daterangeFromProduceUsage { get; set; }
public int daterangeToProduceUsage { get; set; }
public int daterangeFromDeliveryPerformance { get; set; }
public int daterangeToDeliveryPerformance { get; set; }
public int daterangeFromFillRate { get; set; }
public int daterangeToFillRate { get; set; }
public int daterangeFromPriceCompliance { get; set; }
public int daterangeToPriceCompliance { get; set; }
}
}
...and Controller (obviously ultra-spartan at the moment):
public class SaveConfigController : Controller
{
public ActionResult PostUnitConfig(SaveConfigModel model)
{
try
{
string s = model.unitConfigVals.unit;
}
catch (Exception ex)
{
Console.WriteLine(ex.Message);
}
return Json(new { success = true });
}
}
I am reaching the breakpoint in my Controller (on the "string s = model.unitConfigVals.unit;" line), but it throws an exception because the value of "model" is null. Why? Have I got something in my AJAX call wrong, or...?!?
UPDATE
I changed my jquery to this (changed boolean assignments and appended a semicolon):
$("#btnSaveConfig").click(function() {
var saveConfigModel = {
unit: $('#unitsselect').val(),
scheduleProduceUsage: $('#ckbx_produceusage').attr('checked'),
scheduleDeliveryPerformance:
. . .
};
$.ajax({
type: "POST",
url: '#Url.Action("PostUnitConfig", "SaveConfig")',
async: true,
//contentType: 'application/json',
dataType: "json",
data: JSON.stringify({ data: saveConfigModel })
});
});
...but the Controller is still passed a null model.
UPDATE 2
Now I changed "attr('checked')" to "is('checked')" but no difference...
UPDATE 3
"model" is null here in the Controller:
public class SaveConfigController : Controller
{
public ActionResult PostUnitConfig(SaveConfigModel model)
...when the AJAX call is like this:
$.ajax({
type: "POST",
url: '#Url.Action("PostUnitConfig", "SaveConfig")',
async: true,
dataType: "json",
data: saveConfigModel
});
...and also when the AJAX call is like this:
$.ajax({
type: "POST",
url: '#Url.Action("PostUnitConfig", "SaveConfig")',
async: true,
data: saveConfigModel
});
...and this:
$.ajax({
type: "POST",
url: '#Url.Action("PostUnitConfig", "SaveConfig")',
async: true,
contentType: 'application/json',
dataType: "json",
data: JSON.stringify({ model: saveConfigModel })
});
Do I need the "async: true"? I don't use that in my (working) GET AJAX calls. Similarly, do I need "cache: false"? I do use that in those working GET AJAX calls...
UPDATE 4
Even when I provide just some bogus vals:
var saveConfigModel = {
unit: 'Buford', //$('#unitsselect').val(),
scheduleProduceUsage: true, //$('#ckbx_produceusage').is(':checked'),
scheduleDeliveryPerformance: false, // $('#ckbx_deliveryperformance').is(':checked'),
scheduleFillRate: false, //$('#ckbx_fillratebycustomer_location').is('checked'),
schedulePriceCompliance: false, //$('#ckbx_pricecompliance').is('checked'),
// TODO: Finish this by storing add'l emails in an array along with the three on the page; might be as easy as declaring an array like this one, and adding to it as necessary
recipients: 'platypus#whatever.com', // $('#email1').val(),
generationDayOfMonth: '2nd', //$('#dayofmonthselect').val(),
generationOrdinal: 'First', //$('#ordinalselect').val(),
generationDayOfWeek: 'Thursday', // $('#dayofweekselect').val(),
generationWeekOrMonth: 'month', // $('#weekormonthselect').val(),
daterangeFromProduceUsage: $('#produsagefrom').val(),
daterangeToProduceUsage: $('#produsageto').val(),
daterangeFromDeliveryPerformance: '1', // $('#delperffrom').val(),
daterangeToDeliveryPerformance: '1', //$('#delperfto').val(),
daterangeFromFillRate: '1', //$('#fillratefrom').val(),
daterangeToFillRate: '1', //$('#fillrateto').val(),
daterangeFromPriceCompliance: '1', //$('#pricecompliancefrom').val(),
daterangeToPriceCompliance: '1' //$('#pricecomplianceto').val()
};
...it still winds up at the Controller null like forevermore before.
And then, grasping at straws, I even encased the boolean values in single quotes ('true' and 'false'), but that also (probably predictably) made no difference either.
UPDATE 5
For future generations, this is the AJAX that works:
$.ajax({
type: "POST",
url: '#Url.Action("PostUnitConfig", "SaveConfig")',
async: true,
contentType: 'application/json',
dataType: "json",
data: JSON.stringify({ model: saveConfigModel })
});
Since the values you posting back are for your nested UnitConfigVals class (not SaveConfigModel, then you controller method should be
public ActionResult PostUnitConfig(SaveConfigModel.UnitConfigVals model)
and the ajax data option needs to be
data: JSON.stringify({ model: saveConfigModel })
Alternatively you could keep the current controller method and use
data: JSON.stringify({ model: { unitConfigVals: saveConfigModel }})
although it seems a little odd that you using a nested class here.
A few other issues with your initial code
$('#ckbx_produceusage').checked will return undefined, and it
needs to be $('#ckbx_produceusage').is(':checked') which will
return true or false
Since recipients is List<string>, it will need to be
recipients: [ 'someValue', 'anotherValue', etc ]
However all this code to build you json data not really necessary, and if your view is generated correctly using the strongly typed HtmlHelper methods, then your ajax call can be as simple as
$.ajax({
type:"POST",
url:'#Url.Action("PostUnitConfig", "SaveConfig")',
dataType: "json",
data: $('form').serialize(),
success: function(data) {
// do something
}
});

Categories