采坑: Lombok 的 boolean 序列化问题

问题复现

  今天碰到一个小问题,调用方反馈我们支付回调接口返回的数据字段和文档定义不一致.文档定义的字段名称是 isClose,而实际返回字段是 close.
  我赶紧查看源码,代码非常简单,只有Lombok 注解,那问题的源头肯定是使用Lombok注解导致的了!

  • 源码
@Data
@AllArgsConstructor
@NoArgsConstructor
public class PayCallBackResponse implements Serializable {

    private static final long serialVersionUID = 4454976958022297251L;

    boolean isClose;
}
  • lombok 生成的set方法
         PayCallBackResponse response = new PayCallBackResponse();
         response.setClose(Boolean.FALSE);

  这样一看就很明了,都是 Lombok 惹得祸

修复方案

  修复方式非常简单,将属性类型修改为 Boolean 包装类型即可

  • 源码
@Data
@AllArgsConstructor
@NoArgsConstructor
public class PayCallBackResponse implements Serializable {

    private static final long serialVersionUID = 4454976958022297251L;
 
    Boolean isClose;
}
  • 修复后,lombok 生成的set方法
        PayCallBackResponse response = new PayCallBackResponse();
        response.setIsClose(Boolean.FALSE);
问题原因

  时间关系并没有查看 Lombok 源码,但是根据经验猜测,是因为 Lombok 遵守 JavaBean 规范(布尔类型 的字段命名是 isXxx 时,get/set 方法可以省略 is前缀)引起的.Mybatis 源码中的 JavaBean 解析也有此类问题.