2013-10-15 66 views
4

我實施了重命名公司如下的API:如何以冪等方式重命名資源?

PUT /companies/A 
{ 
    "name": "B" 
} 

將返回HTTP 301Location頭在該公司的新的URI指出:/companies/B

我該如何使這個操作冪等與If-Match標題?

  1. 沒有If-Match頭:如果用戶試圖重命名一個不存在的公司,我期望服務器返回HTTP 404,但我不能這樣做,因爲當時合法的重命名操作不會冪(他們會在第一次返回301,在後續調用時返回404)。這是有問題的,因爲我希望客戶能夠區分失敗的重命名(公司不存在)和已經發生的重命名。

  2. With If-Match標題:如果公司的ETag取決於公司名稱,則後續重命名操作將失敗,因爲前提條件不再成立。再一次,這使得看起來操作失敗了,事實上它已經發生了。

回答

1

放置操作成功,應返回相同的資源200或201的後續請求應該返回一個301指示新資源的URI的適當響應主體。

404只應用於真正無法找到的資源,即不存在且永不存在的公司。

protocol所述,冪等性並不意味着該調用始終返回相同的結果。這意味着沒有副作用。此外,冪等性不適用於錯誤條件下,除2xx之外的任何其他(如301)。

我真的很佩服我們承諾按規範正確使用它的承諾,但是與所有的事情一樣,它是受制於解釋的。

0

我不認爲3xx在這裏有意義。 PUT操作成功,所以它應該返回一個2xx。 301意味着資源不在請求者認爲的地方。

一般來說,我一直覺得挺有趣關於人不使用MOVE當他們真正想要MOVE :-)

+1

對不起。我限制自己的核心HTTP方法。沒有WEBDAV對我來說:) – Gili

5

好的,這已經兩歲了,但我會回答它,以防其他人像我一樣絆倒它。

簡短的回答是,從HTTP點,重命名(移動)資源冪,你應該使用POST代替PUT

長的答案:PUT是「創建或 - 替換」操作,通過RFC 2616定義如下(重點煤礦):

將所附實體下提供的存儲PUT方法請求Request-URI

RFC 7231(這在這個問題被問時存在只是作爲草案),提出更加明確:

目標資源的狀態是 創建或取代他們的是PUT方法請求包含在請求消息有效載荷中的表示 定義的狀態。一個給定的 表示的成功PUT將表明對相同 目標資源的後續GET將導致等效表示是 在200OK)響應發送。

因爲一個成功的重命名將導致資源在不同位置可用,PUT是不適用的。

PS。也許你可以在PUT上做這項工作,方法是在請求正文中包含公司的某種唯一標識符,而不管它的名稱或其他屬性如何,這將允許您檢測先前的重命名併發出適當的重定向。不過,我認爲這是違背協議,POST會更合適。

+0

我結束了'GET/companies/{name}'返回一個重定向到'/ companies/{id}',並且只允許後者使用PUT。這樣,'GET'和'PUT'都是冪等的。 – Gili