EDITAR : 31/10/2017
Le même code/approche fonctionnera pour Asp.Net Core 2.0 également. La principale différence est que, dans asp.net core, les contrôleurs de l'api web et les contrôleurs Mvc sont fusionnés en un seul modèle de contrôleur. Donc votre type de retour peut être IActionResult
ou l'une de ses mises en œuvre (Ex : OkObjectResult
)
Utilisez
contentType:"application/json"
Vous devez utiliser JSON.stringify
pour le convertir en chaîne JSON lorsque vous l'envoyez,
Et le model binder liera les données json à votre objet de classe.
Le code ci-dessous fonctionne bien (testé)
$(function () {
var customer = {contact_name :"Scott",company_name:"HP"};
$.ajax({
type: "POST",
data :JSON.stringify(customer),
url: "api/Customer",
contentType: "application/json"
});
});
Resultado
![enter image description here]()
contentType
indique au serveur que nous envoyons les données au format JSON. Puisque nous avons envoyé une structure de données JSON, le model binding se fera correctement.
Si vous inspectez les en-têtes de la requête ajax, vous pouvez voir que l'option Content-Type
est définie comme application/json
.
Si vous ne spécifiez pas explicitement le type de contenu, il utilisera le type de contenu par défaut qui est application/x-www-form-urlencoded;
Modifier en novembre 2015 pour traiter d'autres problèmes éventuels soulevés dans les commentaires.
Enregistrement d'un objet complexe
Disons que vous avez une classe de modèle de vue complexe comme paramètre de la méthode d'action de l'api Web, comme ceci
public class CreateUserViewModel
{
public int Id {set;get;}
public string Name {set;get;}
public List<TagViewModel> Tags {set;get;}
}
public class TagViewModel
{
public int Id {set;get;}
public string Code {set;get;}
}
et le point final de votre api web est comme
public class ProductController : Controller
{
[HttpPost]
public CreateUserViewModel Save([FromBody] CreateUserViewModel m)
{
// I am just returning the posted model as it is.
// You may do other stuff and return different response.
// Ex : missileService.LaunchMissile(m);
return m;
}
}
Au moment où nous écrivons ces lignes, ASP.NET MVC 6 est la dernière version stable et dans MVC6, les contrôleurs de l'API Web et les contrôleurs MVC héritent tous deux de l'élément suivant Microsoft.AspNet.Mvc.Controller
classe de base.
Pour envoyer des données à la méthode du côté client, le code suivant devrait fonctionner correctement
//Build an object which matches the structure of our view model class
var model = {
Name: "Shyju",
Id: 123,
Tags: [{ Id: 12, Code: "C" }, { Id: 33, Code: "Swift" }]
};
$.ajax({
type: "POST",
data: JSON.stringify(model),
url: "../product/save",
contentType: "application/json"
}).done(function(res) {
console.log('res', res);
// Do something with the result :)
});
La liaison de modèle fonctionne pour certaines propriétés, mais pas toutes ! Pourquoi ?
Si vous ne décorez pas le paramètre de la méthode de l'api web avec l'option [FromBody]
attribut
[HttpPost]
public CreateUserViewModel Save(CreateUserViewModel m)
{
return m;
}
Et envoyez le modèle (objet javascript brut, pas au format JSON) sans spécifier la valeur de la propriété contentType.
$.ajax({
type: "POST",
data: model,
url: "../product/save"
}).done(function (res) {
console.log('res', res);
});
La liaison de modèle fonctionnera pour les propriétés plates sur le modèle, pas pour les propriétés où le type est complexe/un autre type. Dans notre cas, Id
y Name
seront correctement liées au paramètre m
Mais le Tags
sera une liste vide.
Le même problème se posera si vous utilisez la version courte, $.post
qui utilisera le Content-Type par défaut lors de l'envoi de la demande.
$.post("../product/save", model, function (res) {
//res contains the markup returned by the partial view
console.log('res', res);
});