Por que quando um construtor é anotado com @JsonCreator, seus argumentos devem ser anotados com @JsonProperty?

Em Jackson, quando você anota um construtor com @JsonCreator , você deve anotar seus argumentos com @JsonProperty . Então esse construtor

 public Point(double x, double y) { this.x = x; this.y = y; } 

torna-se isso:

 @JsonCreator public Point(@JsonProperty("x") double x, @JsonProperty("y") double y) { this.x = x; this.y = y; } 

Eu não entendo porque é necessário. Você pode explicar, por favor?

Jackson precisa saber em que ordem passar os campos de um object JSON para o construtor. Não é possível acessar nomes de parâmetros em Java usando reflection – é por isso que você precisa repetir essas informações em annotations.

Nomes de parâmetros normalmente não são acessíveis pelo código Java em tempo de execução (porque é descartado pelo compilador), portanto, se você deseja essa funcionalidade, é necessário usar a funcionalidade integrada do Java 8 ou usar uma biblioteca como a ParaNamer para obter access para isso.

Então, para não ter que utilizar annotations para os argumentos do construtor ao usar Jackson, você pode fazer uso de qualquer um desses dois módulos Jackson:

jackson-module-parameter-names

Este módulo permite obter argumentos de construtor sem annotations ao usar o Java 8 . Para usá-lo você primeiro precisa registrar o módulo:

 ObjectMapper mapper = new ObjectMapper(); mapper.registerModule(new ParameterNamesModule()); 

Em seguida, compile seu código usando o sinalizador -parameters:

 javac -parameters ... 

Link: https://github.com/FasterXML/jackson-modules-java8/tree/master/parameter-names

jackson-module-paranamer

Este outro simplesmente requer que você registre o módulo ou configure uma introspecção de anotação (mas não ambas como apontadas pelos comentários). Ele permite que você use argumentos de construtor sem annotations em versões do Java anteriores à 1.8 .

 ObjectMapper mapper = new ObjectMapper(); // either via module mapper.registerModule(new ParanamerModule()); // or by directly assigning annotation introspector (but not both!) mapper.setAnnotationIntrospector(new ParanamerOnJacksonAnnotationIntrospector()); 

Link: https://github.com/FasterXML/jackson-modules-base/tree/master/paranamer

É possível evitar annotations de construtor com jdk8 onde, opcionalmente, o compilador introduzirá metadados com os nomes dos parâmetros do construtor. Então, com o módulo jackson-module-parameter-parameters, o Jackson pode usar este construtor. Você pode ver um exemplo no post Jackson sem annotations

  • Os Tutoriais Java ™ – Obtendo Nomes dos parameters do Método

Porque o bytecode de Java não retém os nomes dos argumentos de método ou construtor.

Quando eu entendi isso corretamente, você substitui o construtor padrão por um parametrizado e, portanto, tem que descrever as chaves JSON que são usadas para chamar o construtor.

Conforme indicado na documentação de anotação , a anotação indica que o nome do argumento é usado como o nome da propriedade sem nenhuma modificação, mas pode ser especificado para um valor não vazio para especificar um nome diferente: