์คํ๋ง์ ๋ค์ํ ๊ธฐ๋ฅ2(Filter, Interceptor)
Interceptor
๐๐ค๐ฆ
Interceptor ๋ Filter ์ ๋งค์ฐ ์ ์ฌํ ํํ๋ก ์กด์ฌ ํ์ง๋ง, ์ฐจ์ด์ ์ Spring Context์ ๋ฑ๋ก ๋๋ค.
AOP์ ์ ์ฌํ ๊ธฐ๋ฅ์ ์ ๊ณต ํ ์ ์์ผ๋ฉฐ, ์ฃผ๋ก ์ธ์ฆ๋จ๊ณ๋ฅผ ์ฒ๋ฆฌํ๊ฑฐ๋, Logging๋ฅผ ํ๋ ๋ฐ์ ์ฌ์ฉํ๋ค.
์ด๋ฅผ ์ /ํ ์ฒ๋ฆฌ ํจ์ผ๋ก์จ, Service business logic ๊ณผ ๋ถ๋ฆฌ ์ํจ๋ค.
๋ฐฑ๋ฌธ์ด๋ถ์ฌ์ผํ
์ธ์ฆ๊ด๋ฆฌํ๋ ์ธํฐ์ ํฐ ๋ง๋ค์ด๋ณด์
session์ด๋ ์ฟ ํค๋ฅผ ์ฌ์ฉํด์ผํ์ง๋ง... ์ธํฐ์ ํฐ ์ค์ต์ด๊ธฐ ๋๋ฌธ์ ํ๋๊ฐ๋ฐ์์ ํ์ธ
@Auth
@RestController
@RequestMapping("/api/private")
public class PrivateController {
@GetMapping("/hello")
public String hello() {
return "private hello";
}
}
@RestController
@RequestMapping("/api/public")
public class PublicController {
@GetMapping("/hello")
public String hello() {
return "public hello";
}
}
Private์ปจํธ๋กค๋ฌ์ Public ์ปจํธ๋กค๋ฌ๋ฅผ ๋ง๋ค๊ณ Private์๋ @Auth๋ฅผ ๋ถ์ฌ์ค๋ค.(์ธ์ฆ์ ํต๊ณผํด์ผ ์ปจํธ๋กค๋ฌ์ ์ ๊ทผ๊ฐ๋ฅํ๊ฒ ํ ๊บผ๋ค.)
@Documented
@Retention(RetentionPolicy.RUNTIME)
@Target({ElementType.TYPE, ElementType.METHOD})
public @interface Auth {
}
๐ฆ @Auth ์ด๋ ธํ ์ด์ ๋ง๋ค์ด์ฃผ๊ณ
@Slf4j
@Component
public class AuthInterceptor implements HandlerInterceptor {
@Override
public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
String url = request.getRequestURI();
log.info("request url : {}", url);
return false;
}
private boolean checkAnnotation(Object handler, Class clazz) {
// resource javascript, html
if (handler instanceof ResourceHttpRequestHandler) {
return true;
}
//anntation check
HandlerMethod handlerMethod = (HandlerMethod) handler;
if (null != handlerMethod.getMethodAnnotation(clazz) || null != handlerMethod.getBeanType().getAnnotation(clazz)) {
// Auth anntation ์ด ์์๋๋ true
return true;
}
return false;
}
}
๐ฆ AuthInterceptor ํด๋์ค์ ์กฐ๊ฑด๋ค์ ๋ฌ์์ค๋ค.
@Configuration
@RequiredArgsConstructor //fianl๋ก ์ ์ธํ ๊ฐ์ฒด๋ฅผ ์์ฑ์์ ์ฃผ์
๋ฐ์์ ์๋๋ก ํ๋ค.
public class MvcConfig implements WebMvcConfigurer {
private final AuthInterceptor authInterceptor;
@Override
public void addInterceptors(InterceptorRegistry registry) {
registry.addInterceptor(authInterceptor);
}
}
๐ฆ ์ฌ๊ธฐ์ ์ฃผ์ํ ์ ์ฌ๊ธฐ์ ์์ฑ์ ์ฃผ์
ํ ๋ ์ด๋๊น์ง ๋ @Autowierd๋ฅผ ์ฌ์ฉํ๋ค.
์ด๋ ๊ฒ ๋ง์ด๋ค.
ํ์ง๋ง ์ํ์ฐธ์กฐ๊ฐ ์ผ์ด๋ ์ ์๊ธฐ ๋๋ฌธ์ @RequiredArgsConstructor ๋ฅผ ์ด๋ค.
@RequiredArgsConstructor๋ final๋ก ์ ์ธ๋ ๊ฐ์ฒด๋ฅผ ์์ฑํด์ ์ฃผ์
๋ฐ์์ ์๋๋ก ํ๋ ์ด๋
ธํ
์ด์
์ด๋ค.!!!!! ๊ฟํ์ด๋ค.!!!
๐ฆ ๊ทธ๋ผ ํธ์ถํ๋ฒํด๋ณด์.
๐ฆ privateController๋ก ํธ์ถํ๋ฉด ์ปจํธ๋กค๋ฌ๊น์ง ๋ชป์จ๋ค. AuthInterceptor์์ ๋ง์๋ฒ๋ฆฌ๊ธฐ ๋๋ฌธ์ด๋ค.
๐ฆ ์์ด์ ๊ทธ๋ผ ๊ถํ์ฒดํฌํ๋ ์์๋ฅผ ์ง๋ณด์. ๐ค์ด๋ป๊ฒ?ํ ๊น?๐ค
@Override
public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception {
URI uri = UriComponentsBuilder.fromUriString(request.getRequestURI())
.query(request.getQueryString())
.build()
.toUri();
// ์๋๋ Sessionํ์ธํ๊ฑฐ๋ ์ฟ ํคํ์ธํ๋ค!!!!!
String url = request.getRequestURI();
log.info("request url : {}", url);
boolean hasAnnotation = checkAnnotation(handler, Auth.class);
log.info("has annotation : {}", hasAnnotation); // Auth์ด๋
ธํ
์ด์
์ด ๋ฌ๋ ค์๋??? ํ์ธํ๊ธฐ.
// ๋์ ์๋ฒ๋ ๋ชจ๋ public ์ผ๋ก ๋์์ ํ๋๋ฐ
// ๋จ! Auth ๊ถํ์ ๊ฐ์ง ์์ฒญ์ ๋ํด์๋ ์ธ์
,์ฟ ํค ๋ฑ๋ฑ์ ํ์ธํ๋ค!!!!!
if(hasAnnotation){
//๊ถํ์ฒดํฌ
String query = uri.getQuery();
if(query.equals("name=steve")){
return true; // ์ด๋ฆ์ด ์คํฐ๋ธ์ผ๋๋ง ํต๊ณผํ๋ค.
}
}
return false;
}
๐ค๐ค ๊ทธ๋ผ ๋ด๊ฐ ์ํ๋ ์ปจํธ๋กค๋ฌ์ ๋ฉ์๋๋ง ์ธํฐ์ ํฐ๊ฐ ๋์ํ๊ฒ ๋ชปํ๋?
@Configuration
@RequiredArgsConstructor //fianl๋ก ์ ์ธํ ๊ฐ์ฒด๋ฅผ ์์ฑ์์ ์ฃผ์
๋ฐ์์ ์๋๋ก ํ๋ค.
public class MvcConfig implements WebMvcConfigurer {
private final AuthInterceptor authInterceptor;
@Override
public void addInterceptors(InterceptorRegistry registry) {
registry.addInterceptor(authInterceptor).addPathPatterns("/api/private/*");//๋ด๊ฐ ๊ฒ์ฌํ๊ณ ์ถ์ ์ฃผ์์ค์
//excludePathPatterns()๋ฅผ ์ฌ์ฉํ์ฌ ํน์ ์ปจํธ๋กค๋ฌ๋ฅผ ๋บ์ ์๋ค.
}
}
๐ฆ MvcConfig์ ์ธํฐ์ ํฐ ํจํด์ ์ ๋ ฅํ์ฌ ํน์ ์ปจ๋๋กค๋ฌ๋ฅผ ๋นผ๊ฑฐ๋ ์ค์ ํ ์ ์๋ค.!!
๐ฆ ๊น๋ํ๊ฒ ์์ธ์ฒ๋ฆฌ๊น์ง ํด์ฃผ์
if(hasAnnotation){
//๊ถํ์ฒดํฌ
String query = uri.getQuery();
if(query.equals("name=steve")){
return true; // ์ด๋ฆ์ด ์คํฐ๋ธ์ผ๋๋ง ํต๊ณผํ๋ค.
}
//๊ถํ์ด ์์ผ๋ฉด?? AuthException๋ก ๋์ ธ์ค๋ค.
throw new AuthException();
}
AuthInterceptor์ ๊ถํ์ฒดํฌ๊ฐ ์คํจํ๋ฉด
AuthExeption์ผ๋ก ๋์ ธ์ฃผ๊ณ
@RestControllerAdvice
public class GlobalExceptionHandler {
@ExceptionHandler(AuthException.class)
public ResponseEntity authException(){
return ResponseEntity.status(HttpStatus.UNAUTHORIZED).build();
}
}
๐ฆ ๊ทธ๊ฑธ GlobalExceptionHandler๊ฐ ์ฒ๋ฆฌํด์ค๋ค.
)
steve๊ฐ ์๋๋ฉด ํธ์ถ์ด ์๋๋ค!! ์ฑ๊ณต!!!