Skip to Content
공부백엔드Servlet과 웹 서버5. Filter

Filter

Filter는 웹 컴포넌트가 실행되기 전/후에 요청과 응답을 가로채서 부가적인 기능을 수행하기 위한 웹 컴포넌트다.

Filter와 Servlet의 차이점

  • Filter: 모든 요청에 대한 공통 처리 (횡단 관심사)
  • Servlet: 특정 URL에 대한 비즈니스 로직 처리
  • 실행 순서: WAS → Filter Chain → Servlet → Filter Chain → WAS

Filter가 필요한 이유

  • 인코딩 처리는 모든 요청에 필요 → 각 Servlet에 반복 코드 방지
  • 인증/인가를 중앙에서 통제
  • 요청/응답 로깅을 일괄 처리

Filter의 주요 용도

  • 인증 및 권한 확인: 사용자가 특정 페이지에 접근하기 전에 로그인 여부와 권한 확인
  • 로깅: 어떤 요청이 있었는지, 어떤 응답이 있었는지 추적
  • 보안: 요청을 검사하여 악의적인 코드나 공격 차단 (XSS 공격 등)
  • 인코딩 설정: 모든 요청/응답에 대한 문자 인코딩 일괄 처리
  • CORS 설정: Cross-Origin Resource Sharing 헤더 추가
  • 압축: 응답 데이터 압축 (gzip)

Filter 구현 예시

1. 로깅 필터

모든 요청에 대한 로깅을 수행한다.

LoggingFilter.java
@WebFilter(urlPatterns = {"/*"}) public class LoggingFilter extends HttpFilter implements Filter { public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException { HttpServletRequest hreq = (HttpServletRequest) request; // 1. 요청 정보 로깅 System.out.println(hreq.getRequestURL() + " : " + hreq.getMethod()); // 파라미터 로깅 Map<String, String[]> params = hreq.getParameterMap(); params.forEach((key, values) -> { for (String value : values) { System.out.println("Key: " + key + ", Value: " + value); } }); // 2. 다음 필터 또는 서블릿 호출 chain.doFilter(request, response); } }

2. XSS 공격 방지 필터

크로스 사이트 스크립팅(XSS) 공격을 방지한다.

XssFilter.java
@WebFilter(urlPatterns = {"/*"}) public class XssFilter extends HttpFilter implements Filter { public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException { // XSS 방지를 위한 RequestWrapper 사용 chain.doFilter(new MyXssRequestWrapper((HttpServletRequest) request), response); } // RequestWrapper 클래스 class MyXssRequestWrapper extends HttpServletRequestWrapper { public MyXssRequestWrapper(HttpServletRequest request) { super(request); } @Override public String getParameter(String name) { String value = super.getParameter(name); if (value != null) { // HTML 태그를 안전한 문자로 치환 value = value .replaceAll("<", "&lt;") .replaceAll(">", "&gt;"); } return value; } } }

Filter Chain

Filter는 체인 형태로 연결되어 순서대로 실행된다. 여러 개의 필터가 연쇄적으로 연결되어 순서대로 실행될 수 있으며, 각 Filter는 chain.doFilter()를 호출해야 다음 처리로 넘어간다.

Filter Chain 동작 흐름

Filter 처리 순서

  1. 요청 단계: 클라이언트 → Filter 1 → Filter 2 → Filter 3 → Filter 4 → Servlet
  2. 응답 단계: Servlet → Filter 4 → Filter 3 → Filter 2 → Filter 1 → 클라이언트

각 Filter는 요청/응답을 수정할 수 있으며, 응답은 역방향으로 체인을 통과한다.

Filter 구현 패턴

// Filter의 기본 흐름 public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException { // 1. 전처리 (요청이 Servlet으로 가기 전) // 예: 인코딩 설정, 로깅, 인증 체크 등 // 2. 다음 Filter 또는 Servlet 호출 (필수!) chain.doFilter(request, response); // 3. 후처리 (응답이 클라이언트로 가기 전) // 예: 응답 로깅, 리소스 정리 등 }

Filter와 Interceptor의 차이

Filter (Servlet 스펙)

  • Container 수준에서 동작
  • Servlet이 실행되기 전/후 처리
  • web.xml 또는 @WebFilter로 설정

Interceptor (Spring MVC)

  • Spring MVC 수준에서 동작
  • Handler(Controller) 실행 전/후/완료 시점 처리
  • 더 세밀한 제어 가능

정리

  • Filter: 모든 요청/응답을 가로채서 공통 처리
    • 인증/인가, 로깅, 보안(XSS 방지), 인코딩 등
    • chain.doFilter() 호출 필수
    • 횡단 관심사를 처리하는 핵심 컴포넌트
Last updated on