如何在REST API中建模进度资源?遵循JSON:API v1.0规范
符合JSON:API v1.0规范的进度查询接口设计
结合你的需求和JSON:API v1.0的规范,我整理了一套清晰的接口设计方案,完全贴合你的预期功能,同时严格遵循规范要求:
核心资源定义
先明确两个核心资源的关联逻辑:
sections: 单个章节资源,包含id、title等业务属性progress-entries: 进度条目资源,每个条目和section是一对一关联,建议给每个progress-entry添加position属性来记录它在进度序列中的顺序(比如1、2、3...),或者添加previous-entry关联直接指向序列中的前一个条目,两种方式都能实现你的查询需求。
具体接口实现方案
1. 获取完整进度序列
要拿到按完成顺序排列的所有进度条目,直接请求progress-entries集合并指定排序规则(JSON:API要求显式声明排序,不能依赖默认顺序):
GET /progress-entries?sort=position
返回结构会包含所有进度条目,同时可以用included字段嵌入关联的sections资源,和你预期的格式一致。
2. 获取首个进度条目
有两种符合规范的实现方式:
- 分页方式:利用分页参数取排序后的第一个条目,这是JSON:API推荐的通用方式:
GET /progress-entries?sort=position&page[limit]=1 - 自定义筛选:如果想要更语义化的参数,可以自定义筛选条件(JSON:API允许自定义筛选逻辑,只要在API文档中说明):
GET /progress-entries?filter[first]=true&sort=position
两种方式都会返回你要的sectionG对应的进度条目及关联章节。
3. 获取当前(最后一个)进度条目
同样用两种方式实现:
- 分页方式:倒序排序后取第一个条目:
GET /progress-entries?sort=-position&page[limit]=1 - 自定义筛选:用语义化参数直接指定:
GET /progress-entries?filter[current]=true
返回结果就是序列最后一个sectionA对应的进度条目。
4. 获取指定章节的前序进度条目
这里推荐两种更符合JSON:API规范的实现,比你之前设想的filterAction更贴合规范:
方式一:通过关联关系查询
如果每个progress-entry都有previous-entry关联字段(指向序列中的前一个条目),可以分两步:
- 先找到对应
sectionZ的进度条目:GET /progress-entries?filter[section-id]=sectionZ - 再请求这个条目的
previous-entry关联资源:GET /progress-entries/{找到的progressZ-id}/relationships/previous-entry
这种方式完全遵循JSON:API的关联资源查询规则,非常规范。
方式二:自定义筛选参数(更直接)
如果你想一步到位,可以设计语义化的自定义筛选参数,比如:
GET /progress-entries?filter[next-section-id]=sectionZ
这里next-section-id表示“筛选出下一个条目是sectionZ的进度条目”,也就是你要的sectionG对应的前序条目。
如果坚持要用类似filterAction的逻辑,建议把参数放在filter对象内(符合JSON:API对筛选参数的位置要求):
GET /progress-entries?filter[target-section-id]=sectionZ&filter[action]=get-previous
返回结果就是你预期的sectionG对应的进度条目及关联章节。
关键规范注意点
- 资源类型必须用复数形式(
progress-entries、sections),这是JSON:API的强制要求 - 排序必须显式指定,不能依赖后端的默认存储顺序
- 自定义筛选参数一定要在API文档中明确说明逻辑,因为JSON:API只规定了筛选参数要放在
filter下,没有限制具体格式 - 关联资源可以用
included字段嵌入返回,或者通过related链接指向,按需选择即可
内容的提问来源于stack exchange,提问作者Stephen S
相关产品推荐
相关产品推荐

