SpringMvc中返回json时对象属性为空也要返回key

2022-06-22 00:00:00 返回 为空 也要

场景: 最近在写接口时候,正常使用@RestController返回json串,发现当返回的对象里的属性值为空字符串或者null时候,json返回里就会自动去除这个key,啥意思呢?举个”栗子”:

/**
     * 商品评论、回复、点赞【查询】接口
     *
     * @param goodsId
     * @param userId
     * @param currenPage
     * @param pageSize
     * @return
     * @author simons.fan
     */
    @GetMapping("/get-comments-replys")
    public Response getCommentsAndReplys(
            @RequestParam(value = "goodsid", required = false) Long goodsId,
            @RequestParam(value = "userid", required = false) Long userId,
            @RequestParam(value = "currenpage", defaultValue = "1", required = false) Integer currenPage,
            @RequestParam(value = "pagesize", defaultValue = "20", required = false) Integer pageSize) {
        log.info("商品评论查询接口入参:[goodsid={},userid={},currentpage={},pagesize={}]", goodsId, userId, currenPage, pageSize);
        if (goodsId == null || userId == null)
            return new Response(BaseCodeEnum.PARAMETER_MISS, null);
        try {
            PageBean<CommentsResultVo> commentPageBean = goodsService.getCommentsAndReplys(
                    ImmutableMap.of(
                            "userId", userId,
                            "goodsId", goodsId,
                            "currentPage", currenPage,
                            "pageSize", pageSize
                    ));
            return new Response(BaseCodeEnum.SUCCESS, commentPageBean);
        } catch (Exception e) {
            log.error("商品评论查询接口异常:[userid={},goodsid={},ex={}]", userId, goodsId, e);
        }
        return new Response(BaseCodeEnum.ERROR, null);
    }

CommentsResultVo部分属性为:

@Data
public class Comment {
    private Long id;
    private Long goodsId;
    private Long userId;
    private String commentMsg;
    private Long likeCount;
    /**
     * 用户名
     */
    private String userName;
    /**
     * 用户头像url
     */
    private String avatarUrl;
    /**
     * 用户昵称
     */
    private String userNickName;
}

这么一个方法,预期返回的json应该是:即当avatarUrl为空时候,avatarUrl这个key也必须存在(因为接口的响应报文里面字段非常多,我这里去除了很多字段,主要是一种规范,也是为了前端方便调用)

《SpringMvc中返回json时对象属性为空也要返回key》

可实际情况是,当CommentResultVo类里面的某些属性为空或null时候,比如 avatarUrl属性值为空,json串就直接去掉了这个avatarUrl这个key,不够友好。众所周知,springmvc里默认是使用jackson来处理返回的json对象的,一顿源码找,发现不会过滤掉才对的,纳闷,忽然间看到了项目里存在如下代码:

@Configuration
public class WebConfiguration {
    /**
     * 使用fastjson解析对象返回数据
     *
     * @return
     */
    @Bean
    public HttpMessageConverters fastJsonHttpMessageConverters() {
        FastJsonHttpMessageConverter fastConverter = new FastJsonHttpMessageConverter();
        FastJsonConfig fastJsonConfig = new FastJsonConfig();
        fastJsonConfig.setSerializerFeatures(SerializerFeature.PrettyFormat);
        List<MediaType> fastMediaTypes = new ArrayList<>();
        fastMediaTypes.add(MediaType.APPLICATION_JSON_UTF8);
        fastConverter.setSupportedMediaTypes(fastMediaTypes);
        fastConverter.setFastJsonConfig(fastJsonConfig);
        HttpMessageConverter<?> converter = fastConverter;
        return new HttpMessageConverters(converter);
    }
}

问题就在这里,有个同事显式的设置了fastjson来替代默认的jackson处理json返回,这下就好办了,加上新增的序列化方式SerializerFeature.WriteNullStringAsEmpty 即可顺利解决我的问题:

fastJsonConfig.setSerializerFeatures(SerializerFeature.WriteNullStringAsEmpty, SerializerFeature.PrettyFormat);

上述是在springboot中操作的,xml方式如下:

《SpringMvc中返回json时对象属性为空也要返回key》 注:图片取自网络

这种需求是很常见的,value值为空,key也得返回,这样前端可以很友好的处理你的json。

延伸出来的问题有:

1、当返回的集合类型为空也要包含[ ],例如   “commentList”:[ ],而不是 “commentList”:null 或”commentList”:” “;

2、属性为空,自动给属性对应值赋值为默认的缺省值,比如userId是Long类型,如果为空就自动赋值为0,userName是String,为空则自动赋值为””,而不是null;

当然,有些接口比较特殊,它就是需要和上面相反的做法:当key为空或null,这个字段就不需要返回,这个话,可以借助JackSon的@JsonSerialize(include=JsonSerialize.Inclusion.NON_NULL)注解,加在实体类上即可。

今天暂时就先写这么多吧,忙工作,后面抽时间续写……未完待续……

引申阅读

《SpringMvc中返回json时对象属性为空也要返回key》 Json和Bean间的序列化和反序列化(JSONObject、Gson、FastJson的使用):https://love1024.blog.csdn.net/article/details/78246870

    原文作者:饭一碗
    原文地址: https://blog.csdn.net/fanrenxiang/article/details/95044907
    本文转自网络文章,转载此文章仅为分享知识,如有侵权,请联系博主进行删除。

相关文章