1概要

この簡単な記事では、

HttpMediaTypeNotAcceptableException

例外について説明し、それが発生する可能性があるケースについて理解します。


2問題

SpringでAPIエンドポイントを実装する際には、一般的に消費される/制作されるメディアタイプを(

consumes



produces

パラメータで)指定する必要があります。これは、その特定の操作のためにAPIがクライアントに返す可能性のあるフォーマットを絞り込みます。

HTTPには専用の「Accept」ヘッダーもあります。これは、クライアントが認識して受け入れることができるメディアタイプを指定するために使用されます。簡単に言うと、サーバーはクライアントが要求したメディアタイプの1つを使用してリソース表現を返送します。

  • ただし、両側で動作できる共通の型がない場合、Springは

    HttpMediaTypeNotAcceptableException

    例外をスローします。


3実用例

このシナリオを説明する簡単な例を作成しましょう。

POSTエンドポイントを使用します。これは

__“ application/


json

“ __でのみ機能し、JSONデータも返します。

@PostMapping(
  value = "/test",
  consumes = MediaType.APPLICATION__JSON__VALUE,
  produces = MediaType.APPLICATION__JSON__VALUE)
public Map<String, String> example() {
    return Collections.singletonMap("key", "value");
}

次に、認識されないコンテンツタイプのCURLを使用してリクエストを送信しましょう。

curl -X POST --header "Accept: application/pdf" http://localhost:8080/test -v

> POST/test HTTP/1.1
> Host: localhost:8080
> User-Agent: curl/7.51.0
> Accept: application/pdf

私たちが得た反応は次のとおりです。

< HTTP/1.1 406
< Content-Length: 0


4ソリューション

  • この問題を解決するには、サポートされている種類のいずれかを送受信する方法しかありません。

できることはすべて、受け入れ可能なすべてのメディアタイプについてクライアントに通知するカスタムの

ExceptionHandler

を付けて、より説明的なメッセージ(デフォルトではSpringが空の本文を返す)を提供することです。

私たちの場合、それは

“ application/json”

だけです:

@ResponseBody
@ExceptionHandler(HttpMediaTypeNotAcceptableException.class)
public String handleHttpMediaTypeNotAcceptableException() {
    return "acceptable MIME type:" + MediaType.APPLICATION__JSON__VALUE;
}


5結論

このチュートリアルでは、クライアントが要求したものとサーバーが実際に生成できるものとの間に不一致がある場合にSpring MVCによってスローされる

HttpMediaTypeNotAcceptableException

例外を検討しました。

いつものように、この記事で言及されているコードスニペットはhttps://github.com/eugenp/tutorials/tree/master/spring-mvc-java[our GitHub repository]にあります。