Spring如何定义一个统一返回类呢?
下文笔者讲述Spring定义一个统一返回类的方法及示例分享
定义统一返回类的实现思路:
1.定义一个泛型类 用于返回类对象
2.使用ResponseUtil封装 返回类
3.使用@RestControllerAdvice拦截返回内容
统一返回类
import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.annotation.JSONField;
import com.fasterxml.jackson.annotation.JsonProperty;
import io.swagger.annotations.ApiModel;
import io.swagger.annotations.ApiModelProperty;
@ApiModel(value = "response", description = "响应")
public class Response<T> {
@JsonProperty("rsp_code")
@JSONField(name = "rsp_code")
@ApiModelProperty(value = "响应码(0:成功)", position = 1)
private int rspCode = 0;
@JsonProperty("rsp_desc")
@JSONField(name = "rsp_desc")
@ApiModelProperty(value = "响应码描述 ", position = 2)
private String rspDesc = "successful";
@ApiModelProperty(value = "数据", position = 5)
private T data;
public int getRspCode() {
return rspCode;
}
public void setRspCode(int rspCode) {
this.rspCode = rspCode;
}
public String getRspDesc() {
return rspDesc;
}
public void setRspDesc(String rspDesc) {
this.rspDesc = rspDesc;
}
public T getData() {
return data;
}
public void setData(T data) {
this.data = data;
}
@Override
public String toString() {
return JSON.toJSONString(this);
}
}
import io.swagger.annotations.ApiModel;
import io.swagger.annotations.ApiModelProperty;
@ApiModel(value = "pagingResponse", description = "分页响应")
public class PagingResponse<T> extends Response<T> {
@ApiModelProperty(value = "总条数", position = 3)
private long total;
@ApiModelProperty(value = "总页数", position = 4)
private int pages;
public long getTotal() {
return total;
}
public void setTotal(long total) {
this.total = total;
}
public int getPages() {
return pages;
}
public void setPages(int pages) {
this.pages = pages;
}
}
统一返回工具类
import com.github.pagehelper.PageInfo; import com.java265.common.DataEntity.Model.Response.Common.PagingResponse; import com.java265.common.DataEntity.Model.Response.Common.Response; import org.springframework.data.domain.Page; import java.util.list; public class ResponseUtil { public static <T> Response<T> out(T t) { Response<T> res = new Response<>(); res.setData(t); return res; } public static <T> Response<T> outSuccess() { Response<T> res = new Response<>(); return res; } public static <T> Response<T> outFail() { Response<T> res = new Response<>(); res.setRspCode(-1); res.setRspDesc("操作失败"); return res; } public static <T> PagingResponse<T> outNull() { PagingResponse<T> res = new PagingResponse<>(); res.setData(null); return res; } public static <T> Response<T> outError(String desc) { Response<T> res = new Response<>(); res.setRspCode(-1); res.setRspDesc(desc); return res; } public static <T> PagingResponse<List<T>> out(List<T> t, long total, int pages) { PagingResponse<List<T>> res = new PagingResponse<>(); res.setData(t); res.setPages(pages); res.setTotal(total); return res; } public static <T> PagingResponse<List<T>> out(Page<T> page) { PagingResponse<List<T>> res = new PagingResponse<>(); if (page == null) { return res; } res.setData(page.getContent()); res.setPages(page.getTotalPages()); res.setTotal(page.getTotalElements()); return res; } public static <T> PagingResponse<List<T>> out(PageInfo<T> page) { PagingResponse<List<T>> res = new PagingResponse<>(); if (page == null) { return res; } res.setData(page.getList()); res.setPages(page.getPages()); res.setTotal(page.getTotal()); return res; } public static <T> PagingResponse<List<T>> outPageError(String desc) { PagingResponse<List<T>> res = new PagingResponse<>(); res.setRspCode(-1); res.setRspDesc(desc); return res; } }
controller二次封装
import com.github.pagehelper.PageInfo;
import com.java265.common.DataEntity.Model.Response.Common.Response;
import com.java265.core.DataApi.Common.Util.ResponseUtil;
import org.springframework.core.MethodParameter;
import org.springframework.data.domain.Page;
import org.springframework.http.MediaType;
import org.springframework.http.converter.HttpMessageConverter;
import org.springframework.http.server.ServerHttpRequest;
import org.springframework.http.server.ServerHttpResponse;
import org.springframework.web.bind.annotation.RestControllerAdvice;
import org.springframework.web.servlet.mvc.method.annotation.ResponseBodyAdvice;
@RestControllerAdvice
public class ResponseHandler implements ResponseBodyAdvice<Object> {
/**
* 只处理有RestResponse注解的方法,防止处理其他不需要封装的,或者swaggwer等
*
* @param returnType
* @param converterType
* @return
*/
@Override
public boolean supports(MethodParameter returnType, Class<? extends HttpMessageConverter<?>> converterType) {
//直接返回true就是拦截所有的controller,也会拦截swagger的controller导致swagger不可用
return returnType.hasMethodAnnotation(RestResponse.class);
}
@Override
public Object beforeBodyWrite(Object body, MethodParameter returnType, MediaType selectedContentType,
Class<? extends HttpMessageConverter<?>> selectedConverterType, ServerHttpRequest request,
ServerHttpResponse response) {
Response respVo = null;
if (body instanceof Response) {
respVo = (Response) body;
} else if (body instanceof Page) {
Page page = (Page) body;
respVo = ResponseUtil.out(page);
} else if (body instanceof PageInfo) {
PageInfo pageInfo = (PageInfo) body;
respVo = ResponseUtil.out(pageInfo);
} else {
respVo = ResponseUtil.out(body);
}
//如果返回的字符串类型,会先判断HttpMessageConverter能否支持对应的返回类型再使用ResponseBodyAdvice进行封装
//那么此时在进来就不是String类型,所以会报无法转换成ResponseVO对象,那么这里有两种方法,一种是直接返回json字符串,另一种是
//一种是自己的WebConfig进行额外的配置
// if (body instanceof String){
// return JSONUtil.toJsonStr(respVo);
// }
return respVo;
}
}
定义加入此注解的内容会被转换
package com.java265.core.DataApi.Common.Response;
import java.lang.annotation.*;
/**
*
* @Desc 忽略统一返回封装的注解
* @date 2023/2/17 14:45
*/
@Documented
@Inherited
@Target({ElementType.ANNOTATION_TYPE, ElementType.METHOD})
@Retention(RetentionPolicy.Runtime)
public @interface RestResponse {
}
版权声明
本文仅代表作者观点,不代表本站立场。
本文系作者授权发表,未经许可,不得转载。


