본문 바로가기
백엔드/Spring(Boot)

스프링 @ExceptionResolver 예외처리(API)

by 김어찐 2021. 10. 3.
728x90

API 컨트롤러

produces = MediaType.APPLICATION_JSON_VALUE

요청이 json인지 체크

    @RequestMapping(value = "/error-page/500", produces = MediaType.APPLICATION_JSON_VALUE)
    public ResponseEntity<Map<String, Object>> errorPage500Api(HttpServletRequest request, HttpServletResponse response) {
        log.info("API errorPage 500");
        Map<String, Object> result = new HashMap<>();
        Exception ex = (Exception) request.getAttribute(ERROR_EXCEPTION);
        result.put("status", request.getAttribute(ERROR_STATUS_CODE));
        result.put("message", ex.getMessage());

        Integer statusCode = (Integer) request.getAttribute(RequestDispatcher.ERROR_STATUS_CODE);
        return new ResponseEntity<>(result, HttpStatus.valueOf(statusCode));
    }

postman을 통한 요청 결과

 

스프링이 제공하는 예외처리

    @GetMapping("/api/response-status-ex1")
    public String responseStatusEx1() {
    	// 사용자 정의 Exception
        throw new BadRequestException();
    }

    @GetMapping("/api/response-status-ex2")
    public String responseStatusEx2(){
    	// 메세지를 사용해 에러 전송가능(error.bad)
        throw new ResponseStatusException(HttpStatus.NOT_FOUND, "error.bad", new IllegalAccessException());
    }

 

사용자 정의 Exception (reason에 메시지 사용가능(error.bad)

 

@ExceptionHandler

컨트롤러(@RestControllerAdvice)에서 예외처리 가능

실무에서는 이렇게 사용

package hello.exception.exhandler.advice;

import hello.exception.exception.UserException;
import hello.exception.exhandler.ErrorResult;
import lombok.extern.slf4j.Slf4j;
import org.springframework.http.HttpStatus;
import org.springframework.http.ResponseEntity;
import org.springframework.web.bind.annotation.ExceptionHandler;
import org.springframework.web.bind.annotation.ResponseStatus;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.bind.annotation.RestControllerAdvice;

@Slf4j
//설정하지 않으면 글로벌 예외처리
//패키지도 설정 가능(하위 패키지 포함)
//@RestControllerAdvice(annotations = RestController.class)
@RestControllerAdvice(basePackages = "hello.exception.api")
public class ExControllerAdvice {

    //ResponseStatus 생략하면 200 코드로 전송
    @ResponseStatus(HttpStatus.BAD_REQUEST)
    @ExceptionHandler(IllegalArgumentException.class)
    public ErrorResult illegalExHandler(IllegalArgumentException e) {
        log.error("[exceptionHandler] ex", e);
        //ErrorResult는 내가 만들어준 클래스 객체
        return new ErrorResult("BAD", e.getMessage());
    }

    @ExceptionHandler
    public ResponseEntity<ErrorResult> userExHandler(UserException e) {
        log.error("[exceptionHandler] ex", e);
        ErrorResult errorResult = new ErrorResult("USER_EX", e.getMessage());
        return new ResponseEntity<>(errorResult, HttpStatus.BAD_REQUEST);
    }

    @ResponseStatus(HttpStatus.INTERNAL_SERVER_ERROR)
    @ExceptionHandler
    public ErrorResult exHandler(Exception e) {
        log.error("[exceptionHandler] ex", e);
        return new ErrorResult("EX", "내부 오류");
    }
}
728x90