【问题标题】:Rest API resource naming with multiple IDs具有多个 ID 的 Rest API 资源命名
【发布时间】:2023-03-25 19:49:01
【问题描述】:

看完后:

https://restfulapi.net/resource-naming/

当一个文档具有多个唯一 ID 时,我有一个问题是重新分级引用集合中的文档。

在链接的材料中给出了一个例子:

我们可以使用 URI 识别单个“客户”资源 “/customers/{customerId}”。

http://api.example.com/device-management/managed-devices/{device-id}
http://api.example.com/user-management/users/{id}
http://api.example.com/user-management/users/admin

还有我的例子:

http://myserver/api/courses/{id}

其中有对应的js Express函数:

app.get('/api/courses/:id', (req, res) =>... 

我的问题是,如果我的文档(课程)有两个我想使用的唯一 ID 密钥,我该如何维护一致的 API。

如ID1 & ID2。

我将如何在 express 中编码以及如何编写 url?

所以如果我需要这两个 API:

http://myserver/api/courses/{id1}
http://myserver/api/courses/{id2}

如果我提供两个 Express 例程:

app.get('/api/courses/:id1', (req, res) =>... 
app.get('/api/courses/:id2', (req, res) =>... 

并且 ID1 和 ID2 都是相同的类型(例如数字)。 REST API 如何区分这两者?

【问题讨论】:

  • 您能否告诉我们为什么您有这些不同的 ID?它们与外部世界相关吗?否则,您可以只使用一个 ID。
  • @charlietfl 这不是真的。一个元素可以有多个唯一 ID - 每个 ID 在明确定义的范围内都是唯一的
  • 我很想知道你如何存储你的课程,你将如何在数据库中查询它?如果以相同的方式查找它,那么您仍然只使用单一路线,例如/api/courses/1234/api/courses/5678 可以引用相同的课程但仍使用相同的 API
  • 许多国家/地区的课程/产品都有本地 ID 和国际 ID。库存系统一直在做这件事!!!卖方零件编号,供应商零件编号。既独特又多次不同!!!

标签: javascript rest express


【解决方案1】:

REST API 的命名约定与 express 确定它的方式不同。 OP 编写路线的方式,快递将无法区分这些路线。 Express 将路由存储在堆栈中,并将与首先声明的路由 (id1) 匹配。 id1 只是一个表示通用数据的名称(如作用域变量)。

【讨论】:

    【解决方案2】:

    REST 不关心资源标识符的拼写。约定,如 https://restfulapi.net/resource-naming/ 所描述的约定,大致类似于关于拼写变量名称的编码约定。

    从 REST 客户端的角度来看,/api/courses/X/api/courses/Y 是不同的资源——这些资源可能共享相同的底层表示(因为它们是由相同的底层数据构成的),但这是服务器的实现问题。

    URI 拼写仅受RFC 3986 约束。

    /api/courses?id1=12345
    /api/courses?id2=67890
    

    这是一个完全合理的选择。一个潜在的好处是 HTML 包含一个标准,用于创建带有查询参数的 URI 模板。一个潜在的缺点是相对引用解析对查询部分中的非分层数据的处理方式与路径段中的分层数据不同。

    /api/courses/id1/12345
    /api/courses/id2/67890
    

    完全合理的选择,与上面相反的权衡。

    /api/courses/id1=12345
    /api/courses/id2=67890
    

    这实际上与上面的想法相同,只是拼写略有不同。它具有易于阅读和易于阅读的优点。但是,实际使用该模式可能具有挑战性,具体取决于您拥有哪种路由支持。

    作为URI templates,这些可能看起来像

    /api/courses/id1={id}
    /api/courses/id2={id}
    

    但是在你有 4 级 URI 模板支持的地方,你也许可以使用

     /api/courses/{/ids*}
    

    另一种可能性是使用受“矩阵参数”启发的拼写,例如

    /api/courses;id1=12345
    /api/courses;id2=67890
    

    同样,这为您在可读性、模板支持、相对分辨率支持等方面提供了一组不同的权衡。

    另见 Stefan Tilkov -- REST: I Don't Think It Means What You Think It Does

    【讨论】:

    • REST API 的命名约定与 express 确定它的方式不同。 OP 编写路线的方式,快递将无法区分这些路线。 Express 将路由存储在堆栈中,并将与首先声明的路由 (id1) 匹配。 id1 只是表示通用数据的名称(如作用域变量)。
    【解决方案3】:

    您需要在路径中或作为查询参数的 url 中进行另一种区分,以便知道正在发送哪个字段。默认为字段#1,另一个为字段#2

    app.get('/api/courses/:id1', (req, res) =>... 
    app.get('/api/courses/other-key/:id2', (req, res) =>...
    

    【讨论】:

      猜你喜欢
      • 2011-09-14
      • 1970-01-01
      • 2016-07-21
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2019-07-01
      • 2021-05-24
      • 2017-03-12
      相关资源
      最近更新 更多