Jackson préfère constructeur privé sur @JsonCreator lors de la désérialisation d'une classe avec @JsonValue

J'ai une simple classe avec un constructeur privé et statique de l'usine. Je veux la classe de sérialiser comme un nombre, donc j'ai annoté de la lecture pour le champ avec @JsonValue. Toutefois, Jackson semble préférer le constructeur privé au cours de la statique de l'usine, même quand je annoter la statique de l'usine avec @JsonCreator. Il fonctionne si je annoter le constructeur privé avec @JsonIgnore, mais qui se sent un peu.

J'ai vu quelques messages affirmant que @JsonCreator ne fonctionne que si les paramètres sont annotés avec @JsonProperty; cependant, cela semble être le cas pour les objets sérialisés comme objets JSON. Cet objet est sérialisé comme un nombre, et il n'est donc pas la propriété de fournir à l'annotation.

Est-il quelque chose que je suis absent?

exemple de classe:

package com.example;

import com.fasterxml.jackson.annotation.JsonCreator;
import com.fasterxml.jackson.annotation.JsonValue;
import com.google.common.base.Preconditions;

public class NonNegative {
  private final double n;

  private NonNegative(double n) {
    this.n = n;
  }

  @JsonCreator
  public static NonNegative checked(double n) {
    Preconditions.checkArgument(n >= 0.0);
    return new NonNegative(n);
  }

  @JsonValue
  public double getValue() {
    return n;
  }

  @Override
  public int hashCode() {
    return Objects.hash(n);
  }

  @Override
  public boolean equals(Object obj) {
    if (this == obj) {
      return true;
    }
    if (obj instanceof NonNegative) {
      NonNegative that = (NonNegative) obj;
      return Objects.equals(n, that.n);
    }
    return false;
  }
}

exemple tests:

package com.example;

import static org.assertj.core.api.Assertions.assertThat;

import org.junit.Test;

import com.fasterxml.jackson.databind.JsonMappingException;
import com.fasterxml.jackson.databind.ObjectMapper;

public class NonNegativeTest {
  private static final ObjectMapper MAPPER = new ObjectMapper();

  @Test
  public void itSerializesAndDeserializes() throws Exception {
    NonNegative nonNegative = NonNegative.checked(0.5);

    assertThat(MAPPER.readValue(MAPPER.writeValueAsString(nonNegative), NonNegative.class)).isEqualTo(nonNegative);
  }

  /* This test fails. */
  @Test(expected = JsonMappingException.class)
  public void itDoesNotDeserializeANegativeNumber() throws Exception {
    MAPPER.readValue(MAPPER.writeValueAsString(-0.5), NonNegative.class);
  }
}
avez-vous essayé annoting l'argument de l'objet de la méthode avec @JsonProperty?
J'ai. Il n'a pas aidé.
Peut-être.

OriginalL'auteur NickAldwin | 2014-12-19