在RESTful CRUD API中处理ID

在RESTful CRUD API中处理ID,rest,api,restful-architecture,api-design,restful-url,Rest,Api,Restful Architecture,Api Design,Restful Url,我正在设计一个创建/读取/更新/删除公共web API端点,使用HTTP上的RESTful模式和JSON有效负载,我想知道一个非常常见的设计问题,但我发现很难找到相关指南 让我们只关注API的“读取”和“更新”部分。当涉及到处理ID时,我对当前“适当的”REST最佳实践有点困惑。我的意思是: 通过HTTP GET“读取”员工返回一个或多个“小部件”JSON对象(例如,我有一种方法可以检索满足特定条件的所有小部件)。每个小部件对象都有一个作为GUID的ID字段 我看到了“更新小部件”端点的几个设计

我正在设计一个创建/读取/更新/删除公共web API端点,使用HTTP上的RESTful模式和JSON有效负载,我想知道一个非常常见的设计问题,但我发现很难找到相关指南

让我们只关注API的“读取”和“更新”部分。当涉及到处理ID时,我对当前“适当的”REST最佳实践有点困惑。我的意思是:

通过HTTP GET“读取”员工返回一个或多个“小部件”JSON对象(例如,我有一种方法可以检索满足特定条件的所有小部件)。每个小部件对象都有一个作为GUID的ID字段

我看到了“更新小部件”端点的几个设计选项:

  • HTTP放入整个小部件对象的/api/widgets/{widget id}。如果对象中存在“ID”字段,则API将失败。(我不喜欢这种方法,因为来自“读取”端点的数据不能在不修改的情况下往返到“更新”端点)
  • HTTP放入整个小部件对象的/api/widgets/{widget id}。API将忽略对象中的“ID”字段(如果存在)。(我认为这比上面的更好,但是提供的ID可能不正确,我认为默默忽略坏数据是错误的)
  • HTTP放入整个小部件对象的/api/widgets/{widget id}。API将验证对象中的ID字段必须与URI中的ID匹配,否则将失败。(我认为这更好,但URI和消息体之间的数据仍然是重复的)
  • HTTP放入整个小部件对象的/api/widgets/{widget id}。API将验证对象中的ID字段必须不存在或必须与URI中的ID匹配,否则将失败。(这是我倾向的方法)
  • HTTP放入整个小部件对象的/api/widgets,包括ID字段,即要更新的对象的ID将来自消息体,而不是URI
  • 与#5相同,但使用HTTP POST-如果指定了ID,则可能使用“更新”语义,如果未指定,则使用“创建”语义
  • 我可以在这里看到各种权衡。选项6在我看来特别优雅,但不是特别“RESTful”,对于API的用户来说可能是一种不熟悉的模式。我看到的大多数API设计指南文档似乎都建议使用“PUT to/API/widgets/{widget id}”方法,但没有提到上面的#1/2/3/4区别


    那么什么是“RESTfully correct”/“最佳实践”方法呢?(对于使用我的公共API端点的开发人员来说,这是最熟悉、最容易混淆的方法)。还有其他我没有想到的设计选项(或设计注意事项)吗?

    如果ID是强制性的,您可以公开它。另一种方法是,在实体中可以有一个唯一的字段。无需传递ID,也可以创建包含唯一字段的DTO。在您的例子中,{widget id}是唯一的,并且id始终是自动生成的int id。使用POST,这是公共API的最佳方法

    如果您需要对Widget执行多个操作,请使用“Widget”(例如:site.com/Widget)创建4个不同的端点,它将get、post、put以及delete定义为不同的方法。这意味着单个API将根据其调用的不同方法而发挥不同的作用