[4] [DFN[[CODE(HTTP)[[[4[VAR[xx]]]]]]]] は、[[クライアント]]側の誤りを表す[[状態符号]]です。

[FIG(short list)[
- [CODE(HTTP)[[[400]]]]
- [CODE(HTTP)[[[401]]]]
- [CODE(HTTP)[[[402]]]]
- [CODE(HTTP)[[[403]]]]
- [CODE(HTTP)[[[404]]]]
- [CODE(HTTP)[[[405]]]]
- [CODE(HTTP)[[[406]]]]
- [CODE(HTTP)[[[407]]]]
- [CODE(HTTP)[[[408]]]]
- [CODE(HTTP)[[[409]]]]
- [CODE(HTTP)[[[410]]]]
- [CODE(HTTP)[[[411]]]]
- [CODE(HTTP)[[[412]]]]
- [CODE(HTTP)[[[413]]]]
- [CODE(HTTP)[[[414]]]]
- [CODE(HTTP)[[[415]]]]
- [CODE(HTTP)[[[416]]]]
- [CODE(HTTP)[[[417]]]]
- [CODE(HTTP)[[[419]]]]
- [CODE(HTTP)[[[421]]]]
- [CODE(HTTP)[[[422]]]]
- [CODE(HTTP)[[[423]]]]
- [CODE(HTTP)[[[424]]]]
- [CODE(HTTP)[[[425]]]]
- [CODE(HTTP)[[[426]]]]
- [CODE(HTTP)[[[427]]]]
- [CODE(HTTP)[[[428]]]]
- [CODE(HTTP)[[[429]]]]
- [CODE(HTTP)[[[430]]]]
- [CODE(HTTP)[[[431]]]]
- [CODE(HTTP)[[[451]]]]
]FIG]

* 仕様書

[REFS[
- [2] [CITE@en[RFC 7231 - Hypertext Transfer Protocol (HTTP/1.1): Semantics and Content]] ([TIME[2014-08-07 05:54:02 +09:00]] 版) <https://tools.ietf.org/html/rfc7231#section-6.5>
]REFS]

* 意味

[9] [CODE(HTTP)[4[VAR[xx]]]] は、[[クライアント]] ([[要求]])
に起因する[[誤り]]のため[[要求]]の処理に失敗したことを表します。

[10] ここで[[クライアント]]起因というのは、
[[サーバー]]起因の [CODE(HTTP)[5[VAR[xx]]]] との対比です。
[[サーバー]]の予期せぬ不具合や[[サーバー]]側ネットワークの異常などの[[例外]]的な場合に
[CODE(HTTP)[5[VAR[xx]]]] を使いますが、それ以外のほとんどの処理失敗は
[CODE(HTTP)[4[VAR[xx]]]] を使います。
[[クライアント]]が[[要求]]を修正して再実行することで成功する可能性もありますが、
また失敗する可能性もあります。
[[クライアント]]起因とはいえ、失敗の責任が[[クライアント]]にあるとは限りません。

[EG[
[11] 例えば次のような状況が考えられます。
[FIG(list)[
- 認証に失敗した場合
- 要求頻度制限を超過した場合
- 要求に指定するべき引数が不足している場合
- 要求に構文エラーが含まれる場合
- 指定された前提条件をサーバー側で満たしていない場合
- 指定されたファイルが存在しない場合
- 新規作成を指示されたオブジェクトが既に存在する場合
- 編集対象のファイルが[[ロック]]されていて変更できない場合
]FIG]
]EG]

* 構文

[5] [[サーバー]]は、 [CODE(HTTP)@en[[[HEAD]]]] [[要求]]の場合を除き、
誤りの状況と、状況が一時的か永続的かを説明した[[表現]]を送信する[['''べきです''']]
[SRC[>>2]]。

[12] その具体的な形式は、規定されていません。
多くの[[サーバー]]は、[[自然言語]]で誤りを説明した短めの [[HTML]]
を[[応答本体]]として送信します。

[13] 特定目的の[[サーバー]]は、独自の[[機械可読]]な形式を採用していることがあります。

[EG[
[14] 例えば、 [[WebDAV]] は [[XML]] の[[語彙]]を用意しています 
([CODE(XMLe)@en[DAV:error]] 参照)。
]EG]

[EG[
[15] [[RFC 7807]] は [[JSON]] 形式で誤りを説明する方法 
[CODE(MIME)@en[application/problem+json]] を定義しています。
]EG]

[EG[
[16] [[OAuth 2.0]] は [[JSON]] 形式で誤りを報告する方法を規定しています。
[[[CODE(XMLe)@en[error]]][error (OAuth 2.0)]]参照。
]EG]

;; [17] その他いろいろな [[Web API]] が、それぞれの[[誤り]]の報告方法を用意しています。
特定の[[サーバー]]向けではない、汎用的な[[誤り]]報告用の形式を定めようとする試みも無くはないのですが、
[[誤り]]の状況や報告できる詳細情報が多種多様で、 [[HTTP]] の[[状態符号]]以上に細かな報告を標準化するのは中々難しいようです。

* 処理

[6] [[利用者エージェント]]は、含まれている[[表現]]を[[利用者]]に[[表示]]する[['''べきです''']]
[SRC[>>2]]。

* 状態符号の決定

[7] エラー時の[[状態符号]]は、次のように決定できます。
(それぞれの詳細な意味は、それぞれの項を参照。)

[FIG(steps)[
= 複数の操作の一部がエラーなら、 [CODE(HTTP)[[[207]]]] とします。
= [[検閲]]のため続行できないなら、 [CODE(HTTP)[[[451]]]] とします。
= [[サーバー]]が[[中間器]]なら、
-= [[クライアント]]のアクセス権限の問題なら、
-== [[HTTP認証]]上の問題なら、[CODE(HTTP)[[[407]]]] とします。
-== それ以外の問題なら、 [CODE(HTTP)[[[511]]]] とします。
-= [[HTTPキャッシュ]]から結果を返す上での問題なら、 [CODE(HTTP)[[[504]]]] とします。
-= 障害であれ予定されたメンテナンスであれ、[[上流]]に接続できないなら、 
[CODE(HTTP)[[[503]]]] とします。
-= [[上流]]から[[応答]]を得られないなら、 [CODE(HTTP)[[[504]]]] とします。
-= [[上流]]からの得た[[応答]]が壊れているなら、 [CODE(HTTP)[[[502]]]] とします。
= [[実効要求URL]]の [[URL scheme]] や [[authority]] が[[サーバー]]側の想定と異なるものなら、
[CODE(HTTP)[[[421]]]] とします。
= 対象となる[[資源]]が存在していないなら、
-= 以前は存在していて、それを明らかにしても構わないなら、 [CODE(HTTP)[[[410]]]] とします。
-= それ以外なら、 [CODE(HTTP)[[[404]]]] とします。
= [[クライアント]]のアクセス権限に問題があるなら、
-= 理由や[[資源]]の存在自体を隠したいなら、 [CODE(HTTP)[[[404]]]] とします。
-= [[HTTP認証]]上の問題があるなら、 [CODE(HTTP)[[[401]]]] とします。
-= [[課金]]上の問題があるなら、 [CODE(HTTP)[[[402]]]] とします。
-= アクセス過多なら、 [CODE(HTTP)[[[429]]]] とします。
-= その他の問題があるなら、 [CODE(HTTP)[[[403]]]] とします。
= [[要求]]の解釈上の問題なら、
-= [[要求]]受信のタイムアウトなら、 [CODE(HTTP)[[[408]]]] とします。
-= [[プロトコルの版]]の問題なら、 [CODE(HTTP)[[[505]]]] とします。
-= [[要求URL]]が長すぎるなら、 [CODE(HTTP)[[[414]]]] とします。
-= [CODE(HTTP)@en[[[Content-Length:]]]] が指定されていない (のを[[サーバー]]が処理できない)
なら、 [CODE(HTTP)[[[411]]]] とします。
-= [[ヘッダー]]が長すぎるなら、 [CODE(HTTP)[[[431]]]] とします。
-= [[payload body]] が大きすぎるなら、 [CODE(HTTP)[[[413]]]] とします。
-= [[payload body]] の [[MIME型]]や[[内容符号化]]に対応できないなら、
[CODE(HTTP)[[[415]]]] とします。
-= [[payload body]] の構文解析上の問題なら、 [CODE(HTTP)[[[400]]]] とします。
-= [[XML]] [[外部実体]]の読み込みを[[サーバー]]が拒否したいなら、 [CODE(HTTP)[[[403]]]]
とします。
= [[要求]]の指定する処理の問題なら、
-= プロトコル選択の問題なら、 [CODE(HTTP)[[[426]]]] とします。
-= [CODE(HTTP)@en[[[Expect:]]]] の要求に対応できないなら、 [CODE(HTTP)[[[417]]]]
とします。
-= [[条件付き要求]]的に結果を返せ(さ)ない場合、 [CODE(HTTP)[[[412]]]] または 
[CODE(HTTP)[[[304]]]] とします ([[条件付き要求]]参照)。
-= [[条件付き要求]]でなければならないのにそうでないなら、 [CODE(HTTP)[[[428]]]] とします。
-= [[範囲要求]]的に結果を返せない場合、 [CODE(HTTP)[[[416]]]] とします。
-= [[内容折衝]]的に結果を返せない場合、 [CODE(HTTP)[[[406]]]] とします。
-= [[要求メソッド]]を適用できないなら、
-== 本[[資源]]には適用できない既知の[[メソッド]]なら、 [CODE(HTTP)[[[405]]]] とします。
-== そうでないなら、 [CODE(HTTP)[[[501]]]] とします。
-= 未知の指示が含まれているなら、 [CODE(HTTP)[[[501]]]] とします。
-= 実装上の都合で実施できない操作なら、 [CODE(HTTP)[[[502]]]] とします。
-= その他適用できない操作なら、 [CODE(HTTP)[[[418]]]] とします。
= 対象となる[[資源]]の現状と[[要求]]との不整合が問題なら、
-= [[payload body]] で指定された処理の指示に問題があるなら、 [CODE(HTTP)[[[422]]]]
とします。
-= [[ロック]]のため処理できないなら、[CODE(HTTP)[[[423]]]] とします。
-= その他処理に必要な事前の条件が整わないなら、 [CODE(HTTP)[[[424]]]] とします。
-= 処理中に無限ループが発生するなら、 [CODE(HTTP)[[[508]]]] とします。
-= その他の問題があるなら、 [CODE(HTTP)[[[409]]]] とします。
= 以上のいずれも該当しないなら、
-= サーバーの[[透過内容折衝]]の設定に問題があるなら、 [CODE(HTTP)[[[506]]]] とします。
-= サーバーのディスク容量の問題なら、 [CODE(HTTP)[[[507]]]] とします。
-= その他サーバーのトラブルなら、 [CODE(HTTP)[[[500]]]] とします。
-= それ以外なら、 [CODE(HTTP)[[[400]]]] とします。

;; [8] 複数該当するものがある場合、多くの場合には、[[サーバー]]の判断でどれを返すか決定できます。
]FIG]

