JsonMappingException: Nessun costruttore adatto trovato per il tipo [tipo semplice, classe ]: impossibile istanziare da un oggetto JSON

Sto ottenendo il seguente errore quando cerco di ottenere una richiesta JSON ed elaborarla:

org.codehaus.jackson.map.JsonMappingException: No suitable constructor found for type [simple type, class com.myweb.ApplesDO]: can not instantiate from JSON object (need to add/enable type information?)

Ecco il JSON che sto cercando di inviare:

{
  "applesDO" : [
    {
      "apple" : "Green Apple"
    },
    {
      "apple" : "Red Apple"
    }
  ]
}

In Controller, ho la seguente firma del metodo:

@RequestMapping("showApples.do")
public String getApples(@RequestBody final AllApplesDO applesRequest){
    // Method Code
}

AllApplesDO è un wrapper di 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
    }
}

Penso che Jackson non sia in grado di convertire JSON in oggetti Java per le sottoclassi. Si prega di aiutare con i parametri di configurazione per Jackson per convertire JSON in oggetti Java. Sto usando Spring Framework.

EDIT: Incluso il bug principale che sta causando questo problema nella classe di esempio sopra - Si prega di guardare la risposta accettata per la soluzione.

Soluzione

Così, alla fine ho capito qual è il problema. Non è un problema di configurazione di Jackson, come avevo dubitato.

In realtà il problema era nella 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
    }
}

C'era un costruttore personalizzato definito per la classe che lo rendeva il costruttore predefinito. L'introduzione di un costruttore fittizio ha fatto sparire l'errore:

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() {
    }

}
Commentari (13)

Questo accade per queste ragioni:

  1. la tua classe interna dovrebbe essere definita come statica

    private static class Condition { //jackson specific
    }
  2. Potrebbe essere che tu non abbia un costruttore di default nella tua classe ( AGGIORNAMENTO: Questo sembra non essere il caso)

    classe privata statica Condition {
        id privato lungo;
    
        public Condition() {
        }
    
        // Setters e Getters
    }
  3. Potrebbe essere che i vostri setter non siano definiti correttamente o non siano visibili (ad esempio setter privato)

Commentari (14)

Potete per favore testare questa struttura. Se ricordo bene si può usare in questo modo:

{
    "applesRequest": {
        "applesDO": [
            {
                "apple": "Green Apple"
            },
            {
                "apple": "Red Apple"
            }
        ]
    }
}

In secondo luogo, per favore aggiungi un costruttore predefinito ad ogni classe, potrebbe anche aiutare.

Commentari (4)