欧美bbbwbbbw肥妇,免费乱码人妻系列日韩,一级黄片

springboot項目攔截前端請求中的特殊字符串(解決方案)

 更新時間:2023年10月31日 15:15:05   作者:墨落成白123  
springboot項目中,需要對前端請求數(shù)據(jù)進(jìn)行過濾,攔截特殊字符,本文通過實例代碼給大家分享完美解決方案,感興趣的朋友一起看看吧

項目場景:

springboot項目中,需要對前端請求數(shù)據(jù)進(jìn)行過濾,攔截特殊字符。

問題描述

GET請求可以很方便的通過處理URL判斷是否包含特殊字符,POST類型請求需要對form-data/json特殊處理,使用@RequestBody注解的controller獲取不到數(shù)據(jù)

原因分析:

request中的getInputStream()方法和getReader()方法只能獲取一次數(shù)據(jù),通過@RequestBody注解再次獲取getInputStream()拿到結(jié)果為空,此處通過重寫getInputStream()方法和getReader()解決。貼出完整代碼如下。

解決方案:

1、注冊攔截器

package com.xxx;
import org.springframework.context.annotation.Configuration;
import org.springframework.web.servlet.config.annotation.InterceptorRegistry;
import org.springframework.web.servlet.config.annotation.WebMvcConfigurer;
/**
 * @author lsh
 * @version 1.0
 * @date 2022/4/1 16:54
 */
@Configuration
public class SpecialCharConfig implements WebMvcConfigurer {
    @Override
    public void addInterceptors(InterceptorRegistry registry) {
        if(registry!=null){
            registry.addInterceptor(new SpecialCharInterceptor()).addPathPatterns("/**");
        }
    }
}

2、注冊過濾器

package com.xxx;
import org.springframework.stereotype.Component;
import javax.servlet.*;
import javax.servlet.annotation.WebFilter;
import javax.servlet.http.HttpServletRequest;
import java.io.IOException;
/**
 * @author lsh
 * @version 1.0
 * @date 2022/4/1 17:03
 */
@Component
@WebFilter(filterName="specialCharFilter",urlPatterns="/*")
public class SpecialCharFilter implements Filter {
    @Override
    public void init(FilterConfig filterConfig) throws ServletException {
    }
    @Override
    public void doFilter(ServletRequest request, ServletResponse response,FilterChain chain) throws IOException, ServletException {
        ServletRequest requestWrapper = null;
        if (request instanceof HttpServletRequest){
            requestWrapper = new SpecialCharHttpServletRequestWrapper((HttpServletRequest) request);
        }
        // 獲取請求中的流,將取出來的字符串,再次轉(zhuǎn)換成流,然后把它放入到新request對象中
        // 在chain.doFiler方法中傳遞新的request對象
        if(requestWrapper == null) {
            chain.doFilter(request, response);
        } else {
            chain.doFilter(requestWrapper, response);
        }
    }
    @Override
    public void destroy() {
    }
}

3、自定義保存流數(shù)據(jù)

package com.xxx;
import java.io.BufferedReader;
import java.io.ByteArrayInputStream;
import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.nio.charset.Charset;
import javax.servlet.ReadListener;
import javax.servlet.ServletInputStream;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletRequestWrapper;
/**
 * 自定義保存流數(shù)據(jù)
 * @author lsh
 * @version 1.0
 * @date 2022/4/1 16:56
 */
