[Spring] 필터(filter)와 인터셉터(interceptor)의 차이

2022. 6. 7. 15:54 Spring Framework/Spring 입문 - 개념 및 핵심

Controller에 요청이 들어오기전에 무엇인가를 수행한다는 기능만 보면 interceptor와 filter는 무척 비슷해 보인다. 

 

(전, 후처리기 역할을 수행한다.)

위의 사진을 보면 차이점을 쉽게 알 수 있는데, 둘다 컨트롤러 전에 작업을 처리하는 용도로 사용되지만 호출되는 시점이 다르다.

필터(Filter)는 dispatcherServlet으로 요청이 가기전에 실행되고

인터셉터(Interceptor)는 Controller로 요청이 가기전에 실행이된다.

 

Filter

  • DispatcherServlet 앞단에서 정보 처리
  • J2EE 표준스펙에 정의되어 있는 기능
Interceptor
  • DispatcherServlet에서 Handler(Controller)로 가기전에 정보 처리
  • SpringFramework에서 자체적으로 제공하는 기능

 

따라서 주로 전역적으로 무엇인가를 처리해야하는 로직은 필터로 구현을 하고(인코딩 및 보안관련 처리) 디테일한 처리는 인터셉터로 구현 한다.(인증, 권한)

 

실제로 위 그림대로 실행이되는지 테스트를 해보자

 

Interceptor 설정

interceptor 는 Spring Framework에서 자체적으로 제공하는 기능이다. 따라서 dispatcher servlet이 읽는 설정 파일에 interceptor를 설정해야한다.

<!-- interceptor -->
<mvc:interceptors>
       <mvc:interceptor>
              <mvc:mapping path="/*"/>
              <beans:bean class="com.sunghyun.test.interceptor.TestInterceptor"></beans:bean>
       </mvc:interceptor>
</mvc:interceptors>

- servlet-context.xml 또는 dispatcher-servlet.xml에 interceptor를 등록

 

Interceptor 생성

HandlerInterceptorAdapter를 상속받아서 custom한 interceptor를 작성한다.

package com.sunghyun.test.interceptor;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import org.springframework.web.servlet.ModelAndView;
import org.springframework.web.servlet.handler.HandlerInterceptorAdapter;

public class TestInterceptor extends HandlerInterceptorAdapter{
    
    @Override
    public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler){
        System.out.println("===== before(interceptor) =====");
        return true;
    }
    
    @Override
    public void postHandle(
            HttpServletRequest request, HttpServletResponse response, Object handler, ModelAndView modelAndView)
            throws Exception {
        System.out.println("===== after(interceptor) =====");
    }

    @Override
    public void afterCompletion(
            HttpServletRequest request, HttpServletResponse response, Object handler, Exception ex)
            throws Exception {
        System.out.println("===== afterCompletion =====");
    }
}​
 
각 method의 실행시점
  • preHandle() : 컨트롤러 들어가기 전에 실행
  • postHandle() : 컨트롤러에 들어갔다가 나온 후 뷰로 보내지기 전에 실행
  • afterCompletion() : 뷰까지 끝고난 후 실행

 

Filter 설정

filter는 J2EE 표준에 정의되어 있는 기술으로, web.xml에 설정한다.

<!-- filter -->
<filter>
       <filter-name>TestFilter</filter-name>
       <filter-class>com.sunghyun.test.filter.TestFilter</filter-class>
</filter>
<filter-mapping>
       <filter-name>TestFilter</filter-name>
       <filter-class>/*</filter-class>
</filter-mapping>

 

Filter 생성

Filter클래스를 implements하여 작성한다.

 
package com.sunghyun.test.filter;

import java.io.IOException;

import javax.servlet.Filter;
import javax.servlet.FilterChain;
import javax.servlet.FilterConfig;
import javax.servlet.ServletException;
import javax.servlet.ServletRequest;
import javax.servlet.ServletResponse;

public class TestFilter implements Filter{

    @Override
    public void destroy() {
        System.out.println("===== filter destory =====");
    }

    @Override
    public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain)
            throws IOException, ServletException {
        System.out.println("===== before(filter) =====");
        
        chain.doFilter(request, response);
        
        System.out.println("===== after(filter) =====");
    }

    @Override
    public void init(FilterConfig config) throws ServletException {
        System.out.println("===== init filter =====");
    }

}

각 method의 실행시점

  • init() : 필터 인스턴스 초기화시점에 실행
  • doFilter() : 전/후 처리
  • destory() : 필터 인스턴스 종료시 실행
  •  

테스트 결과

(Sts를 활용하여 생성하면 자동으로 생성되는 HomeController를 호출해보았음)

위 그림처럼 결과가 나오는 것을 확인할 수 있다. filter(before) -> interceptor(before) -> controller (Log info) -> interceptor(after) -> view 출력(home.jsp 가 없다고 나옴) -> afterCompletion -> after(filter)

 

출처: https://cornswrold.tistory.com/56?category=755359 [평범한개발자노트:티스토리]