I work around e-commerce`s cart. I have two view models.
First for customers info:
public class CartViewModel
{
public string FirstName{get;set;}
public string Email{get;set;}
//... other fields
}
And second for customers cart:
public class ProductsCart
{
public Guid Id { get; set; }
public decimal Price { get; set; }
public int ItemsOrdered { get; set; }
}
The main thing is that cart storing in users localStorage and I should pass it from localStorage with customers info via jquery to MVC`s action:
[HttpPost]
public ActionResult ConfirmOrder(CartViewModel model, IEnumerable<ProductsCart> cart)
{
// validate and save to database
}
And I have javascript method to send data to my action:
function ConfirmOrder() {
var serverCart = LocalCartToSercerCart(); //see first screnshot
var customerData = $("#FORM_WITH_CUSTOMERS_VIEW_MODEL").serialize();
$.ajax({
method: "POST",
url: "/Cart/ConfirmOrder",
data: {model: customerData, cart: serverCart }
})
.done(function () {
//do something
});
}
But I always getting null value for my CartViewModel (screenshot 2)
I also attached files with my debug info.
If I write javascript function like this:
function ConfirmOrder() {
var customerData = $("#cartForm").serialize();
$.ajax({
method: "POST",
url: "/Cart/ConfirmOrder",
data: customerData
})
.done(function () {
//some code
});
}
I getting only model data (see screenshot 3)
EDIT: I wrote code using Igor`s answer, but still getting null in action parameter
Introduction. In MVC we cannot pass multiple models from a controller to the single view. This article provides a workaround for multiple models in a single view in MVC.
Defines a class used to provide values and methods to the component's view.
The @model directive allows access to the list of movies that the controller passed to the view by using a Model object that's strongly typed. For example, in the Index.cshtml view, the code loops through the movies with a foreach statement over the strongly typed Model object: CSHTML Copy.
The reason you are receiving a null value is because the data is not being converted to JSON before it is sent to the server. The JQUERY ajax call does not do this automatically for you. You can easily convert it using JSON.stringify
like so.
$.ajax({
method: "POST",
url: "/Cart/ConfirmOrder",
data: JSON.stringify({model: customerData, cart: serverCart }),
contentType: 'json' // added to tell the server the format of the data being sent
})
.done(function () {
//do something
});
JSON.stringify converts your object to properly formatted JSON which is then sent to the server. From the documentation.
The JSON.stringify() method converts a JavaScript value to a JSON string, optionally replacing values if a replacer function is specified, or optionally including only the specified properties if a replacer array is specified.
Note This edit was based on @StephenMuecke comment below. My previous answer was not correct, the only change that was necessary was to your javascript ajax call, not your c# code.
After many tries I finaly found solution. For me it was this javascript code:
function ConfirmOrder() {
var serverCart = LocalCartToSercerCart();
var customerData = $('#cartForm').serialize();
var paramObj = {};
$.each($('#cartForm').serializeArray(), function (_, kv) {
paramObj[kv.name] = kv.value;
});
var Data = {
model: paramObj,
cart: serverCart
}
$.ajax({
method: "POST",
url: "/Cart/ConfirmOrder",
contentType: 'application/json',
data: JSON.stringify(Data)
})
.done(function () {
});
}
And this action in MVC :
[HttpPost]
public ActionResult ConfirmOrder(CartViewModel model, IEnumerable<ProductsCart> cart)
{
// operations with data
}
The kye was right transformation form data to javacript object. As I understand, Serialize() method convert form to WebForm data and it is not valid to be send as a ONE OF THE PARAMETERS. Serialize() must be whole object... Maybe I'm wrong, you can write your suggetions in comments, I'll be glad to read it.
Special thanks to Igor and StephenMuecke
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With