简体   繁体   English

杰克逊特定字段名称

[英]Jackson specifc field name

I have this class: 我有这个课:

@Data
public class DiscountDto {

    @JsonProperty(required = true)
    private DiscountType type;

    @JsonProperty(required = true)
    private double discountValue;
}

DiscountType is enum: DiscountType是枚举:

public enum  DiscountType {

    PERCENT, AMOUNT
}

I want to serialize the discountValue to a specific value, depending on the Enum value. 我想了序列化discountValue为特定值,取决于枚举值。 If enum have value PERCENT , then discountValue must be serialize to percent_off . 如果枚举的值是PERCENT ,则必须将percent_off序列化为percent_off If enum have value AMOUNT then discountValue must be serialize to amount_off . 如果枚举具有价值AMOUNTdiscountValue必须序列化到amount_off How could I possibly do that? 我怎么可能那样做?

Expected result: 预期结果:

If type == AMOUNT, I want discountValue name = amount_off 如果类型== AMOUNT,我想要DiscountValue名称= amount_off

"discountDto": {
    "amount_off": "11.0",
    "type": "AMOUNT"
}

If type == PERCENT, I want discountValue name = percent_off 如果类型== PERCENT,我想要DiscountValue名称= percent_off

"discountDto": {
    "percent_off": "11.0",
    "type": "PERCENT"
}

Possible solutions: 可能的解决方案:

1.Create a constructor with both DiscountType and discountValue and set directly the value of the percentOff or amountOff field: 1.使用DiscountType和DiscountValue创建一个构造函数,并直接设置percentOff或amountOff字段的值:

@JsonInclude(Include.NON_NULL)
public class DiscountDto {

     private DiscountType type;

     @JsonProperty("percent_off")
     private Double percentOff;

     @JsonProperty("amount_off")
     private Double amountOff;

     public DiscountDto(DiscountType type, double discountValue){
          this.type = type;
          if(type.equals(DiscountType.PERCENT)){
              this.percentOff = discountValue;
          }else {
              this.discountOff = discountValue;
          }

     }
     //getters and setters
}

2.Use a custom JSON serializer: 2,使用自定义的JSON序列化器

public class DiscountDtoSerializer extends StdSerializer<DiscountDto> {

    public DiscountDtoSerializer() {
        this(null);
    }

    public DiscountDtoSerializer(Class<DiscountDto> t) {
        super(t);
    }

    @Override
    public void serialize(DiscountDto value, JsonGenerator jgen, SerializerProvider provider)
      throws IOException, JsonProcessingException {

        jgen.writeStartObject();
        jgen.writeNumberField("type", value.getDiscountType());
        if(value.getDiscountType().equals(DiscountType.PERCENT)){
            jgen.writeStringField("percent_off", value.getDiscountValue());
        }else{
            jgen.writeStringField("amount_off", value.getDiscountValue());
        }
        jgen.writeEndObject();
    }
 }

and your ObjectMapper should have this new serializer: 并且您的ObjectMapper应该具有这个新的序列化器:

 ObjectMapper mapper = new ObjectMapper();
 SimpleModule module = new SimpleModule();
 module.addSerializer(DiscountDto.class, new DiscountDtoSerializer());
 mapper.registerModule(module);

This is a typical example of how not to do polymorphism. 这是如何进行多态的典型示例。 Don't get me wrong, I am not crticizing you, this has happend to most of us. 不要误会我的意思,我不是在批评你,这在我们大多数人中已经发生。 This is a sort of inner-state polymorphism, that is, depending on the value of some property ( type even the name says it, right?) some other property gets a different meaning. 这是一种内部状态多态性,也就是说,取决于某些属性的值(甚至是名称所表示的type ,对吗?),某些其他属性的含义有所不同。

To solve the problem correctly, you should move the poperty type , at the level of the class, having a class for each type. 为了正确解决问题,您应该在类级别移动poperty 类型 ,每种类型都有一个类。 You can start by having an abstract, uninstantiable type, and your specific types will derive from it. 您可以从拥有一个抽象的,无法实例化的类型开始,您的特定类型将从中派生。

You can find some sample implementation here , for technical reference. 您可以在此处找到一些示例实现,以供技术参考。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM