J'essaie de consommer une API en utilisant Retrofit et Jackson pour désérialiser. J'obtiens l'erreur onFailure No Creators, like default construct, exist): cannot deserialize from Object value (no delegate- or property-based Creator
.
Réponses
Trop de publicités?En prolongeant la réponse de Yoni Gibbs, si vous êtes dans un projet Android utilisant retrofit et configurant la sérialisation avec Jackson, vous pouvez faire ces choses afin que la désérialisation fonctionne comme prévu avec la classe de données de Kotlin.
Dans votre build gradle, importez :
implementation "com.fasterxml.jackson.module:jackson-module-kotlin:2.11.+"
Ensuite, votre mise en œuvre de la modernisation :
val serverURL = "http://localhost:8080/api/v1"
val objectMapper = ObjectMapper()
objectMapper.registerModule(KotlinModule())
//Only if you are using Java 8's Time API too, require jackson-datatype-jsr310
objectMapper.registerModule(JavaTimeModule())
Retrofit.Builder()
.baseUrl(serverURL)
.client(
OkHttpClient.Builder()
.readTimeout(1, TimeUnit.MINUTES)//No mandatory
.connectTimeout(1, TimeUnit.MINUTES)//No mandatory
.addInterceptor(UnauthorizedHandler())//No mandatory
.build())
.addConverterFactory(
JacksonConverterFactory.create(objectMapper)
)
.addCallAdapterFactory(RxJava2CallAdapterFactory.create())
.build()
Classe de données :
@JsonIgnoreProperties(ignoreUnknown = true)
data class Task(val id: Int,
val name: String,
@JsonSerialize(using = LocalDateTimeSerializer::class)
@JsonDeserialize(using = LocalDateTimeDeserializer::class)
val specificDate: LocalDateTime?,
var completed: Boolean,
val archived: Boolean,
val taskListId: UUID?
La réponse de Bek est correcte.
Mais dans le cas où quelqu'un essaierait d'utiliser une classe immuable dans le restcontroller, c'est-à-dire qu'il utiliserait la méthode de lombok. @value
alors vous devez ajouter lombok.anyConstructor.addConstructorProperties=true
Vous pouvez créer un fichier nommé lombok.config
au même endroit où se trouve le pom.xml racine et ajoutez cette ligne dans le fichier
Dans les cas où nous n'avons pas de construction par défaut, par exemple lorsque nous travaillons avec des objets immuables, Jackson ne sera pas en mesure, par défaut, de désérialiser le JSON de l'objet. Nous pouvons résoudre ce problème en utilisant des annotations telles que @JsonCreator
qui peut aider Jackson à savoir comment désérialiser un JSON donné.
Un exemple de code ressemblera à ceci :
package com.test.hello;
import com.fasterxml.jackson.annotation.JsonCreator;
import com.fasterxml.jackson.annotation.JsonProperty;
public class Payment {
private final Card card;
private final Amount amount;
@JsonCreator(mode = JsonCreator.Mode.PROPERTIES)
public Payment(@JsonProperty("card") Card card, @JsonProperty("amount") Amount amount) {
this.card = card;
this.amount = amount;
}
public Card getCard() {
return card;
}
public Amount getAmount() {
return amount;
}
}
2 votes
Il semble que vous n'utilisiez pas le module Jackson pour Kotlin, qui fonctionne avec les classes de données qui n'ont pas de constructeur par défaut, ce qui n'est pas le cas de la vôtre. Vérifiez ce module et voyez si vous avez des problèmes par la suite.
0 votes
Veuillez modifier la réponse acceptée.