Jackson别名@JsonAlias详细用法

参考文章:https://blog.csdn.net/weixin_49969179/article/details/126369966?spm=1001.2014.3001.5502

@JsonAlias

源码

package com.fasterxml.jackson.annotation;

import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;

@Target({ElementType.ANNOTATION_TYPE, ElementType.FIELD, ElementType.METHOD, ElementType.PARAMETER})
@Retention(RetentionPolicy.RUNTIME)
@JacksonAnnotation
public @interface JsonAlias {
    String[] value() default {};
}

使用场景

  • 反序列化时,json字符串中的字段名与实体中的字段名不一样时,在实体的字段上使用该注解,并赋予别名(json字符串中的字段名),这样反序列化时数据才可以成功序列化。

科普

  • 反序列化:json字符串转为实例对象
  • 序列化:实例对象转为json字符串

具体用法示例

单别名

import com.fasterxml.jackson.annotation.JsonAlias;
import com.integration.api.utils.JackJsonUtils;
import lombok.Getter;
import lombok.Setter;

@Setter
@Getter
public class TestUser {
    @JsonAlias("xm")
    private String name;

    public static void main(String[] args) {
        String json = "{\"xm\":\"张三\"}";
        System.out.println(JackJsonUtils.toJSONString(JackJsonUtils.parseObject(json, TestUser.class)));
        json = "{\"name\":\"张三\"}";
        System.out.println(JackJsonUtils.toJSONString(JackJsonUtils.parseObject(json, TestUser.class)));
    }
}
  • 输出
{"name":"张三"}
{"name":"张三"}

多别名

  • 通过看源码可以发现,@JsonAlias接收的参数可以是个数组,因为可以设置多个别名。
import com.fasterxml.jackson.annotation.JsonAlias;
import com.integration.api.utils.JackJsonUtils;
import lombok.Getter;
import lombok.Setter;

@Setter
@Getter
public class TestUser {
    @JsonAlias({"xm", "mc", "username", "NAME"})
    private String name;

    public static void main(String[] args) {
        String json = "{\"name\":\"张三\"}";
        System.out.println(JackJsonUtils.toJSONString(JackJsonUtils.parseObject(json, TestUser.class)));
        json = "{\"xm\":\"张三\"}";
        System.out.println(JackJsonUtils.toJSONString(JackJsonUtils.parseObject(json, TestUser.class)));
        json = "{\"mc\":\"张三\"}";
        System.out.println(JackJsonUtils.toJSONString(JackJsonUtils.parseObject(json, TestUser.class)));
        json = "{\"username\":\"张三\"}";
        System.out.println(JackJsonUtils.toJSONString(JackJsonUtils.parseObject(json, TestUser.class)));
        json = "{\"NAME\":\"张三\"}";
        System.out.println(JackJsonUtils.toJSONString(JackJsonUtils.parseObject(json, TestUser.class)));
    }
}

  • 输出
{"name":"张三"}
{"name":"张三"}
{"name":"张三"}
{"name":"张三"}
{"name":"张三"}

总结

  • 使用JsonAlias注解后,原来实体类内的字段名反序列化时依然有效。比如你原来小名叫【李狗蛋】,使用JsonAlias给你赋予别名【李世民】后,Jackson反序列化时知道【李狗蛋】【李世民】都是你。
  • 使用JsonAlias注解内容,只会作为反序列化时的别名,对序列化无影响。

具有相似用法的注解:@JsonProperty

源码

package com.fasterxml.jackson.annotation;

import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;

@Target({ElementType.ANNOTATION_TYPE, ElementType.FIELD, ElementType.METHOD, ElementType.PARAMETER})
@Retention(RetentionPolicy.RUNTIME)
@JacksonAnnotation
public @interface JsonProperty {
    String USE_DEFAULT_NAME = "";
    int INDEX_UNKNOWN = -1;

    String value() default "";

    boolean required() default false;

    int index() default -1;

    String defaultValue() default "";

    JsonProperty.Access access() default JsonProperty.Access.AUTO;

    public static enum Access {
        AUTO,
        READ_ONLY,
        WRITE_ONLY,
        READ_WRITE;

        private Access() {
        }
    }
}

基本用法

import com.fasterxml.jackson.annotation.JsonAlias;
import com.fasterxml.jackson.annotation.JsonProperty;
import com.integration.api.utils.JackJsonUtils;
import lombok.Getter;
import lombok.Setter;

@Setter
@Getter
public class TestUser {
    @JsonAlias({"xm", "mc", "username", "NAME"})
    @JsonProperty("xingming")
    private String name;

    public static void main(String[] args) {
        String json = "{\"name\":\"张三\"}";
//        System.out.println(JackJsonUtils.toJSONString(JackJsonUtils.parseObject(json, TestUser.class)));
        json = "{\"xm\":\"张三\"}";
        System.out.println(JackJsonUtils.toJSONString(JackJsonUtils.parseObject(json, TestUser.class)));
        json = "{\"mc\":\"张三\"}";
        System.out.println(JackJsonUtils.toJSONString(JackJsonUtils.parseObject(json, TestUser.class)));
        json = "{\"username\":\"张三\"}";
        System.out.println(JackJsonUtils.toJSONString(JackJsonUtils.parseObject(json, TestUser.class)));
        json = "{\"NAME\":\"张三\"}";
        System.out.println(JackJsonUtils.toJSONString(JackJsonUtils.parseObject(json, TestUser.class)));
        json = "{\"xingming\":\"张三\"}";
        System.out.println(JackJsonUtils.toJSONString(JackJsonUtils.parseObject(json, TestUser.class)));
    }
}

  • 输出
{"xingming":"张三"}
{"xingming":"张三"}
{"xingming":"张三"}
{"xingming":"张三"}
{"xingming":"张三"}

区别总结

JsonProperty还有其他参数,此处不做演示讲解,有兴趣可自行测试。

  • JsonProperty给予的名字,会同时作为序列化和反序列化的名字,即改字段失去了原有的名字。

  • JsonProperty只能设置一个名字。

  • 如果json字符串中同时含有JsonProperty和JsonAlias给予的名字,反序列化时会以JsonProperty的值为准。
    编程切勿纸上谈兵,一切代码都需要自己去实践和感受,才能真正建立自己的理解。


版权声明:本文为hu18315778112原创文章,遵循CC 4.0 BY-SA版权协议,转载请附上原文出处链接和本声明。