스프링 부트는 현재까지 한 오류페이지 과정을 모두 기본으로 제공된다.
- ErrorPage를 자동으로 등록 ==> /error 라는 경로로 기본 오류페이지가 설정되있다.
- 상태코드와 예외를 설정하지 않을 경우 기본 오류 페이지로 사용된다.
- 서블릿 밖으로 예외 발생 도는 response.sendError() 가 호출시 모든 오류는 /error 를 호출
- BasicErrorController를 자동으로 등록
- ErrorPage에서 등록한 /error를 매핑해서 처리하는 컨트롤러
- 이것 때문에 개발자는 오류페이지 화면만 BasicErrorController 가 제공하는 룰과 우선순위에 따라서 등록해주면 된다.
- 정적 HTML 인 경우 정적 리소스에, 뷰 템플릿을 사용해서 동적 오류화면을 만들 때는 뷰 템플릿 경로에 오류 페이지 파일을 만들어서 넣어주면 된다.
지금까지 만든 WebServerCustomizer에 @Component를 주석처리
- 기본 오류 매커니즘을 사용하게 주석처리를 통해서 빈 등록이 되지않게 해준다.
뷰 선택 우선순위
- 뷰 템플릿
- /resources/templates/error/500.html
- /resources/templates/error/5XX.html
- 정확한 오류 번호 페이지가 아닌 500대 오류인 경우 이 페이지를 보여주게된다.
- 정적 리소스(static, public)
- /resources/static/error/400.html;
- /resources/static/error/404.html;
- /resources/static/error/4XX.html;
- 적용 대상이 없을때 뷰 이름(error)
- /resources/templates/error.html;
뷰 템플릿이 우선순위가 가장 높고, 구체적인 것이 우선순위가 높음.
- 자세한 경우 자세하게 적힌 것이 우선순위다.
- 500에러가 터진경우 500.html 페이지를 보여줌.
- 만약 500에러가 터졌는데 500.html 페이지가 없다면 5XX 페이지를 보여줌.
템플릿에 4xx.html, 404.html,500.html를 만들어주고 테스트 해보면 제대로 작동한다.
- 대신 이 상황에서 400 을 내보내게되면 404 가발생해서 404 페이지가 나옴.
이유
-
컨트롤러가 받을수 없는 URL 작성시 , 스프링은 최종적으로 404 오류를 내보내게 된다. -> 현재 컨트롤러로 400을 만들지 않아서 받을 수 없는 상황
-
@Slf4j
@Controller
public class ServletExController {
@GetMapping("/error-ex")
public void errorEx(){
throw new RuntimeException("예외 발생");
}
@GetMapping("/error-404")
public void error404(HttpServletResponse response) throws IOException{
response.sendError(404,"404 오류");
}
@GetMapping("/error-500")
public void error500(HttpServletResponse response) throws IOException{
response.sendError(500,"500 오류");
}
}
- /error-400 을 보낸다고 해도 컨트롤러에 이걸 받을 수 없다면 결국 404 오류를 내보내게 되어서 404 오류페이지를 보이게된다.
- 페이지가 존재하지 않기 때문에 404 NOT FOUND 발생 -> 만들어둔 404 페이지로 처리된다.
BasicErrorController가 제공하는 기본정보들
* timestamp: Fri Feb 05 00:00:00 KST 2021
* status: 400
* error: Bad Request
* exception: org.springframework.validation.BindException
* trace: 예외 trace
* message: Validation failed for object='data'. Error count: 1
* errors: Errors(BindingResult)
* path: 클라이언트 요청 경로 (`/hello`)
- 이 정보는 굳이 사용자에게 노출할 필요가없다.
- 보안상 문제가 될 수도 있고, 고객이 정보를 읽는다 해도 혼란 생길수 있기 때문에
- 사용자에게는 잘 정돈된 오류 화면과 이해하기 쉬운 오류 메시지를 보여주고 오류는 서버에 로그로 남겨서 로그로 확인해야한다.