[ 1. 인터셉터란? ]
인터셉터란 특정 URL 요청시 Controller로 가는 요청을 가로채는 역활을 한다.
▶ 즉 컨트롤러에 가는 요청을 인터셉터가 가로채서인터셉터가 검증하는 것 이다.
예를들어 URL이 /login이라고 한다면 이 /login URL을 인터셉터에 지정해놓는다면
이 경로가 들어올 때 "마다" 인터셉터가 가로채서 검증하는 것 이다.
[ 2.사용 이유? ]
개발자는 특정 Controller가 호출되기전이나 후에 추가적인 작업을 원할 때 사용되는 것이 인터셉트 이다.
추가적인 작업이란 로그인 처리,로그인 체크 등이 있다.
인터셉트를 사용하는 이유 중 로그인 처리나 로그인 체크 부분이 많은 비중을 차지한다.
우리가 어떤 웹사이트를 갔는데 한 30분 정도 지나고 다시 웹사이트를 쓸려고 하면 갑자기 로그인 화면으로
튕기는 경험을 한 경험이 있을 것 이다. 이것이 바로 인터셉트에 의한 원리라고 생각하면 쉽다.
[ 2. Interceptor와 Filter의 차이?? ]
인터셉트를 배운다면 인터셉트와 스프링 필터 부분이 같으면서도 다른거 같아서 햇갈릴 때가 있다.
단도직입적으로 말하자면 기능은 같다.
하지만 사용방법은 조금 다른데
필터의 경우는 같은 웹 어플리케이션 내에서만 접근이 가능한 방면
인터셉트는 스프링이 관리하기 때문에 스프링내에서 모든 객체에 접근이 가능하다.
그래서 인터셉트의 경우는 로그인 처리 , 필터의 경우 주로 한글처리에 이용이 된다.
즉 인터셉트는 스프링에서 지원하는 것 이고 필터는 HttpServlet에서 지원하는 기능이다.
[ 인터셉트의 동작 방식 ]
Http 요청 -> WAS -> 필터 -> 서블릿 -> 스프링 인터셉터 -> 컨트롤러
이렇게 인터셉터는 동작하는데 만약 스프링 인터셉터에서 어떠한 조건을 건다면
그 조건을 확인한 후 컨트롤러를 호출 시킨다. 그렇기에 로그인 같은 경우 적절하지 않은
사용자라 한다면 스프링 인터셉터에서 컨트롤러를 호출 하지 않는다.
[ 인터셉트의 사용 방법 ]
일단 인터셉트를 쓰게 되면 3가지 메서드를 볼 수 있는데 각자의 특징을 알아보도록 하자.
1) preHandle()
▶ 컨트롤러가 호출되기전에 실행된다.
▶ 컨트롤러가 실행 이전에 해야할 작업이 있는 경우 preHandle()를 사용하면 효과적이다.
▶ 리턴값이 Boolean임으로 리턴이 true일 경우 preHandle() 실행 후 핸들러에 접근한다.
핸들러 = 컨트롤러라고 생각하면 쉽다. false경우 작업을 중단하기 때문에 컨트롤러와
인터셉트가 실행되지 않는다.
▶ 쉽게 생각하자면 PreHandle는 인터셉터가 url요청을 가로채면 제일 먼저 실행되는
부분이다. 이 메서드 부분에서 false를 선언한다면 밑에 있는 메서드는 실행되지 않음.
▶PreHandle부분이 머리 부분이고 다른 메서드들을 몸통 다리 부분이라고 생각하면 쉽다.
머리부분에서 명령을 전달하기 때문에 머리 부분이 false라고 한다면 밑에 몸통, 다리 부분은
행동하지 않는 것.
2) postHandle()
▶ 핸들러가 실행은 되었지만 아직 View가 생성되기 이전에 호출된다.
즉 컨트롤러에 들어오고 View가 생성되기 전에 호출된다.
▶ preHandle() 에서 리턴값이 fasle인경우 실행되지않음.
▶ ModelAndView 타입의 정보를 인자로 받는다.
따라서 Controller에서 View 정보를 전달하기 위해 작업한 Model 객체의 정보를
참조하거나 조작할 수 있다.
▶ 비동기 요청처리 시에는 처리되지 않는다.
3) afterCompletion()
▶ 모든 View에서 최종 결과를 생성하는 일을 포함한 모든 작업이 완료된 후 실행된다.
즉 모든 작업이 종료된 후 실행되는 메서드이다.
▶ 요청 처리 중 사용한 리소스를 반환해주기 적당한 메서드이다.
▶ PreHandle에서 리턴 값이 false인 경우 실행되지 않음.
▶ afterCompletion은 예외를 받는 인자가 있기 때문에 오류 검출에서도 많은 사용을 한다.
[ 인터셉트의 사용과 구현 ]
일단 스프링의 인터셉터를 사용하기 위해선
implements HandlerInterceptor
를 구현받아야한다.
구현을 받는다면
이렇게 세 가지의 메서드가 만들어진다. 이 메서드가 어떤 기능을 하는지는 위에 적어놨기 때문에 생략한다.
나의 경우는 로그인 체크 사용할 것 이기 때문에 나머지 두 메서드들은 빼고 preHandle만 사용 할 것 이다.
그렇게 내가 필요한 로직들을 적었다. 필자의 경우는 로그인 체크를 할 것 이기 때문에
PreHanlde만 오버라이딩해서 작성했는데 이렇게 된다면 웹 사이트를 쓰는
사용자는 페이지를 하나하나 들어갈 때 마다
인터셉트의 체크를 받게된다. 거기서 세션이 없다면 바로 로그인 화면으로 튕기게 로직을 짯다.
이렇게 다 짜고 끝이 아니다.
기본적으로 인터셉트는 Config에 등록을 해줘야 하는데 등록을 안하면 인터셉트가 적용이 안된다.
이렇게 WebConfig란 클래스를 만들어서 어노테이션 @Configuration을 붙여서 사용해야 한다.
저 어노테이션을 붙이지 않으면 내가 등록한 설정정보들이 스프링이 인식을 못해서 인터셉트가 적용이 안된다.
그 후에는
implements WebMvcConfigurer
WebConfig 클래스에 WebMvcConfigurer라는 인터페이스를 구현받아야 한다.
구현을 받는다면 이렇게 많은 메서드들이 있다. 기본적으로 이 메서드들은 Default 메서드 이기 때문에
직접 다 구현할 필요는 없고 여기에서 addInterceptor라는 메서드가 있을 것 이다.
이 부분을 구현받자.
addInterceptors를 구현받으면 이렇게 생긴 메서드가 있을 것 이다. 여기에서 이제 인터셉트의 설정 정보를 적용 시켜야 한다. 기본적으로 인터셉트는 메서드 체이닝 형태로 사용 할 수 있는데
여기서 주의해야 할 점은
1.addIntercepotr에 내가 만든(HandlerInterceptor)를 구현받은 클래스를 넣으면 된다.
2. 두번째로 여기에서 어떠한 설정을 넣을 것 인지가 나오는데
order()
순서를 정하는 메서드이다. order() 인자안에 순서를 넣을 수 있는데 order(1)이면
제일 먼저 첫번째로 우선순위를 가지게 만들고 order(2)면 두번째로 우선순위를 가진다.
이 경우에는 인터셉트를 여러 개 사용할때 필요하다.
.addPathPatterns()
addPathPatterns은 인터셉트를 적용할 범위이다.
예를들어 addPathPatterns("/**") 라고 넣는다면 모든 범위에 인터셉트를 적용 할 수 있다.
기본적으로 URL의 경로를 제어하는 메서드이다.
addPathPatterns에 내가 제어하고싶은 컨트롤러가 있다면 그 컨트롤러가 받는 url를 넣는다면
제어할 수 있다.
excludePathPatterns
이 excludePathPatterns은 addPathPaterns() 파라미터안에 들어간 URL주소에서 제외할 영역을 정하는 메서드이다.
예를들어 addPathPaterns("/**")을 넣으면 모든 URL에 경로를 인터셉트를 거치게 만들지만
excludePathPatterns("/login","/logout") 을 넣는다면 전체 경로에서 이 경로는 인터셉트 대상에서 제외된다.
또한 excludePathPatterns 사용할 때 주의 할 점이 있는데 인자 값 안에 excludePathPatterns("logout","login")이렇게
/ 를 제외하고 넣으면 작동이 안된다. 그러니까 항상 경로를 적을땐 / <를 넣어서 사용하는걸 잊지말자.
그리고 경로를 설정할 때 가끔 GetMapping에서만 받는 정보들을 넣는 사람이 있다.
만약 로그인 체크를 관리하기 위해서는 GetMapping과 PostMapping에 있는 두개의 경로 "다" 적어야 한다.
만약 GetMapping과 PostMapping가 같은 경로를 받는다면 상관없지만 경로가 다르면 PostMapping은
addPathPatterns에 막혀서 컨트롤러가 실행을 못한다.
사진으로 본다면 이런 느낌이다. 순번은 첫번째로 전 경로에 인터셉트를 적용시키지만 내가 적은 URL 경로는
인터셉트에서 제외해라 라는 뜻이담긴 코드이다.
[ 요약 ]
인터셉트를 먹일 클래스를 만든 후 ->
HandlerIntercepotor를 구현 받는다 ->
WebConfig란 클래스를 만든 후 ->
@Configuration 어노테이션 적용 ->
그 후 WebConfig에 WebMvcConfigurer를 구현받는다
-> 구현받은 후 addInterceptor를 찾는다 ->
찾은 후 내가 인터셉트를 만든 클래스를 넣고 ->
설정정보 들을 적으면 끝.
'[자바]스프링' 카테고리의 다른 글
[Oauth 구현시 액세스 차단됨이 나올 때 관련 문제 해결하기] (0) | 2023.11.23 |
---|---|
[스프링] 스프링 Converter 스프링의 자동변환 정리 (2) | 2023.06.04 |
[스프링] Spring에서 세션이란? 세션의 이해와 원리 그리고 로그인 (0) | 2023.05.31 |
[스프링] 쿠키란? 쿠키의 원리부터 구현까지 (0) | 2023.05.31 |
스프링 querydsl 의존성 추가 스프링 부트 3.0.0이상 gradle 5.0이상 (1) | 2023.05.05 |