随手记录6:application/json 类型请求修改request中的请求参数
简介
http请求类型为contentType = application/json
传递的json格式的参数,在到对应的Controll之前修改对应request中的请求参数,也可以通过filter中获取到请求参数统一修改/新增某个属性字段完成统一处理的逻辑内容
代码展示
1.DataFormatFilter 自定义的filter
自定义的filter,在doFilter方法中获取到原来的request中的请求参数
@Component
public class DataFormatFilter implements Filter {
@Override
public void doFilter(ServletRequest servletRequest, ServletResponse servletResponse, FilterChain chain)
throws IOException, ServletException {
HttpServletRequest request = (HttpServletRequest) servletRequest;
HttpServletResponse response = (HttpServletResponse) servletResponse;
try {
String requestId = DateFormatUtils.format(new Date(), "yyyyMMddHHmmssSSS") + RandomStringUtils.randomNumeric(8);
//通过在个方法可以将请求参数中的json格式的参数取出来然后在吧json格式的参数放回去(可以在参数里面操作一些内容)
String contentType = request.getContentType();
System.out.println("过滤器DataFormatFilter获取到的 请求方式"+contentType);
//如果传参方式为json格式的内容
if(StringUtils.isNotBlank(contentType) && contentType.equals("application/json")){
BodyReaderHttpServletRequest bodyRequest = new BodyReaderHttpServletRequest(request);
String bodyString = bodyRequest.getReqContentString();
JSONObject jsonObject = JSON.parseObject(bodyString);
jsonObject.put("version","1.0");//请求参数中统一设置version
jsonObject.put("requestId",requestId);//请求参数中统一设置requestId
bodyRequest.setReqContentString(jsonObject.toString());
bodyRequest.setAttribute("attr","获取的attr");
chain.doFilter(bodyRequest, response);
}else{
request.setAttribute("version","1.0");
request.setAttribute("requestId",requestId);
chain.doFilter(request, response);
}
} catch (Exception e) {
e.printStackTrace();
}
return;
}
@Override
public void init(FilterConfig filterConfig) throws ServletException {}
@Override
public void destroy() {
}
}
2.自定义的request类BodyReaderHttpServletRequest
在自定义的request中从写对应的getInputStream( )方法该方法是封装参数到 @requestBody中的.
public class BodyReaderHttpServletRequest extends HttpServletRequestWrapper {
private String reqBody = null;
public BodyReaderHttpServletRequest(HttpServletRequest request) {
super(request);
//获取原有request中的请求参数设置到本对象中
reqBody = HttpHelper.getBodyString(request);
}
@Override
public BufferedReader getReader() throws IOException {
return new BufferedReader(new InputStreamReader(getInputStream()));
}
/**
* 重写读取方法
*/
@Override
public ServletInputStream getInputStream() throws IOException {
final ByteArrayInputStream bais = new ByteArrayInputStream(reqBody.getBytes(Charset.forName("UTF-8")));
return new ServletInputStream() {
@Override
public boolean isFinished() {
return false;
}
@Override
public boolean isReady() {
return false;
}
@Override
public void setReadListener(ReadListener listener) {}
@Override
public int read() throws IOException {
return bais.read();
}
};
}
public String getReqContentString() {
return reqBody;
}
public void setReqContentString(String content) {
reqBody = content;
}
}
3.HttpHelper request中读取请求参数工具类
public class HttpHelper {
/**
* 获取请求体中的参数内容
* @author khy
* @createTime 2020年11月11日上午10:19:06
* @param request
* @return
*/
public static String getBodyString1(ServletRequest request) {
String result = null;
try (InputStream inputStream = request.getInputStream();){
result = IOUtils.toString(inputStream, CharEncoding.UTF_8);
} catch (IOException e) {
e.printStackTrace();
}
return result;
}
/**
* 获取请求体中的参数内容
* @author khy
* @createTime 2020年11月11日上午10:19:06
* @param request
* @return
*/
public static String getBodyString(ServletRequest request) {
JSONObject json=null;
try (BufferedReader reader = request.getReader();){
StringBuilder sb = new StringBuilder();
String line=null;
while((line=reader.readLine())!=null){
sb.append(line);
}
json=JSONObject.parseObject(StringUtils.defaultIfBlank(sb.toString(), "{}"));
} catch (IOException e) {
e.printStackTrace();
}
return json.toString();
}
}
controll中方法内容
@RequestMapping("/saveUser")
public String saveUser(@RequestBody UserReq req){
return "方法执行完毕"+JSON.toJSONString(req);
}
postman中的请求
总结
请求发送过来到自定义的filter中
判断request的contentType类型;然后通过我们在定义的request中将原有的request中的请求参数获取出来,然后在filter中将获取到的json格式的参数解析然后统一设置我们的请求参数字段之后;设置到自定义的request中;然后重新自定义request中的getInputStream() 方法,最后早controller中方法中通过@requestBody注解将参数封装到实体对象中去;然后看打印结果已经可以看到已经统一修改了;
当然还可以将统一将参数设置到request.attribute属性中,在controll中统一从request中获取对应attribute属性