J'obtiens l'erreur suivante lorsque j'essaie de recevoir une requête JSON et de la traiter :
org.codehaus.jackson.map.JsonMappingException : No suitable constructor found for type [simple type, class com.myweb.ApplesDO] : cannot not instantiate from JSON object (need to add/enable type information ?)
Voici le JSON que j'essaie d'envoyer :
{
"applesDO" : [
{
"apple" : "Green Apple"
},
{
"apple" : "Red Apple"
}
]
}
Dans le contrôleur, j'ai la signature de la méthode suivante :
@RequestMapping("showApples.do")
public String getApples(@RequestBody final AllApplesDO applesRequest){
// Method Code
}
AllApplesDO est une enveloppe d'ApplesDO :
public class AllApplesDO {
private List<ApplesDO> applesDO;
public List<ApplesDO> getApplesDO() {
return applesDO;
}
public void setApplesDO(List<ApplesDO> applesDO) {
this.applesDO = applesDO;
}
}
ApplesDO :
public class ApplesDO {
private String apple;
public String getApple() {
return apple;
}
public void setApple(String appl) {
this.apple = apple;
}
public ApplesDO(CustomType custom){
//constructor Code
}
}
Je pense que Jackson est incapable de convertir JSON en objets Java pour les sous-classes. Veuillez m'indiquer les paramètres de configuration permettant à Jackson de convertir JSON en objets Java. J'utilise Spring Framework.
EDIT : J'ai inclus le bug majeur qui cause ce problème dans l'exemple de classe ci-dessus - Veuillez regarder la réponse acceptée pour la solution.
J'ai finalement compris quel était le problème. Ce n'est pas un problème de configuration de Jackson comme j'en doutais.
En fait, le problème se situe dans la classe ApplesDO :
public class ApplesDO {
private String apple;
public String getApple() {
return apple;
}
public void setApple(String apple) {
this.apple = apple;
}
public ApplesDO(CustomType custom) {
//constructor Code
}
}
Il y avait un constructeur personnalisé défini pour la classe qui en faisait le constructeur par défaut. L'introduction d'un constructeur fictif a fait disparaître l'erreur :
public class ApplesDO {
private String apple;
public String getApple() {
return apple;
}
public void setApple(String apple) {
this.apple = apple;
}
public ApplesDO(CustomType custom) {
//constructor Code
}
//Introducing the dummy constructor
public ApplesDO() {
}
}
Cela se produit pour les raisons suivantes :
Votre classe interne doit être définie comme statique.
private static class Condition { //jackson specific
}
Il se peut que vous n'ayez pas de constructeur par défaut dans votre classe (MISE À JOUR: Cela ne semble pas être le cas).
private static class Condition {
private Long id ;
public Condition() {
}
// Setters et Getters
}
Il se peut que vos setters ne soient pas définis correctement ou qu'ils ne soient pas visibles (par exemple, un setter privé).
Pouvez-vous tester cette structure ? Si je me souviens bien, vous pouvez l'utiliser de cette façon :
{
"applesRequest": {
"applesDO": [
{
"apple": "Green Apple"
},
{
"apple": "Red Apple"
}
]
}
}
Deuxièmement, veuillez ajouter un constructeur par défaut à chaque classe, cela pourrait aussi aider.