@JsonAppend
有时候我们需要在不改变类的属性字段的情况下,添加字段,Jackson提供了@JsonAppend注解来实现这个功能,使用方式如下
@Getter
@Setter
@AllArgsConstructor(staticName = "of")
@NoArgsConstructor
@JsonAppend(attrs = {@JsonAppend.Attr(value = "age"),@JsonAppend.Attr(value = "height")},
props = {@JsonAppend.Prop(value =TestWriter.class ,type = String.class,name = "version")})
class JsonPropertyPojo{
private String sex;
private String name;
private String unknown;
}
@NoArgsConstructor
class TestWriter extends VirtualBeanPropertyWriter{
private TestWriter(BeanPropertyDefinition propDef, Annotations contextAnnotations, JavaType declaredType) {
super(propDef, contextAnnotations, declaredType);
}
@Override
protected Object value(Object bean, JsonGenerator gen, SerializerProvider prov) throws Exception {
Field nameField = ReflectionUtils.findField(bean.getClass(),"name");
ReflectionUtils.makeAccessible(nameField);
if( nameField.get(bean).toString().length()>2){
return "1.2";
}
return "1.0";
}
@Override
public VirtualBeanPropertyWriter withConfig(MapperConfig<?> config, AnnotatedClass declaringClass, BeanPropertyDefinition propDef, JavaType type) {
return new TestWriter(propDef, declaringClass.getAnnotations(), type);
}
}
测试代码如下
@Test
public void JsonAppendTest() throws Exception{
CombineJacksonAnnotation.JsonPropertyPojo pojo = CombineJacksonAnnotation.JsonPropertyPojo.of("男","小小刘","some");
System.out.println(om.writerFor(CombineJacksonAnnotation.JsonPropertyPojo.class).withAttribute("age","10").withAttribute("height","12").writeValueAsString(pojo));
}
序列化结果如下
{
"sex" : "男",
"name" : "小小刘",
"unknown" : "some",
"age" : "10",
"height" : "12",
"version" : "1.2"
}
通过上面的例子可以看到,@JsonAppend提供了两种方式来动态的添加虚拟字段
1 attrs
此种方式需要在序列化时候手动的添加Attribute,如下
om.writerFor(CombineJacksonAnnotation.JsonPropertyPojo.class).withAttribute("age","10").withAttribute("height","12")
2 props
此种方式比较灵活,但是要实现一个VirtualBeanPropertyWriter类即可,如果真的有这种需求,推荐使用第二种方式来实现
网友评论