HTTPメソッドのPUT・DELETEは、
本当に冪等(べきとう)なのか?

冪等とは?

冪等とは、ある操作を1回行っても複数回行っても結果が同じこと、である。

HTTPメソッド

GET・HEAD

GET・HEADが冪等というのは、納得がいく。

確かに、同じリソースファイルのURLに何度GET・HEADリクエストしようとも、リソースの状態は変わらないだろう。

少し引っかかるのは、クライアントに返却されるレスポンスコードは変わるということだ。

GETのレスポンスは、リソースファイルがクライアントでキャッシュされているかによって、200(200)か304(Not Modified)になるだろう。

PUT・DELETE

PUT、DELETEについては疑問が残る。

PUTは、対象のリソースを更新するが、リソースがなければ作成する。

DELETEは、対象のリソースがあれば削除するが、リソースがなければ何もしない。

サーバーのリソースの状態を見ると、PUTの場合、1度目のリクエストでリソースが作成され、2度目のリクエストでリソースが更新される。

DELETEの場合、1度目のリクエストでリソースが削除され、2度目のリクエストはリソースが見つからず何もしない。

クライアントへのレスポンスを見ると、PUTの場合、1度目のリクエストで201 (Created)が返され、2度目のリクエストで200 (Ok)が返ってくる。

DELETEの場合、1度目のリクエストで200 (Ok)が返され、2度目のリクエストで404 (NotFound)が返ってくる。

つまり、1度目のリクエストと2度目のリクエストで、サーバー側で行われる処理(サーバー内部処理と、サーバーからクライアントへのレスポンス)が異なるのだ。

これでも、冪等(複数回行っても結果が同じ)と言っていいのだろうか?

答え

RFCの定義


4.2.2.  Idempotent Methods

A request method is considered “idempotent” if the intended effect on

the server of multiple identical requests with that method is the

same as the effect for a single such request.  Of the request methods

defined by this specification, PUT, DELETE, and safe request methods

are idempotent.

Hypertext Transfer Protocol (HTTP/1.1): Semantics and Content

RFCには、冪等なメソッド(Idempotent Methods)について上記の記述がある。

あるリクエストメソッドを使って、複数回の同じリクエストをした場合、サーバー上の結果が、1回のリクエストの結果と同じである場合、そのリクエストメソッドは「冪等」である。

つまり、まず「effect on the server」とあるので、クライアントへのレスポンス結果は無視して良い。

そしてサーバーの「結果」に着目すると、PUTの1回目の結果はリソースが存在するし、2回目も結果としてリソースが存在するので、サーバー上の「結果」としては同じ(=冪等)なのだ。

「effect on the server」のeffectを「効果」や「影響」の意味で捉えてしまうと、誤解してしまう。

また、当初の疑問のように、サーバーに通信した「結果」サーバー上で起こること、と捉えると混乱するので、サーバーに通信した後のサーバー上の「結果」と捉えればよい。

「安全」とは?

余談だが、PUT・DELETEは冪等であり「安全」でない、と定義されている。

「安全」とは「read-only」のことだ。

PUT・DELETEは読み込みだけでなく書き込みも行うため、当然「安全」ではない。

カテゴリー: