「労働者が自分の仕事をうまくやりたいなら、まず自分の道具を研ぎ澄まさなければなりません。」 - 孔子、「論語。陸霊公」
表紙 > プログラミング > Spring Boot での例外処理

Spring Boot での例外処理

2024 年 8 月 25 日に公開
ブラウズ:339

Exception Handling in Spring Boot

例外処理は、堅牢でユーザーフレンドリーなアプリケーションを構築する上で重要な部分です。 Spring Boot では、アプリケーションの安定性を確保し、ユーザーに有意義なフィードバックを提供するために、さまざまな方法で例外を処理できます。このガイドでは、カスタム例外、グローバル例外処理、検証エラー、本番環境のベスト プラクティスなど、例外処理のさまざまな戦略について説明します。

1. 例外処理の基本

例外は、プログラムの通常の流れを中断するイベントです。それらは次のように分割できます:

  • チェックされた例外: コンパイル時にチェックされる例外。
  • 未チェックの例外 (実行時例外): 実行時に発生する例外。
  • エラー: OutOfMemoryError.
  • など、アプリケーションで処理すべきではない重大な問題

2. カスタム例外クラス

カスタム例外クラスを作成すると、アプリケーションでの特定のエラー状態の処理に役立ちます。

package com.example.SpringBootRefresher.exception;

public class DepartmentNotFoundException extends RuntimeException {
    public DepartmentNotFoundException(String message) {
        super(message);
    }
}

3. コントローラーでの例外処理

@ExceptionHandler 注釈:
コントローラー クラスで例外を処理するメソッドを定義できます。

package com.example.SpringBootRefresher.controller;

import com.example.SpringBootRefresher.exception.DepartmentNotFoundException;
import org.springframework.http.HttpStatus;
import org.springframework.http.ResponseEntity;
import org.springframework.web.bind.annotation.ExceptionHandler;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RestController;

@RestController
public class DepartmentController {

    @GetMapping("/department")
    public String getDepartment() {
        // Simulate an exception
        throw new DepartmentNotFoundException("Department not found!");
    }

    @ExceptionHandler(DepartmentNotFoundException.class)
    public ResponseEntity handleDepartmentNotFoundException(DepartmentNotFoundException ex) {
        return new ResponseEntity(ex.getMessage(), HttpStatus.NOT_FOUND);
    }
}

4. @ControllerAdvice によるグローバル例外処理

例外をグローバルに処理するには、@ControllerAdvice と集中例外ハンドラーを使用できます。

package com.example.SpringBootRefresher.error;

import com.example.SpringBootRefresher.entity.ErrorMessage;
import com.example.SpringBootRefresher.exception.DepartmentNotFoundException;
import org.springframework.http.HttpStatus;
import org.springframework.http.ResponseEntity;
import org.springframework.web.bind.annotation.ControllerAdvice;
import org.springframework.web.bind.annotation.ExceptionHandler;
import org.springframework.web.bind.annotation.ResponseStatus;
import org.springframework.web.context.request.WebRequest;
import org.springframework.web.servlet.mvc.method.annotation.ResponseEntityExceptionHandler;

@ControllerAdvice
@ResponseStatus
public class CustomResponseEntityExceptionHandler extends ResponseEntityExceptionHandler {

    @ExceptionHandler(DepartmentNotFoundException.class)
    public ResponseEntity handleDepartmentNotFoundException(DepartmentNotFoundException exception, WebRequest request) {
        ErrorMessage message = new ErrorMessage(
                HttpStatus.NOT_FOUND.value(),
                exception.getMessage(),
                request.getDescription(false)
        );

        return ResponseEntity.status(HttpStatus.NOT_FOUND)
                .body(message);
    }

    @ExceptionHandler(Exception.class)
    public ResponseEntity handleGlobalException(Exception exception, WebRequest request) {
        ErrorMessage message = new ErrorMessage(
                HttpStatus.INTERNAL_SERVER_ERROR.value(),
                exception.getMessage(),
                request.getDescription(false)
        );

        return ResponseEntity.status(HttpStatus.INTERNAL_SERVER_ERROR)
                .body(message);
    }
}

5. 標準エラー応答の作成

標準エラー応答クラスを定義してエラー メッセージを構造化します。

package com.example.SpringBootRefresher.entity;

public class ErrorMessage {
    private int statusCode;
    private String message;
    private String description;

    public ErrorMessage(int statusCode, String message, String description) {
        this.statusCode = statusCode;
        this.message = message;
        this.description = description;
    }

    // Getters and setters

    public int getStatusCode() {
        return statusCode;
    }

    public void setStatusCode(int statusCode) {
        this.statusCode = statusCode;
    }

    public String getMessage() {
        return message;
    }

    public void setMessage(String message) {
        this.message = message;
    }

    public String getDescription() {
        return description;
    }

    public void setDescription(String description) {
        this.description = description;
    }
}

6. 検証エラーの処理

Spring Boot は Bean Validation (JSR-380) と適切に統合されています。検証エラーをグローバルに処理するには、@ControllerAdvice.
を使用します。

package com.example.SpringBootRefresher.error;

import org.springframework.http.HttpStatus;
import org.springframework.http.ResponseEntity;
import org.springframework.validation.FieldError;
import org.springframework.web.bind.MethodArgumentNotValidException;
import org.springframework.web.bind.annotation.ControllerAdvice;
import org.springframework.web.bind.annotation.ExceptionHandler;
import org.springframework.web.bind.annotation.ResponseStatus;
import org.springframework.web.context.request.WebRequest;
import java.util.HashMap;
import java.util.Map;

@ControllerAdvice
@ResponseStatus
public class ValidationExceptionHandler extends ResponseEntityExceptionHandler {

    @ExceptionHandler(MethodArgumentNotValidException.class)
    public ResponseEntity> handleValidationExceptions(MethodArgumentNotValidException ex) {
        Map errors = new HashMap();
        ex.getBindingResult().getAllErrors().forEach((error) -> {
            String fieldName = ((FieldError) error).getField();
            String errorMessage = error.getDefaultMessage();
            errors.put(fieldName, errorMessage);
        });
        return new ResponseEntity(errors, HttpStatus.BAD_REQUEST);
    }
}

7. 単純な例外に対する @ResponseStatus の使用

簡単な場合は、例外クラスに @ResponseStatus アノテーションを付けて、HTTP ステータス コードを指定できます。

package com.example.SpringBootRefresher.exception;

import org.springframework.http.HttpStatus;
import org.springframework.web.bind.annotation.ResponseStatus;

@ResponseStatus(HttpStatus.NOT_FOUND)
public class DepartmentNotFoundException extends RuntimeException {
    public DepartmentNotFoundException(String message) {
        super(message);
    }
}

8. 本番環境のベストプラクティス

  1. 一貫したエラー応答: アプリケーションが一貫性のある構造化されたエラー応答を返すようにします。標準エラー応答クラスを使用します。
  2. Logging: デバッグと監視の目的で例外をログに記録します。機密情報がログに漏洩しないようにしてください。
  3. ユーザーフレンドリーなメッセージ: ユーザーフレンドリーなエラーメッセージを提供します。内部の詳細やスタック トレースをユーザーに公開しないでください。
  4. セキュリティ: 機密データの公開を避けるために、エラー応答に含まれる情報には注意してください。
  5. ドキュメント: チームと将来のメンテナー向けに例外処理戦略を文書化します。

まとめ

Spring Boot での例外処理には、@ExceptionHandler、@ControllerAdvice、@ResponseStatus などのアノテーションを使用してエラーを効果的に管理することが含まれます。カスタム例外を作成し、検証エラーを処理し、ベスト プラクティスに従うことで、エラーを適切に処理し、ユーザーに有意義なフィードバックを提供する堅牢なアプリケーションを構築できます。 Java 17 機能を使用すると、アプリケーションは Java エコシステムの最新の改善点を確実に活用できます。

リリースステートメント この記事は次の場所に転載されています: https://dev.to/isaactony/Exception-handling-in-spring-boot-2lgd?1 侵害がある場合は、[email protected] に連絡して削除してください。
最新のチュートリアル もっと>

免責事項: 提供されるすべてのリソースの一部はインターネットからのものです。お客様の著作権またはその他の権利および利益の侵害がある場合は、詳細な理由を説明し、著作権または権利および利益の証拠を提出して、電子メール [email protected] に送信してください。 できるだけ早く対応させていただきます。

Copyright© 2022 湘ICP备2022001581号-3