public class SpecialCharHttpServletRequestWrapper extends HttpServletRequestWrapper {
    public final HttpServletRequest  request;
    private final String bodyStr;
    public SpecialCharHttpServletRequestWrapper(HttpServletRequest request) throws IOException {
        super(request);
        this.request = request;
        this.bodyStr = getBodyString();
    }
    /**
     * 獲取請求Body
     * @return
     */
    public String getBodyString() {
        StringBuilder sb = new StringBuilder();
        InputStream inputStream = null;
        BufferedReader reader = null;
        try {
            inputStream = cloneInputStream(request.getInputStream());
            reader = new BufferedReader(new InputStreamReader(inputStream, Charset.forName("UTF-8")));
            String line = "";
            while ((line = reader.readLine()) != null) {
                sb.append(line);
            }
        }
        catch (IOException e) {
            e.printStackTrace();
        }
        finally {
            if (inputStream != null) {
                try {
                    inputStream.close();
                }
                catch (IOException e) {
                    e.printStackTrace();
                }
            }
            if (reader != null) {
                try {
                    reader.close();
                }
                catch (IOException e) {
                    e.printStackTrace();
                }
            }
        }
        return sb.toString();
    }
    /**
     * 復(fù)制輸入流
     * @param inputStream 輸入流
     * @return
     */
    public InputStream cloneInputStream(ServletInputStream inputStream) {
        ByteArrayOutputStream byteArrayOutputStream = new ByteArrayOutputStream();
        byte[] buffer = new byte[1024];
        int len;
        try {
            while ((len = inputStream.read(buffer)) > -1) {
                byteArrayOutputStream.write(buffer, 0, len);
            }
            byteArrayOutputStream.flush();
        }
        catch (IOException e) {
            e.printStackTrace();
        }
        InputStream byteArrayInputStream = new ByteArrayInputStream(byteArrayOutputStream.toByteArray());
        return byteArrayInputStream;
    }
    @Override
    public BufferedReader getReader() throws IOException {
        return new BufferedReader(new InputStreamReader(getInputStream()));
    }
    @Override
    public ServletInputStream getInputStream() throws IOException {
        final ByteArrayInputStream bais = new ByteArrayInputStream(bodyStr.getBytes(Charset.forName("UTF-8")));
        return new ServletInputStream() {
            @Override
            public int read() throws IOException {
                return bais.read();
            }
            @Override
            public void setReadListener(ReadListener listener) {
            }
            @Override
            public boolean isReady() {
                return false;
            }
            @Override
            public boolean isFinished() {
                return false;
            }
        };
    }
}

4、特殊字符攔截類(application/json的數(shù)據(jù)格式只能為json和json數(shù)組,根據(jù)業(yè)務(wù)場景自行調(diào)整)

package com.xxx;
import com.alibaba.fastjson.JSONObject;
import com.alibaba.fastjson.TypeReference;
import org.apache.commons.lang3.StringUtils;
import javax.servlet.http.HttpServletRequest;
import java.io.*;
import java.net.URLDecoder;
import java.util.List;
import java.util.Map;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
/**
 * 攔截請求中包含的特殊字符
 * @author lsh
 * @version 1.0
 * @date 2022/4/1 16:27
 */
