唯一键会破坏 POST 非幂等性吗?

does unique keys break the POST non-idempotency?

我读了很多关于幂等和非幂等的文章,我 认为 我清楚地理解了这个概念。 然而,POST 的场景让我感到困惑。

a POST 应该总是创建一个新资源。例如:

  1. POST api/persons { Name: "John" } --> persons/1
  2. POST api/persons { Name: "Jack" } --> persons/2
  3. POST api/persons { Name: "Jack" } --> persons/3

这很明显,但假设一个人有一个 ID 作为 PK,还有 SSN,这是一个唯一的密钥。 在那种情况下,如果我发送两个具有相同 SSN 的 POST 请求,它不会创建两个新资源:

  1. POST api/persons { Name: "John", SSN: 123 } --> persons/1
  2. POST api/persons { Name: "Jack", SSN: 123 } --> error

请注意,我没有发送 ID PK,因此理论上,POST 应该将其视为新资源并创建它。

这会破坏 REST POST 非幂等性标准吗?

POST should always create a new resource.

这是一种误解 - 您可以将 POST 用于其他目的。它故意非常通用。

Does that breaks the REST POST non-idempotency standard?

不,因为 POST 不需要 是非幂等的。

例如,假设我们要提供一个 Web API,允许消费者查询数据库中的信息。由于操作是“本质上只读的”,我们可以使用具有 safe 语义的消息。

我们通常会使用 GET 并使用查询字符串来描述查询参数。

但是 URI 的长度存在事实上的限制,因此也限制了查询的长度。如果我们需要支持超出这些限制的查询,我们唯一的选择是将参数移动到请求正文中。

并且标准的“安全”HTTP 方法没有为请求主体定义明确的语义。

因此,为了确保正确的行为,我们使用 POST,而不是 GET。服务器上的效果仍然是“本质上只读”,但是只能看到消息的 generic 组件(而不是我们的带外 API 文档)将不知道消息是安全的,并且将无法执行使用安全方法时可用的优化(缓存、自动重新发送、爬网)。

换句话说,我们在 HTTP 中所做的一切都可以用 POST 完成 - 其他方法所做的是允许我们解锁通用 consumers/observers 消息的优化。

实际上,HTTP 根本不限制实现——它描述了语义。这是 Roy Fielding 在 2002 年的解释:

HTTP does not attempt to require the results of a GET to be safe. What it does is require that the semantics of the operation be safe, and therefore it is a fault of the implementation, not the interface or the user of that interface, if anything happens as a result that causes loss of property (money, BTW, is considered property for the sake of this definition).

POST 不承诺是幂等的,因此如果客户认为它确实实现了该承诺,他们就会崩溃。