0

到目前为止,我理解幂等性的方式基本上是:如果我向服务器发送 10 个相同的 PUT,则创建的额外资源将与我发送单个 PUT 语句时相同。

我认为这意味着以下实现将遵守这一点:

[AcceptVerbs(HttpVerbs.Put)]
ContentResult User(){

     //parse XML that was sent to get User info
     //User has an e-mail address which is unique to the system
     //create a new user in the system only if one for this e-mail address does not exist

     return Content(something, "text/xml");
}

现在,如果我为用户数据发送了 10 个带有 XML 的 PUT,并且它们都包含相同的电子邮件地址,那么只会创建一个用户。

但是,如果他们发送了 10 个请求(无论出于何种原因)并且它们都是不同的,但电子邮件是相同的,该怎么办。如果第一个请求没有通过,那么将使用第二个请求的数据来创建用户,而后面的 8 个请求将被忽略。这里有漏洞吗?或者我应该忽略在各个方面都明确相同的请求,而是返回一个错误,说明如果用户使用相同的电子邮件地址,用户已经存在?

另外,这样的 PUT 语句应该发送什么样的响应?关于用户的信息?也许一个 ID 可以通过其他 API 调用来操纵它们?或者它应该只说“成功”或“失败:[错误详细信息]”?

4

2 回答 2

2

您的问题不会显示 PUT 请求发送到的 URL。这实际上非常重要,因为决定是创建新资源还是更新旧资源的不是 XML 数据中的电子邮件地址,而是您发送请求的 URL。

因此,如果您将 PUT 发送到 /users/jonh.doe@foo.com/ 它会创建用户 john.doe@foo.com 或更新它(如果它已经在系统中)。

同样,如果您将 PUT 发送到 /users/123/(使用 id 而不是电子邮件),它将创建或更新用户 123。但是,在这种情况下,如果电子邮件必须是唯一的并且有人发送 PUT /users/456/ 并且在如果 XML 与用户 123 已经拥有的电子邮件相同,则您必须使用 409 Conflict 进行响应。

于 2011-06-07T22:19:23.323 回答
0

如果用户已经使用相同的电子邮件地址存在,则第二次和后续的 PUT 操作应更新该资源的数据。成功或失败应在状态码中传达。如果更新成功,回复“200 OK”,或者“204 No Content”;您可以返回一些信息,但不要期望缓存将其存储为好像它是您从 GET 获得的新表示。如果您不打算让该资源接受除第一个之外的 PUT 操作,则改为使用“405 Method Not Allowed”进行响应,并在响应正文中进行解释。如果提交的表示可能会替换资源,但不能因为它'

于 2011-06-07T21:53:34.243 回答