使用SpringBoot使用過濾器去除@RequestBody參數兩端的空格


使用SpringBoot使用過濾器去除@RequestBody參數兩端的空格

使用SpringBoot使用過濾器去除@RequestBody參數兩端的空格;一般我們去普通的請求我們都會對請求參數進行驗證。Java也提供了@notNull和@notBlank這種驗證方式,但是對@RequestBody 這種只能驗證是不是非空,對數據兩端的空格未進行處理,同時大家也不想遍歷一遍參數然后再處理再封裝到對象中,正好項目中有這個需要,所以就參考別的做了Post請求中針對application/json格式的有@RequestBody注解的參數進行了去空格處理

協議:CC BY-SA 4.0 https://creativecommons.org/licenses/by-sa/4.0/

版權聲明:本文為原創文章,遵循 CC 4.0 BY-SA 版權協議,轉載請附上原文出處鏈接及本聲明。

第一步:編寫一個配置信息

ParamsFilterConfig.java

package com.codepeople.framework.config;

import javax.servlet.DispatcherType;

import org.springframework.boot.web.servlet.FilterRegistrationBean;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

import com.ruoyi.framework.filter.ParamsFilter;

/**
 * @ClassName: ParamsFilterConfig
 * @Description: SpringBoot中去除@RequestBody中前后端空格
 * @Author 劉 仁
 * @DateTime 2020-7-23 10:07:02
 */
@Configuration
public class ParamsFilterConfig {

	@Bean
	public FilterRegistrationBean paramsFilterRegistration() {
		FilterRegistrationBean registration = new FilterRegistrationBean();
		registration.setDispatcherTypes(DispatcherType.REQUEST);
        registration.setFilter(new ParamsFilter());
        registration.addUrlPatterns("/*");
        registration.setName("paramsFilter");
        registration.setOrder(Integer.MAX_VALUE-1);
        return registration;
	}
}

第二步:編寫ParamsFilter過濾器

ParamsFilter.java

package com.codepeople.framework.filter;

import java.io.IOException;

import javax.servlet.DispatcherType;
import javax.servlet.Filter;
import javax.servlet.FilterChain;
import javax.servlet.FilterConfig;
import javax.servlet.ServletException;
import javax.servlet.ServletRequest;
import javax.servlet.ServletResponse;
import javax.servlet.annotation.WebFilter;
import javax.servlet.http.HttpServletRequest;

import org.springframework.stereotype.Component;

@Component
@WebFilter(urlPatterns = "/**", filterName = "ParamsFilter", dispatcherTypes = DispatcherType.REQUEST)
public class ParamsFilter implements Filter {

	@Override
	public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain)
			throws IOException, ServletException {
		ParameterRequestWrapper parmsRequest = new ParameterRequestWrapper((HttpServletRequest) request);
		chain.doFilter(parmsRequest, response);
	}

	@Override
	public void init(FilterConfig filterConfig) throws ServletException {
		
	}

	@Override
	public void destroy() {
		
	}

	
}

第三步:實現ParameterRequestWrapper

ParameterRequestWrapper.java

package com.codepeople.framework.filter;

import java.io.ByteArrayInputStream;
import java.io.IOException;
import java.util.HashMap;
import java.util.Iterator;
import java.util.Map;
import java.util.Set;

import javax.servlet.ReadListener;
import javax.servlet.ServletInputStream;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletRequestWrapper;

import org.apache.commons.io.IOUtils;
import org.apache.commons.lang3.StringUtils;
import org.springframework.http.HttpHeaders;
import org.springframework.http.MediaType;

import com.alibaba.fastjson.JSON;
import com.codepeople.framework.util.StringJsonUtils;

public class ParameterRequestWrapper extends HttpServletRequestWrapper {

	private Map<String , String[]> params = new HashMap<>();
	
	public ParameterRequestWrapper(HttpServletRequest request) {
		// 將request交給父類,以便於調用對應方法的時候,將其輸出,其實父親類的實現方式和第一種new的方式類似
        super(request);
        //將參數表,賦予給當前的Map以便於持有request中的參數
        Map<String, String[]> requestMap=request.getParameterMap();
        this.params.putAll(requestMap);
        this.modifyParameterValues();
	}

	/**
	 * 重寫getInputStream方法  post類型的請求參數必須通過流才能獲取到值 
	 */
	@Override
    public ServletInputStream getInputStream() throws IOException {
		/** 非json類型,直接返回 */
		if(!super.getHeader(HttpHeaders.CONTENT_TYPE).equalsIgnoreCase(MediaType.APPLICATION_JSON_VALUE)){
            return super.getInputStream();
        }
        //為空,直接返回
        String json = IOUtils.toString(super.getInputStream(), "utf-8");
        if (StringUtils.isEmpty(json)) {
            return super.getInputStream();
        }
        System.out.println("去除POST請求數據兩端的空格前參數:"+json);
        Map<String,Object> map= StringJsonUtils.jsonStringToMap(json);
        System.out.println("去除POST請求數據兩端的空格后參數:"+JSON.toJSONString(map));
        ByteArrayInputStream bis = new ByteArrayInputStream(JSON.toJSONString(map).getBytes("utf-8"));
        return new MyServletInputStream(bis);
    }

