jackSon注解– @JsonInclude 注解不返回null值字段
Spring Boot項目中遇到的小知識
@Data @JsonInclude(JsonInclude.Include.NON_NULL) public class OrderDTO { private String orderId; @JsonProperty("name") private String buyerName; @JsonProperty("phone") private String buyerPhone; @JsonProperty("address") private String buyerAddress; @JsonProperty("openid") private String buyerOpenid; private BigDecimal orderAmount; /** * 訂單狀態,默認是0 */ private Integer orderStatus; /** * 支付狀態 */ private Integer payStatus; @JsonSerialize(using = Date2LongSerializer.class) private Timestamp createTime; @JsonSerialize(using = Date2LongSerializer.class) private Timestamp updateTime; @JsonProperty("items") List<OrderDetailEntity> orderDetailList; }
@JsonInclude(JsonInclude.Include.NON_NULL)表示,如果值為null,則不返回
全局jsckson配置
spring: datasource: driver-class-name: com.mysql.jdbc.Driver username: root password: 123456 url: jdbc:mysql://192.168.41.60/sell?characterEncoding=utf-8&useSSL=false jpa: show-sql: true jackson: default-property-inclusion: non_null # 全局jackson配置
JSON庫 Jackson 常用注解介紹
注:以下所涉及到的實體類都使用了 Lomback 插件
Jackson JSON 框架中包含了大量的注解來讓我們可以干預 Jackson 的 JSON 處理過程,
例如我們可以通過注解指定 java pojo 的某些屬性在生成 json 時被忽略。。本文主要介紹如何使用 Jackson 提供的注解。
Jackson注解主要分成三類,一是只在序列化時生效的注解;二是只在反序列化時候生效的注解;三是兩種情況下都生效的注解。
一: 兩種情況下都有效的注解
1. @JsonIgnore 作用域屬性或方法上
@JsonIgnore 用來告訴 Jackson 在處理時忽略該注解標注的 java pojo 屬性,
不管是將 java 對象轉換成 json 字符串,還是將 json 字符串轉換成 java 對象。
@Data public class SellerInfoEntity { private String id; private String username; private String password; private String openid; @JsonIgnore private Timestamp createTime; @JsonIgnore private Timestamp updateTime; public SellerInfoEntity() { } public SellerInfoEntity(String id, String username, String password, String openid) { this.id = id; this.username = username; this.password = password; this.openid = openid; } }
2. @JsonIgnoreProperties 作用在類上
@JsonIgnoreProperties 和 @JsonIgnore 的作用相同,都是告訴 Jackson 該忽略哪些屬性,
不同之處是 @JsonIgnoreProperties 是類級別的,並且可以同時指定多個屬性。
@Data @JsonIgnoreProperties(value = {"createTime","updateTime"}) public class SellerInfoEntity { private String id; private String username; private String password; private String openid; private Timestamp createTime; private Timestamp updateTime; public SellerInfoEntity() { } public SellerInfoEntity(String id, String username, String password, String openid) { this.id = id; this.username = username; this.password = password; this.openid = openid; } }
使用Spring Boot快速搭建Controller進行測試:
@RestController @RequestMapping("/jackson") public class TestJackson { @RequestMapping("test1") public Result test1(){ SellerInfoEntity entity = new SellerInfoEntity("1","user1","123456","openid"); return new Result(MyResultEnum.SUCCESS,entity); } }
訪問: localhost/sell/jackson/test1
使用注解前:返回值
{ "code": 0, "msg": "成功", "data": { "id": "1", "username": "user1", "password": "123456", "openid": "openid", "createTime": null, "updateTime": null } }
使用注解后:返回值
{ "code": 0, "msg": "成功", "data": { "id": "1", "username": "user1", "password": "123456", "openid": "openid", } }
3. @JsonIgnoreType
@JsonIgnoreType 標注在類上,當其他類有該類作為屬性時,該屬性將被忽略。
package org.lifw.jackosn.annotation; import com.fasterxml.jackson.annotation.JsonIgnoreType; @JsonIgnoreType public class SomeOtherEntity { private Long id; public Long getId() { return id; } public void setId(Long id) { this.id = id; } }
public class SomeEntity { private String name; private String desc; private SomeOtherEntity entity; }
SomeEntity 中的 entity 屬性在json處理時會被忽略。
4. @JsonProperty
@JsonProperty 可以指定某個屬性和json映射的名稱。例如我們有個json字符串為{“user_name”:”aaa”},
而java中命名要遵循駝峰規則,則為userName,這時通過@JsonProperty 注解來指定兩者的映射規則即可。這個注解也比較常用。
public class SomeEntity { @JsonProperty("user_name") private String userName; // ... }
二、只在序列化情況下生效的注解
1. @JsonPropertyOrder
在將 java pojo 對象序列化成為 json 字符串時,使用 @JsonPropertyOrder 可以指定屬性在 json 字符串中的順序。
2. @JsonInclude
在將 java pojo 對象序列化成為 json 字符串時,使用 @JsonInclude 注解可以控制在哪些情況下才將被注解的屬性轉換成 json,例如只有屬性不為 null 時。
@Data @JsonInclude(JsonInclude.Include.NON_NULL) public class SellerInfoEntity { private String id; private String username; @JsonInclude(JsonInclude.Include.NON_EMPTY) private String password; private String openid; private Timestamp createTime; private Timestamp updateTime; public SellerInfoEntity() { } public SellerInfoEntity(String id, String username, String password, String openid) { this.id = id; this.username = username; this.password = password; this.openid = openid; } }
Controller 測試
@RestController @RequestMapping("/jackson") public class TestJackson { @RequestMapping("test1") public Result test1(){ SellerInfoEntity entity = new SellerInfoEntity("1","user1","","openid"); return new Result(MyResultEnum.SUCCESS,entity); } }
結果:
{ "code": 0, "msg": "成功", "data": { "id": "1", "username": "user1", "openid": "openid" } }
上述例子的意思是 SellerInfoEntity 的所有屬性只有在不為 null 的時候才被轉換成 json,
如果為 null 就被忽略。並且如果password為空字符串也不會被轉換.
該注解也可以加在某個字段上。
另外還有很多其它的范圍,例如 NON_EMPTY、NON_DEFAULT等
三、是在反序列化情況下生效的注解
1. @JsonSetter
@JsonSetter 標注於 setter 方法上,類似 @JsonProperty ,也可以解決 json 鍵名稱和 java pojo 字段名稱不匹配的問題。
public class SomeEntity { private String desc; @JsonSetter("description") public void setDesc(String desc) { this.desc = desc; } }
上述例子中在將 json 字符串轉換成 SomeEntity 實例時,會將 json 字符串中的 description 字段賦值給 SomeEntity 的 desc 屬性。
Spring Boot中全局處理返回為空或null的字段,不需要其他注解,直接加入這個類就可以過濾字段值為空和null的情況:
import org.springframework.boot.autoconfigure.condition.ConditionalOnMissingBean; import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; import org.springframework.context.annotation.Primary; import org.springframework.http.converter.json.Jackson2ObjectMapperBuilder; import com.fasterxml.jackson.annotation.JsonInclude; import com.fasterxml.jackson.databind.ObjectMapper; @Configuration public class JacksonConfig { @Bean @Primary @ConditionalOnMissingBean(ObjectMapper.class) public ObjectMapper jacksonObjectMapper(Jackson2ObjectMapperBuilder builder) { ObjectMapper objectMapper = builder.createXmlMapper(false).build(); objectMapper.setSerializationInclusion(JsonInclude.Include.NON_EMPTY); objectMapper.setSerializationInclusion(JsonInclude.Include.NON_NULL); return objectMapper; } }