[MVC2] 9. API異常処理


[前の位置]


異常が発生するとerrorで再要求されます.Spring BootのBasicErrorControllerを/errorにマッピングし、ステータスコードに一致するエラーページビューを検索してレンダリングします.
サーバリターンビューではなくBodyデータを含むAPI通信では、エラーページビューをレンダリングするのではなく、エラーページビューを個別に処理する必要があります.API通信の例外処理の理解

[BasicErrorController利用]


BasicErrorControllerは、要求されたAcceptヘッダがtext/htmlの場合、ユーザにエラーページビューをレンダリングさせ、そうでなければHTTP BodyのJSONデータを返す.このとき、BasicErrorControllerは、ビューに渡されたデータタイムスタンプ、ステータス、エラーなどのJSONを返します.

すなわち,BasicErrorControllerはAPI異常処理も可能であるが,細かい処理ができないため,主にエラーページを返すために用いられる.

[ ExceptionResolver ]


ExceptionResolverは



ExceptionResolverとは、スプリングでコントローラの異常をキャプチャし、通常のフローに変更することです.元のコントローラから異常が投げ出されるとWASに遡り、/errorで再要求されます.ただし、ExceptionResolverを使用すると、コントローラの異常はExceptionResolverによって処理され、ModelAndViewに戻って通常のストリームに変更されます.これ以上要求しない.ExceptionResolverではインタフェースのPostHandleは呼び出されません.

ExceptionResolverの使用


HandlerExceptionResoverlerインタフェースを実装し、ResolveExceptionメソッドを上書きします.例外が発生した場合は、このメソッドが実行されます.
public class MyHandlerExceptionResolve implements HandlerExceptionResolver {
	@Override
    public ModelAndView resolveException(HttpServlerRequest request,
    	HttpServlerResponse response, Object handler, Exception ex) {
    	try {
        	if (ex instance of RuntimeException) {
            	// response.sendError로 에러코드 변경
                // 빈 ModelAndView 반환시 뷰 렌더링 X 정상흐름으로 리턴됨
                // return new ModelAndView 에 데이터를 채워서 뷰 렌더링 수행
                // response.getWriter() 로 JSON 응답 수행
            }
        }
    }

}
応答します.sendErrorを使用してエラーコードを変更したり、通常のストリームを使用してビューをレンダリングしたり、JSON応答を実行したりすることもできます.すなわち、異常が発生した場合には必ず実行しなければならないので、必要な処理を行うことができる.
生成されたExceptionResolverは、WebMvnコンフィギュレータのクラスを実装するextendHandlerExceptionResolverメソッドにIntercepterのように登録する必要があります.
@Overried
public void excetndHandlerExceptionResolvers(List<HandlerExceptionResolver> resolvers) {
	resolvers.add(new MyHandlerExceptionResolver());
}

スプリングを提供するExceptionResolver


ExceptionResolverを使用すると、WASに異常をアップロードでき、再要求することなく中間で異常を処理でき、通常のプロセスを実現できます.しかし、実現するのは面倒だ.便宜上、Spring Bootに付属しているExceptionResolverについて優先順位をつけてみましょう.
  • ExceptionHandlerExceptionResolver
    @ExceptionHandlerのExceptionResolver.API例外処理では、この機能が使用されることが多い.
  • ResponseStatusExceptionResolver
    エラーに対してHTTPステータスコードを指定します.
  • DefaultHandlerExceptionResolver
    スプリング内部の基本例外を処理します.
  • [ ResponseStatusExceptionResolver ]


    ResponseStatusExceptionResolverは応答を表します.sendErrorを呼び出してステータスコードを変更することで再要求を実行します.@ResponseStatusとResponseStateExceptionの2つの例外を処理します.

    @ResponseStatus

    @ResponseStatus(code = HttpStatus.BAD_REQUEST, reason="잘못된 요청")
    public class BadRequestException extends RuntimeException {
    }
    
    public String responseStatusEx() {
    		throw new ResponseStatusException(HttpStatus.NOT_FOUND, "error.bad", new RuntimeException());
    }
    前述したように、@ResponseStatusの例外またはResponseStatusExceptionが追加された場合、ResponseStatusExceptionResolverはそれをキャプチャします.次にsendErrorを使用してステータスコードを変更し、/errorで再要求を実行します.

    [ DefaultHandlerExceptionResolver ]


    DefaultHandlerExceptionResolverはスプリング内部に発生した異常を処理します.たとえば、モデルのプロパティ・オブジェクトにバインドされている場合、タイプが一致しない場合、タイプMissmatchExceptionが発生し、DefaultHandlerExceptionResolverはこの例外を処理して応答します.sendErrorを使用してステータスコードを400に変更し、再要求を実行します.

    [ @ExceptionHandler ]


    ResponseStatusExceptionResolverはResponseStatus異常を処理し、DefaultHandelExceptionResolverはスプリング内部異常を処理します.では、他の例外は誰が処理しますか?
    Springは@ExceptionHandler宣言を提供します.パラメータに異常が発生した場合、適切な宣言を追加する方法はExceptionResolverとして使用されます.

    @ExceptionHandlerの使用

    @ExceptionHandler
    public ReponseEntity<ErrorData> userExHandle(UserException e) {
    		ErrorData errorData = new ErrorData("User-ex", e.getMessage());
            return new ResponseEntity<>(errorData, HttpStatus.BAD_REQUEST);
    }
    コントローラ内部に@ExceptionHandlerを追加し、UserExceptionをパラメータとするメソッドを作成します.UserExceptionが発生した場合、ExceptionHandlerExceptionResolverはこのメソッドをExceptionResolverとして使用します.上からResponseEntityに戻り、エラー結果に応答するためにメッセージ変換器がJSONに変換されます.
    @ExceptionHandlerは、存在するコントローラクラス内部の異常のみをキャプチャして処理します.

    @ControllerAdvice


    @ExceptionHandlerは定義クラス内部で発生した例外のみを処理します.これにより,通常処理ハンドルと異常処理ハンドルが混在する.したがって、クラスに@Controller Advisorを追加して、ExceptionHandlerを個別に持つことができます.@ControllerAdviceでは、コントローラ範囲を設定して例外処理を実行できます.そうしないと、すべてのコントローラに適用されます.@RestController Advisorも存在します.

    n/a.結論


    エラーページを返すには、BasicErrorControllerを使用して開発者がビューを作成するだけです.ただし、詳細に返すAPIエラーはExceptionResolverを使用します.ExceptionResolverは、コントローラに異常が発生した場合にキャプチャし、正常なストリームにします.API例外処理@RestControllerAddviceクラスで@ExceptionHandlerを使用し、各例外は処理プロセスを宣言します.