springmvc 過濾問題

很久沒有寫博客了,這兩天遇到一個關於url編碼的問題,作一個記錄 java

需求是這樣的;spring

系統遭受不法人員攻擊,老大系統系統寫一個過濾器,當有安全攻擊的時候,直接經過配置的方式禁止該接口的使用瀏覽器

原本覺得很簡單 ,直接寫了一個定時加載的功能,讀取配置,而後與請求過來的url進行對比便可,用瀏覽器測試都沒有問題,可是通過安全的時候,問題來了,在瀏覽器中會url自動的解析,可是在當在抓起工具中輸入如下地址,仍然能請求道相應的請求,安全

/product/./queryChannelProductInfo
/product/123/../queryChannelProductInfo
/product%2fqueryChannelProductInfo服務器

從表面現象能夠看出,服務器底層還有一個層與瀏覽器作了一樣的規則處理 mvc

一開始處理的方式 , 獲取器Dispatcher,經過反射而後獲取器url,而後在進行比較 app

  

 RequestDispatcher dispatcher = arg0.getRequestDispatcher(reqUrl);
                @SuppressWarnings("deprecation")
                Field path = arg0.getRequestDispatcher(URLDecoder.decode(reqUrl)).getClass().getDeclaredFields()[16];
                path.setAccessible(true);
                path.get(dispatcher);
                String dispatcherUrl =(String) path.get(dispatcher);
                if (new AntPathMatcher().match(strUrl,dispatcherUrl)) {
                    logger.warn(reqUrl + "have  no authority for rquest");
                    return;
                }


這種方法解決了./ ../這種方式,可是url編碼的格式仍然能夠繞過 框架


一時分析,框架用的是springmvc 應該是在內容的處理致使的 ,因而開始分析spring mvc 的源碼 async

protected void doDispatch(HttpServletRequest request, HttpServletResponse response) throws Exception {
        HttpServletRequest processedRequest = request;
        HandlerExecutionChain mappedHandler = null;
        boolean multipartRequestParsed = false;
        WebAsyncManager asyncManager = WebAsyncUtils.getAsyncManager(request);

        try {
            try {
                ModelAndView mv = null;
                Exception dispatchException = null;

                try {
                    processedRequest = this.checkMultipart(request);
                    multipartRequestParsed = processedRequest != request;
                    mappedHandler = this.getHandler(processedRequest, false);
                    if (mappedHandler == null || mappedHandler.getHandler() == null) {
                        this.noHandlerFound(processedRequest, response);
                        return;
                    }
     ......
}

 

@Deprecated
    protected HandlerExecutionChain getHandler(HttpServletRequest request, boolean cache) throws Exception {
        return this.getHandler(request);
    }

    protected HandlerExecutionChain getHandler(HttpServletRequest request) throws Exception {
        Iterator i$ = this.handlerMappings.iterator();

        HandlerExecutionChain handler;
        do {
            if (!i$.hasNext()) {
                return null;
            }

            HandlerMapping hm = (HandlerMapping)i$.next();
            if (this.logger.isTraceEnabled()) {
                this.logger.trace("Testing handler map [" + hm + "] in DispatcherServlet with name '" + this.getServletName() + "'");
            }

            handler = hm.getHandler(request);
        } while(handler == null);

        return handler;
    }

 

public final HandlerExecutionChain getHandler(HttpServletRequest request) throws Exception {
		Object handler = getHandlerInternal(request);
		if (handler == null) {
			handler = getDefaultHandler();
		}
		if (handler == null) {
			return null;
		}

		if (handler instanceof String) {
			String handlerName = (String) handler;
			handler = getApplicationContext().getBean(handlerName);
		}
		return getHandlerExecutionChain(handler, request);
	}
protected HandlerExecutionChain getHandlerExecutionChain(Object handler, HttpServletRequest request) {
		HandlerExecutionChain chain = new HandlerExecutionChain(handler);

		chain.addInterceptors(getAdaptedInterceptors());

		String lookupPath = this.urlPathHelper.getLookupPathForRequest(request);
		for (MappedInterceptor mappedInterceptor : this.mappedInterceptors) {
			if (mappedInterceptor.matches(lookupPath, this.pathMatcher)) {
				chain.addInterceptor(mappedInterceptor.getInterceptor());
			}
		}

		return chain;
	}
相關文章
相關標籤/搜索