public class UrlFilter {
    /**
     * 特殊字符正則表達(dá)式
     */
    private final static String REG_EX = "[`~!@#$%^*()+|{}\\[\\].<>/??。ǎ尽俊?;:”“'。,、\\\\]";
    /**
     * 判斷url中是否含有特殊字符
     * @param urls 前端請求鏈接
     * @return 是否包含特殊字符
     */
    public static boolean checkSpecials(String urls) {
        try {
            if (StringUtils.isNotEmpty(urls)) {
                // url參數(shù)轉(zhuǎn)義
                urls = URLDecoder.decode(urls, "utf-8");
                if (Pattern.compile(REG_EX).matcher(urls).find()) {
                    return true;
                }
            }
        } catch (UnsupportedEncodingException e) {
            e.printStackTrace();
        }
        return false;
    }
    /**
     * 判斷formData值對象中是否包含特殊字符
     * @param map formData值對象
     * @return 是否包含特殊字符
     */
    public static boolean checkSpecials(Map<String,String[]> map){
        if(!map.isEmpty()){
            for(String[] paraArray : map.values()){
                for(String paraStr : paraArray){
                    if(Pattern.compile(REG_EX).matcher(paraStr).find()){
                        return true;
                    }
                }
            }
        }
        return false;
    }
    /**
     * 判斷前端傳過來的json和json數(shù)組中是否含有特殊字符
     * @param request 前端請求(包含json數(shù)據(jù))
     * @return 是否包含特殊字符
     */
    public static boolean checkSpecials(HttpServletRequest request) {
        try {
            SpecialCharHttpServletRequestWrapper wrapper = new SpecialCharHttpServletRequestWrapper(request);
            InputStream is = wrapper.getInputStream();
            BufferedReader br = new BufferedReader(new InputStreamReader(is));
            StringBuilder sb = new StringBuilder();
            String line;
            while ((line = br.readLine()) != null) {
                sb.append(line);
            }
            if (sb.length() > 0) {
                //判斷json是否包含list數(shù)組,包含則先遍歷數(shù)組再遍歷對象值
                if (sb.toString().contains("[")){
                    List<Object> objectList = JSONObject.parseObject(sb.toString(), new TypeReference<List<Object>>() {});
                    for(Object objTemp:objectList){
                        Map<String, Object> map = JSONObject.parseObject(JSONObject.parseObject(objTemp.toString()).toJSONString(), new TypeReference<Map<String, Object>>() {});
                        for (Object object : map.values()) {
                            if (object != null) {
                                Matcher m = Pattern.compile(REG_EX).matcher(object.toString());
                                if (m.find()) {
                                    return true;
                                }
                            }
                        }
                    }
                }else{
                    Map<String, Object> map = JSONObject.parseObject(JSONObject.parseObject(sb.toString()).toJSONString(), new TypeReference<Map<String, Object>>() {});
                    for (Object object : map.values()) {
                        if (object != null) {
                            Matcher m = Pattern.compile(REG_EX).matcher(object.toString());
                            if (m.find()) {
                                return true;
                            }
                        }
                    }
                }
            }
        } catch (IOException e) {
            e.printStackTrace();
        }
        return false;
    }
}

5、實現(xiàn)攔截器

package com.xxx;
import org.springframework.lang.Nullable;
import org.springframework.web.multipart.MultipartHttpServletRequest;
import org.springframework.web.multipart.MultipartResolver;
import org.springframework.web.multipart.commons.CommonsMultipartResolver;
import org.springframework.web.servlet.HandlerInterceptor;
import org.springframework.web.servlet.ModelAndView;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
/**
 * 特殊字符過濾
 * @author lsh
 * @version 1.0
 * @date 2022/4/1 16:25
 */
public class SpecialCharInterceptor implements HandlerInterceptor {
    @Override
    public boolean preHandle(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse, Object o) throws Exception {
        if("GET".equals(httpServletRequest.getMethod())){
            if(UrlFilter.checkSpecials(httpServletRequest.getQueryString())){
                throw new Exception("url中包含特殊字符");
            }
        }else{
            String contentType = httpServletRequest.getContentType();
            //處理form-data請求類型數(shù)據(jù)值
            if (contentType != null && contentType.contains("multipart/form-data")) {
                MultipartResolver resolver = new CommonsMultipartResolver(httpServletRequest.getSession().getServletContext());
                MultipartHttpServletRequest multipartRequest = resolver.resolveMultipart(httpServletRequest);
                if(UrlFilter.checkSpecials(multipartRequest.getParameterMap())){
                    throw new Exception("請求參數(shù)中包含特殊字符");
                }
            }
            else{
                if(UrlFilter.checkSpecials(httpServletRequest)){
                    throw new Exception("請求的數(shù)據(jù)中包含特殊字符 ");
                }
            }
        }
        return true;
    }
    @Override
    public void postHandle(HttpServletRequest request, HttpServletResponse response, Object handler, @Nullable ModelAndView modelAndView) throws Exception {
    }
    @Override
    public void afterCompletion(HttpServletRequest httpServletRequest, HttpServletResponse httpServletResponse, Object o, Exception e) throws Exception {
    }
}

到此這篇關(guān)于springboot項目攔截前端請求中的特殊字符串的文章就介紹到這了,更多相關(guān)springboot攔截特殊字符串內(nèi)容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!