	/**
	 * @Title: modifyParameterValues
	 * @Description:  將parameter的值去除空格后重寫回去
	 * @DateTime 2020-7-23 10:31:12
	 */
    public void modifyParameterValues(){
        Set<String> set = params.keySet();
        Iterator<String> it = set.iterator();
        while(it.hasNext()){
            String key= it.next();
            String[] values = params.get(key);
            values[0] = values[0].trim();
            params.put(key, values);
        }
    }
    
    @Override
    public String getParameter(String name) {
        String[]values = params.get(name);
        if(values == null || values.length == 0) {
            return null;
        }
        return values[0];
    }
    /**
	 * @Title: getParameterValues
	 * @Description:  重寫getParameterValues
	 * @DateTime 2020-7-23 10:31:12
	 */
    @Override
    public String[] getParameterValues(String name) {//同上
        return params.get(name);
    }
 
    class MyServletInputStream extends  ServletInputStream{
        private ByteArrayInputStream bis;
        public MyServletInputStream(ByteArrayInputStream bis){
            this.bis=bis;
        }
        @Override
        public boolean isFinished() {
            return true;
        }
 
        @Override
        public boolean isReady() {
            return true;
        }
 
        @Override
        public void setReadListener(ReadListener listener) {
 
        }
        @Override
        public int read(){
            return bis.read();
        }
    }

}

第四步:利用fastjson實現json字符串轉map功能

package com.codepeople.framework.util;

import java.util.ArrayList;
import java.util.HashMap;
import java.util.Iterator;
import java.util.List;
import java.util.Map;

import com.alibaba.fastjson.JSONArray;
import com.alibaba.fastjson.JSONObject;
/**
 * @ClassName: StringJsonUtils
 * @Description: 
 * @Author 劉 仁
 * @DateTime 2020-7-23 10:26:28
 */
public class StringJsonUtils {
	
	/**
	 * @Title: jsonStringToMap
	 * @Description: 把jsonString轉為Map
	 * @Author 劉 仁
	 * @DateTime 2020-7-23 10:27:11
	 * @param jsonString
	 * @return
	 */
	public static Map<String, Object> jsonStringToMap(String jsonString) {
        Map<String, Object> map = new HashMap<>();
        JSONObject jsonObject = JSONObject.parseObject(jsonString);
        for (Object k : jsonObject.keySet()) {
            Object o = jsonObject.get(k);
            if (o instanceof JSONArray) {
                List<Map<String, Object>> list = new ArrayList<>();
                Iterator<Object> it = ((JSONArray) o).iterator();
                while (it.hasNext()) {
                    Object obj = it.next();
                    list.add(jsonStringToMap(obj.toString()));
                }
                map.put(k.toString(), list);
            } else if (o instanceof JSONObject) {
                // 如果內層是json對象的話,繼續解析
                map.put(k.toString(), jsonStringToMap(o.toString()));
            } else {
                // 如果內層是普通對象的話,直接放入map中
               // map.put(k.toString(), o.toString().trim()); 
                 if (o instanceof String) {
                   map.put(k.toString(), o.toString().trim());
                } else {
                    map.put(k.toString(), o);
                }   
            }
        }
        return map;
    }

}

主要引入的包

<!--常用工具類 -->
		<dependency>
			<groupId>org.apache.commons</groupId>
			<artifactId>commons-lang3</artifactId>
		</dependency>
<!-- 阿里JSON解析器 -->
		<dependency>
			<groupId>com.alibaba</groupId>
			<artifactId>fastjson</artifactId>
		</dependency>
<!-- io常用工具類 -->
		<dependency>
			<groupId>commons-io</groupId>
			<artifactId>commons-io</artifactId>
		</dependency>
<!-- servlet包 -->
        <dependency>
		    <groupId>javax.servlet</groupId>
		    <artifactId>javax.servlet-api</artifactId>
		</dependency>

測試日志

11:28:07.995 [http-nio-80-exec-17] INFO  c.r.f.f.ParameterRequestWrapper - [getInputStream,54] - 去除POST請求數據兩端的空格前參數:{
	"idNumber": "110101201003073036",
	"password": " 123456 "
}
11:28:07.997 [http-nio-80-exec-17] INFO  c.r.f.f.ParameterRequestWrapper - [getInputStream,56] - 去除POST請求數據兩端的空格后參數:{"password":"123456","idNumber":"110101201003073036"}

博客地址:https://www.codepeople.cn

=====================================================================

微信公眾號:


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM