优雅的返回json数据之Jackson常用注解介绍

优雅的返回json数据之Jackson常用注解介绍

一、Jackson简介

1. Jackson可以用来干嘛?

Jackson 是一个能够将java对象序列化为JSON字符串,也能够将JSON字符串反序列化为java对象的框架。

2. Json解析器

Jackson提供了两种不同的JSON解析器:

  • ObjectMapper: 把JSON解析到自定义的Java类中,或者解析到一个Jackson指定的树形结构中(Tree model);
  • Jackson JsonParser: 一种“拉式”(pull)解析器,每次解析一组JSON数据。

3. Json生成器

Jackson也包含了两种不同的JSON生成器:

  • ObjectMapper: 把自定义的Java类,或者一个Jackson指定的树形结构生成为JSON文件;
  • Jackson JsonGenerator: 每次只生成一组JSON数据。

二、Jackson常用注解

官方Wiki:https://github.com/FasterXML/jackson-annotations/wiki/Jackson-Annotations

1. 序列化/反序列化时忽略特定属性

在很多场景里,我们并不希望将Java对象的所有属性都序列化。举个例子,我们有一个User实体类,里面有username、password等字段,为了增强安全性,在返回的json数据中肯定是不能包含password属性的。

(1)@JsonIgnoreProperties

@JsonIgnoreProperties是类级别的注解,写在需要序列化 / 反序列化的类上,用来列出要忽略的属性,或表示将忽略任何未知的属性。

  • 序列化时,@JsonIgnoreProperties({"prop1", "prop2"}) 表示忽略Java类里的prop1、prop2对象;
  • 反序列化时,@JsonIgnoreProperties(ignoreUnknown=true) 表示忽略没有 Getter / Setter方法的属性。

@JsonIgnoreProperties还可以配合allowGetters,allowSetters一起用,用来控制是在序列化还是反序列化的时候才忽略属性,这样更加灵活,如:

  • @JsonIgnoreProperties(value = {"prop1", "prop2"},allowGetters = true) 表示属性允许序列化,反序列的时候忽略该属性;
  • @JsonIgnoreProperties(value = {"prop1", "prop2"},allowSetters = true) 允许属性反序列化,序列化的时候忽略该属性。
(2)@JsonIgnore

@JsonIgore注解是方法级别的注解,写在类属性上或类属性的 Getter / Setter方法上,用于忽略指定属性的序列化与反序列化。

  • 仅需要将该注解添加到 属性名、属性的getter / setter方法 三者中的其中一个上面。@JsonIgore 注解会影响“ 整个”属性:也就是说,向“ getter”方法中添加注解也将禁用“ setter”方法。
  • 如果需要控制到更小粒度,我们可以用@JsonProperty 注解来控制是在序列化还是反序列化的时候才忽略属性。 比如,在属性的getter方法上写@JsonIgnore 注解,“ setter”方法上写@JsonProperty 注解,表示允许属性反序列化,序列化的时候忽略该属性。
(3)@JsonIgnoreType

@JsonIgnoreType是类级别的注解,写在Java类上,表明在序列化和反序列化的时候忽略这个类 。

(4)@JsonInclude

@JsonInclude 注解用于定义序列化时是否不应包含某些“non-values ” (nulls or empty values);可以按属性使用,也可以作为类的默认值使用(用于类的所有属性)。有以下几种策略:

  • @JsonInclude(value = JsonInclude.Include.ALWAYS) ,默认策略,表示任何情况下都序列化该字段,和不写这个注解是一样的效果。
  • @JsonInclude(value = JsonInclude.Include.NON_NULL) ,最常用策略,表示如果加该注解的字段为null,那么就不序列化这个字段了。

mark

2.序列化/反序列化时格式化日期属性

@JsonFormat 注解用于指定序列化日期/时间值(Date/Time)时要使用的格式。

(1)格式化Date

首先我这里写个实体类,getter和setter方法没有贴出来:

public class Param {
    private Date date;
}

这是这个实体类序列化后的json数据格式显示 :

{
  "date": "2019-04-28T08:18:21.554+0000"
}

对实体类稍微修饰了一下,加上了格式转换 :

public class Param {
    @JsonFormat(shape = JsonFormat.Shape.STRING , pattern = "yyyy-MM-dd HH:mm:ss")
    private Date date;
}

现在序列化后的json数据长下面这样:

{
  "date": "2019-04-28 08:24:14"
}
(2)返回毫秒数

还是同一个实体类,此时指定shape为 JsonFormat.Shape.NUMBER类型,返回的是毫秒数。

public class Param {
    @JsonFormat(shape = JsonFormat.Shape.NUMBER)
    private Date date;
}

序列化后的json数据长下面这样:

{
  "date": 1556440065032
}
(3)指定时区
public class Param {
    @JsonFormat(shape = JsonFormat.Shape.STRING , pattern = "yyyy-MM-dd HH:mm:ss", , timezone = "UTC")
    private Date date;
}
{
  "date": "2019-04-28 08:30:47"
}

我测试的时候每次返回的都是现在的时间,但是现在的时间是16点多,但是一直显示的是早上八点多,所以我看了下里面的代码,发现用了这个注解以后默认的时区就是UTC,所以用这个注解的时候要进行时区转换。

    /**
     * {@link java.util.TimeZone} to use for serialization (if needed).
     * Special value of {@link #DEFAULT_TIMEZONE}
     * can be used to mean "just use the default", where default is specified
     * by the serialization context, which in turn defaults to system
     * default (UTC) unless explicitly set to another timezone.
     */
    public String timezone() default DEFAULT_TIMEZONE;

将时区重新设置成Asia/Shanghai

public class Param {
    @JsonFormat(shape = JsonFormat.Shape.STRING , pattern = "yyyy-MM-dd HH:mm:ss", , timezone = "Asia/Shanghai")
    private Date date;
}

现在时间就是咱们的北京时间了,16点多。

{
  "date": "2019-04-28 16:45:22"
}

参考资料

[1]:Jackson Wiki

[2]:jackSon中@JsonFormat注解使用详解

  • 1
    点赞
  • 6
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值