相關(guān)文章

  • Spring Data JPA分頁復(fù)合查詢原理解析

    Spring Data JPA分頁復(fù)合查詢原理解析

    這篇文章主要介紹了Spring Data JPA分頁復(fù)合查詢原理解析,文中通過示例代碼介紹的非常詳細(xì),對大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價值,需要的朋友可以參考下
    2019-11-11
  • 如何從eureka獲取服務(wù)的ip和端口號進(jìn)行Http的調(diào)用

    如何從eureka獲取服務(wù)的ip和端口號進(jìn)行Http的調(diào)用

    這篇文章主要介紹了如何從eureka獲取服務(wù)的ip和端口號進(jìn)行Http的調(diào)用,具有很好的參考價值,希望對大家有所幫助。如有錯誤或未考慮完全的地方,望不吝賜教
    2022-03-03
  • 一文教你利用Stream?API批量Mock數(shù)據(jù)的方法

    一文教你利用Stream?API批量Mock數(shù)據(jù)的方法

    在日常開發(fā)的過程中我們經(jīng)常會遇到需要mock一些數(shù)據(jù)的場景,比如說?mock?一些接口的返回或者說?mock?一些測試消息用于隊列生產(chǎn)者發(fā)送消息。本文將教你如何通過?Stream?API?批量?Mock?數(shù)據(jù),需要的可以參考一下
    2022-09-09
  • 詳解SpringBoot如何實現(xiàn)多環(huán)境配置

    詳解SpringBoot如何實現(xiàn)多環(huán)境配置

    在實際的軟件開發(fā)過程中,一個應(yīng)用程序通常會有多個環(huán)境,pring?Boot?提供了一個非常靈活和強(qiáng)大的方式來管理這些環(huán)境配置,下面就跟隨小編一起學(xué)習(xí)一下吧
    2023-07-07
  • java微信公眾號開發(fā)案例

    java微信公眾號開發(fā)案例

    這篇文章主要為大家詳細(xì)介紹了java微信公眾號開發(fā)案例,如何接入公眾號,訂閱號怎么樣接收消息,具有一定的參考價值,感興趣的小伙伴們可以參考一下
    2016-11-11
  • java統(tǒng)計漢字字?jǐn)?shù)的方法示例

    java統(tǒng)計漢字字?jǐn)?shù)的方法示例

    這篇文章主要介紹了java統(tǒng)計漢字字?jǐn)?shù)的方法,結(jié)合實例形式分析了java正則判定、字符串遍歷及統(tǒng)計相關(guān)操作技巧,需要的朋友可以參考下
    2017-05-05
  • java 查找list中重復(fù)數(shù)據(jù)實例詳解

    java 查找list中重復(fù)數(shù)據(jù)實例詳解

    這篇文章主要介紹了java 查找list中重復(fù)數(shù)據(jù)實例詳解的相關(guān)資料,需要的朋友可以參考下
    2017-01-01
  • java實現(xiàn)通過綁定郵箱找回密碼功能

    java實現(xiàn)通過綁定郵箱找回密碼功能

    這篇文章主要為大家詳細(xì)介紹了java實現(xiàn)通過綁定郵箱找回密碼功能,具有一定的參考價值,感興趣的小伙伴們可以參考一下
    2019-02-02
  • SpringCloud Config連接git與數(shù)據(jù)庫流程分析講解

    SpringCloud Config連接git與數(shù)據(jù)庫流程分析講解

    springcloud config是一個解決分布式系統(tǒng)的配置管理方案。它包含了 client和server兩個部分,server端提供配置文件的存儲、以接口的形式將配置文件的內(nèi)容提供出去,client端通過接口獲取數(shù)據(jù)、并依據(jù)此數(shù)據(jù)初始化自己的應(yīng)用
    2022-12-12
  • Reactor定制一個生產(chǎn)的WebClient實現(xiàn)示例

    Reactor定制一個生產(chǎn)的WebClient實現(xiàn)示例

    這篇文章主要為大家介紹了Reactor定制一個生產(chǎn)的WebClient實現(xiàn)示例解析,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪
    2023-08-08

最新評論