* 歴史

[FIG(quote)[
[FIGCAPTION[
[3] RFC 1945 (HTTP/1.0) 9.4; RFC 2068 & 2616 (HTTP/1.1) 10.4 Client Error 4xx
]FIGCAPTION]

> The 4xx class of status code is intended for cases in which the client seems to have erred. [DEL[[INS[{1945}]] If the client has not completed the request when a 4xx code is received, it should immediately cease sending data to the server.]]
Except when responding to a HEAD request, the server [DEL[[INS[{1945}]] should]] [INS[[INS[{2068}]] SHOULD]]
include an entity containing an explanation of the
error situation, and whether it is a temporary or permanent
condition. These status codes are applicable to any request method. [INS[[INS[{2068}]] User agents SHOULD display any included entity to the user.]]

[CODE(HTTP)[4[VAR[xx]]]] 級の状態符号は、クライアントが誤っていると思われる場合に使うことを意図しています。 [DEL[クライアントが [CODE(HTTP)[4[VAR[xx]]]] 符号を受信した時に要求が完了していなければ、クライアントは即座にサーバーへのデータの送信を止めるべきです。]]
[CODE(HTTP)[[[HEAD]]]] 要求に対する応答の場合を除き、サーバーは誤り状況の説明と、
一時的条件なのか永続的条件なのかを含んだ実体を含める'''べきです'''。
これらの状態符号はどの要求 method についても適用できます。 [INS[ル容赦エージェントは含まれている実体を利用者に表示する'''べきです'''。]]

> [DEL[[INS[{1945,2068}]] Note:]] If the client is sending data, [INS[[INS[{2068}]] a]] server implementation[DEL[s]] [DEL[[INS[{1945}]] on]] [INS[[INS[{2068}]] using]]
TCP [DEL[[INS[{1945,2068}]] should]] [INS[[INS[{2616}]] SHOULD]] be careful to ensure that the client acknowledges receipt of the packet(s) containing the response[INS[,]] [DEL[[INS[{1945}]] prior to closing]] [INS[[INS[{2068}]] before the server closes]]
the input connection. If the client continues sending data to the server after the close, the server's [DEL[[INS[{1945}]] controller]] [INS[[INS[{2068}]] TCP stack]]
will send a reset packet to the client, which may erase the client's unacknowledged
input buffers before they can be read and interpreted by the HTTP application.

クライアントがデータを送信している時、 TCP
を使っているサーバー実装は、サーバーが入力接続を閉じる前にクライアントが応答を含んでいるパケットの受信に確実に肯定応答するよう注意する'''べきです'''。
閉じた後もクライアントがサーバーにデータを送り続けるなら、
サーバーの TCP スタックはクライアントに[RUBY[再設定] [リセット]]パケットを送信することとなり、
クライアントの否定応答入力バッファを HTTP 応用により読んで解釈することが出来る前に消去してしまうかもしれません。
]FIG]

[1] [CITE[Extended HTTP Error Codes]]
( ([TIME[2009-03-01 03:42:47 +09:00]] 版))
<http://www.gumbyware.com/~eric/http-errors.html>

* 関連

[432] [CODE(HTTP)[[[4xx]]]] は[[クライアント]]の[[要求]]に関するエラーを表し、
[CODE(HTTP)[[[5xx]]]] が[[鯖]]側のエラーを表します。