带有身份验证的RESTful API URL设计

时间:2020-05-03 19:59:12

标签: rest api restful-authentication

我的数据模型是这样的:

User: id, email, hashed_password
Item: id, name, color
UserItem: user_id, item_id, rating

,我想编写一个RESTful API来获取这些资源。通过OAuth 2使用JWT令牌(包含已记录的用户ID)提供身份验证。

第一种方法

端点

URL结构的第一个想法是(我在仍然没有身份验证时选择的结构):

/items/{item_id}
/users/{user_id}
/users/{user_id}/items/{item_id}

在这种情况下,标识为1的用户可以使用:

  • GET /users/1来获取自己的信息;
  • GET /users/1/items获得自己的物品(带有评分);
  • GET /items获取所有可以添加到收藏夹的物品。

分析

我认为这种解决方案很明确,但也没有意义。

好:

  • 您可以轻松获取其他用户的信息(如果他们可用)
  • 端点和数据模型之间的
  • 一对一关系。

坏:

  • 更长的网址;
  • 存在冗余(为什么在令牌中您已经拥有有关ID 1的信息,为什么GET /users/1/items?)。

第二种方法

端点

鉴于您可以从令牌中提取用户ID,因此结构也可以更简单:

/items/{item_id}
/users/{user_id}

在这种情况下,标识为1的用户可以使用:

  • GET /users/me来获取自己的信息;
  • GET /items?class=owned获得自己的物品(带有评分);
  • GET /items?class=all获取所有可以添加到收藏夹的物品。

分析

此解决方案有点混乱,但可能更优雅。

好:

  • 更短的网址;
  • 减少冗余(GET /items来获取您自己的物品)。

坏:

  • 仅表示模型UserItem(即使在这种情况下,获得没有评分的Item可能几乎没有意义,如果用户尚未添加,则可以将其设置为null);
  • 获取其他用户的商品并不容易(也许像GET /items?user=3?)。

结论

老实说,在这种情况下,我不知道什么是最佳实践。我觉得这两者都有些问题。也许我没有看到一种混合方法?

您将如何组织这样的模型?

1 个答案:

答案 0 :(得分:2)

您可以查看类似HAL的格式。 HAL为您提供了一种描述特定资源(项目)的方法,并允许您创建指向这些资源的多个集合。

这意味着可以在/items/xyz托管单个项目,但这些项目可以同时属于/user/a/items/items集合的一部分。

我在超媒体客户端https://github.com/badgateway/ketting中做了很多工作。不过,这不仅是广告,还有其他选择,但我们可能非常适合您这种API设计方法。

但是,无论您使用的是哪个客户端,这样的系统都可以避免通过多个端点检索同一项目的问题。单个项目具有规范的网址,如果系统设计良好,则只需检索一次即可。

集合只是到属于该集合的资源(项目)的链接的列表。他们指向该项目,但不要像常规超链接那样“包含”该项目。