Spring Bootでエラーハンドラーを実装する




Spring Bootのエラーハンドラーには種類が多くてどれを使ったらいいか迷ってしまいますが@ControllerAdviseと@ExceptionHandlerで実装したエラーハンドラーは実装量も少なくカスタマイズもしやすいのでいいなと思ったので紹介します。

エラーハンドラーの実装

エラーハンドラーの実装に@ControllerAdviseと@ExceptionHandlerの2つのアノテーションを使います。

クラスの先頭に@ControllerAdviseをつけることで全てのコントローラーに対して処理を割り込ませることができます。

@ExceptionHandlerはメソッドの方につけて引数にキャッチしたいクラスを指定します。このクラスがコントローラー以下でthrowされた時にこのハンドラーでキャッチすることができます。

package com.sample.api.controller_advise


import com.sample.dto.response.BadRequestException
import com.sample.dto.response.ErrorResponse
import org.springframework.http.ResponseEntity
import org.springframework.stereotype.Component
import org.springframework.web.bind.annotation.ControllerAdvice
import org.springframework.web.bind.annotation.ExceptionHandler
import javax.servlet.http.HttpServletRequest

@ControllerAdvice
@Component
class RequestExceptionHandler {

    /**
     * BadRequestExceptionのハンドラー
     */
    @ExceptionHandler(BadRequestException::class)
    fun getException(req: HttpServletRequest, error: BadRequestException): ResponseEntity<ErrorResponse> {
        return ErrorResponse.createResponse(error);
    }
}

ErrorResponseクラス

上記コードの中で使っているErrorReponseについて説明します。これは独自に実装したクラスでクライアントにカスタマイズしたエラーレスポンスを返すためのクラスになります。

Kotlinで書いているのでcompanion objectを使ってstaticメソッドのような振る舞いをするように定義しています。

ResponseEntityにHTTPのステータスコードを設定することができるので用途に分けて400や403などのステータスコードを使用すると汎用性がますかと思います。

package com.mercury.dto.response

import org.springframework.http.HttpStatus
import org.springframework.http.ResponseEntity

class ErrorResponse(var message: String) {

    companion object {
        fun createResponse(e: BadRequestException): ResponseEntity<ErrorResponse> {
            return ResponseEntity<ErrorResponse>(ErrorResponse(e.errorMessage), HttpStatus.FORBIDDEN);
        }
    }
}

BadRequestExceptionクラス

これはエラーメッセージを設定するだけのクラスでExceptionを継承したものとして定義しています。命名がいまいちですがここは適宜変更してください。

package com.mercury.dto.response

class BadRequestException(var errorMessage: String) : Exception() {

    fun BadRequestException(errorMessage: String) {
        this.errorMessage = errorMessage
    }
}

あとはこのクラスをにメッセージを渡したものをthrowするだけでRequestExceptionHandlerクラスのgetExceptionメソッドがキャッチしてクライアントにカスタマイズしたレスポンスを返してくれます。

Springって仕組み化されすぎてて何がどう動いているのかさっぱりなんですが、一度その仕組みを理解するとこうもあっさり実装できるところはいいなと思ったりします。

基本的には自分はあまり好きじゃないですが笑

まとめ

  • @ControllerAdviseと@ExceptionHandlerを使ったエラーハンドラークラスを実装する
  • エラーレスポンスを作るクラスを実装する(ErrorResponse)
  • エラーメッセージを格納するクラスを実装する(BadRequestException)

おすすめ書籍

JPAに関して体系的に学べる良い書籍だと思います。良くあるSpring系書籍ですとJPAは少ししか紹介がありませんが丸々一冊JPAに関してなので詳細な解説がされています。内容はJPAと他のORMとの比較から始まりセットアップ、実装の仕方まで幅広く網羅されています。これからJPAで開発を初めてみようかなと考えている方は一読することをオススメします!

Springの概要からインストール方法、各コア機能(Security, Sessionなど)の解説が体系的にまとめられています。2018年に出版されたばかりなので情報も新しいです。これからSpring Bootでアプリケーション開発をしたい方の最初に読む一冊としておすすめします。対象は初心者だけでなく上級者まで幅広く学べるので是非読んでみてください!

 

The following two tabs change content below.

髙妻智一

2013年CyberAgent新卒入社 スマホゲームを作る子会社に所属し、サーバーサイドのエンジニアを担当。2年目の終わりから新規子会社の立ち上げに参加し、サーバーサイドのエンジニアリーダーとしてサービースのリリースから運用までを担当。 2018年仮想通貨のスマホウォレットを提供するGinco Incにブロックチェーンエンジニアとして入社。






よく読まれている関連記事はこちら



コメントを残す

メールアドレスが公開されることはありません。 が付いている欄は必須項目です