Web API规范设计指引
前言
本文本身不是规范,而是指引做规范的。
关于RESTful
应认真考虑要不要使用RESTful规范,不要盲目跟风。它的缺点在小公司里特别明显:
- 高度抽象,需要一定的设计能力。初级程序员很容易破坏整体设计,这不可能都被Review到。接口使用者也未必能做好反馈
- 需要对HTTP协议有一定的理解
- 一般越好的设计就有越多的约束,也就可能有越高复杂度,因此交接工作的学习成本高
- 产品迭代很快时,接口可能变动很频繁导致版本升级也很快,各种为了好设计而花费的时间都失去意义
- 不针对业务,复杂场景需要多次请求
如果确定使用,可以参考Github上这两个最多star的规范
- OpenAPI-Specification
- http-api-design
文档系统
无论是独立的wiki还是整合在网关系统中,文档系统都应该支持全局模糊搜索。
文档有3种,全局设计规范、API参考手册、文档系统本身的使用指南。
其中,参考手册的每个API说明应包括这些信息:
- URL
- method
- 传参方式(URL query、HTTP header、body)
- 请求与响应的参数表
- 参数名
- 类型(string、array、object、int、float、bool)
- 是否必填,必填时的默认值
- 说明:中文名称、功能意义、取值范围。至少要能看出对应需求文档或UI稿的哪个东西
- 可能的错误码与错误信息
- 示例
全局规范
URL格式
大小写和连接符的规范应该全局统一:snake_case或者camelCase。一般snake_case会更像普通的web URL。
如果使用RESTful,URL格式可以是
https://api.example.com/{service_name}/{version}/{api_name}?{filters}
或
https://www.example.com/api/{service_name}/{version}/{api_name}?{filters}
。
注:Web URL和API URL的规范是不同的。
header
如果不用RESTful,最好也不要把参数放到header里,尽量在HTTP协议框架内实现业务。在此前提下,如果存在(所有接口都需要的)公共参数,可以放在URL query里;或者最方便地使所有接口的method都是POST然后放body里。
JSON格式的Content-Type
是application/json
。如果进行了加密和BASE64转码,正确的Content-Type
应该是text/plain
。
如有必要,可进一步指定编码:application/json;charset=utf-8
。
业务参数
(以下讨论的是放在body里的JSON。)
各个key的大小写和连接符的规范应该全局统一:snake_case或者camelCase。
必填参数应该约定默认值。如不指定,可认为各类型的默认值是0
、0.0
、{}
、[]
、""
、false
,决不能是null
或undefined
。
非必填参数在无值时有3种风格,应该选定一种全局统一:
- 不存在这个key
- value是
null
- value是
undefined
非必填参数不允许是这个参数类型的默认值(0
、0.0
、{}
、[]
、""
、false
)
值是数字就用数字类型,不要用字符串。
布尔类型用JSON的语义true/false
来表示,不要用1/0
。
值为枚举时,尽量用字符串表示而不是用数字。牺牲一点点性能但可以大大增强代码可读性。这能大幅降幅维护成本,减少出错。
// 直接把枚举value写成字符串更便于开发维护
type: "duck",
type: "chicken"
// “用数字表示然后在文档中详细说明”可读性差,通常不会有人把文档复制成代码注释
type: 1, // duck
type: 2 // chicken
尽量不要为前端做格式化。例如时间,应返回“1970年1月1日0点至今的秒数”或者“按ISO8601进行格式化的UTC(世界标准时间)时间”,而不是直接返回“2018年11月11日 23:22:33”。让大前端自己做格式化能更好应对UI变化以及兼容特殊要求。比如客户端从中文切换成英文,界面上的“5月6日”需要变成“May 6th”;这种场景下如果是后端传的“5月6日”,那无论是再次请求英文还是客户端自行解释时间后做转换都是糟糕的设计。
保证向后兼容的前提下及时删除废弃的参数或接口。可以先对参数或接口标记Deprecated
,在前端发布后或客户端强制升级后删除。
同一意义的字段名,在不同接口返回的命名统一。不要这边叫“page_count”,那边叫“page_size”或"page_amount"。
响应体
较常见的JSON结构是这样的:
{"code": 0,"msg": "","data": {}
}
- code:0表示正常/成功,非0代表错误码。
- msg:表示错误信息。
- data:业务数据。所有的业务信息都应该放到data对象上。data一定是对象!
其中,错误码和错误信息也可以设计一份全局统一的对照表。需要注意的是,这里的code都表示业务情况,跟HTTP的status不要混用。 各级网关都可能以HTTP status表示错误,故它无法明确表示是业务API的问题。简单的例子是,业务API鉴权失败,HTTP也应该返回200 OK而不是返回401。因为接口是正常的,是数据逻辑不正确。
如果不用考虑多语言,msg
错误信息可以是面向用户的中文语句,由前端/客户端直接toast告知用户。
分页设计
请求参数应包含:
- 当前页码。接口文档应注释是从0还是从1开始计数。
- 每页条数
- (可选)排序
响应参数应包含:
- (可选)当前页码、每页条数、排序
- 数据数组
- 总页数或总条数,或是否还有下一页。总之不要让使用者再请求一次才知道没有更多数据了。
信息流
信息流跟分页的区别是在于信息流不知道有多少页,甚至可以就是无限的。如果前端UI不需要展示总页数或总条数,那分页也可以看做信息流,处理会更方便。
请求参数包含:
- 条数page_size
- 上次获取的最后一条信息的id或其它属性,用于给后端定位本次请求的数据起点。如果本参数为空则是从头开始。
响应参数包括:
- 数据数组
- (可选)是否还有下一页。这里可以用约定来提高性能。使用者判断到本次响应返回的条数小于请求里的条数,则认为没有下一页了。加上容错的考虑,可把“响应-请求”的条数差值加到2或3才认定。
组合请求
为了减少请求数,后端可提供组合请求接口,并且可组合任意接口。以下设计仅是举例:
假如有3个接口(示例的响应体经简化仅保留data
):
/a
:请求{"a": "a"}
会响应{"data": {"d": "d"}}
/b
:请求{"b": "b"}
会响应{"data": {"e": "e"}}
/c
:请求{"c": "c"}
会响应{"data": {"f": "f"}}
增加一个接口/combo
可以一次性获取这3个接口的数据:
// 请求
{"api": {"/a": {"a": "a"},"/b": {"b": "b"},"/c": {"c": "c"}}
}
// 响应
{"data": {"/a": {"data": {"d": "d"}},"/b": {"data": {"e": "e"}},"/c": {"data": {"f": "f"}}}
}
防攻击
- 加密机制。可对body做加密,使用
AES
、DES
、3DES
、RSA
、DSA
、ECC
等算法。一般会对密文做BASE64转码再在网络上传输。 - 校验机制,防篡改。对body做签名,可使用
MD5
、SHA1
、HMAC
等算法。签名只能放在URL query或HTTP header中。 - 防重放机制。可使用
timestamp
、nonce
等机制,在一定时间内重复即认为是重放。或者timestamp距今超过一定时间的,认为是非法请求。 - 鉴权。也就是常用的token。
最好在测试环境能通过参数控制上述机制的开关,方便调试、测试。
Web API规范设计指引相关推荐
- 《Web API 的设计与开发》读书笔记
设计优美的Web API: 易于使用.便于更改.健壮性好.不怕公开 REST的两层含义: 指符合Fielding的REST架构风格的Web服务系统 指使用符合RPC风格的XML或JSON + HTTP ...
- restful 风格 web api规范
协议:http/https 域名 : http://api.example.com/xxx/xxx api: 标明api接口服务 xxx: 服务 xxx: 资源 版本控制: 一.使用MediaType ...
- Web API核查表:设计、测试、发布API时需思考的43件事
当设计.测试或发布一个新的Web API时,你是在一个原有的复杂系统上构建新的系统.那么至少,你也要建立在HTTP上,而HTTP则是基于TCP/IP创建的.TCP/IP建立在一系列的管道上.当然,你也 ...
- ASP NET Web API 2框架揭秘
ASP.NET Web API2框架揭秘(.NET领域再现力作顶级专家精讲微软全新轻量级通信平台) 蒋金楠 著 ISBN 978-7-121-23536-8 2014年7月出版 定价:108.00 ...
- Web API应用架构设计分析(2)
在上篇随笔<Web API应用架构设计分析(1)>,我对Web API的各种应用架构进行了概括性的分析和设计,Web API 是一种应用接口框架,它能够构建HTTP服务以支撑更广泛的客户端 ...
- ASP.NET Web API 安全筛选器
原文:https://msdn.microsoft.com/zh-cn/magazine/dn781361.aspx 身份验证和授权是应用程序安全的基础.身份验证通过验证提供的凭据来确定用户身份,而授 ...
- 【转】Web API项目中使用Area对业务进行分类管理
在之前开发的很多Web API项目中,为了方便以及快速开发,往往把整个Web API的控制器放在基目录的Controllers目录中,但随着业务越来越复杂,这样Controllers目录中的文件就增加 ...
- Web Api 内部数据思考 和 利用http缓存优化 Api
在上篇<Web Api 端点设计 与 Oauth>后,接着我们思考Web Api 的内部数据: 其他文章:<API接口安全加强设计方法> 第一 实际使用应该返回怎样的数据 ? ...
- Web API应用架构在Winform混合框架中的应用(3)--Winfrom界面调用WebAPI的过程分解...
最近一直在整合WebAPI.Winform界面.手机短信.微信公众号.企业号等功能,希望把它构建成一个大的应用平台,把我所有的产品线完美连接起来,同时也在探索.攻克更多的技术问题,并抽空写写博客,把相 ...
- 元数据驱动设计 —— 为动态移动应用创建Web API
时间回到多年之前(当时我的头发还没这么稀疏),Google在4月1日这一天发布了Gmail,这不由得令许多人怀疑这个产品是否只是Google精心炮制的一个玩笑.但谁又能够去指责他们的怀疑呢?毕竟整个互 ...
最新文章
- 马斯克的脑机接口能如愿以偿吗?
- python接入微信公众号_Python学习之微信公众号接入 一 验证
- Funny:还是程序猿会玩——弹幕炸天学AI和区块链,玩起来!弹慕君,你也值得拥有!
- 【论文解读】这篇顶会paper,讲述了疫情期间憋疯的你和我
- Flask 生成下载文件
- 采用开源方案的优势--从搭建WebGIS系统说起
- GARFIELD@12-30-2004
- mysql执行语句后回退_MySQL命令学习笔记(八)
- 2017.9.22 松鼠的聚会 失败总结
- Node.js ORM 框架 Sequelize 重要更新 v5 发布
- python如何解析xml请求 http_怎么用python处理xml请求和xml响应,wsdl, soap,希望有源码参考。...
- 统计信号处理基础-估计与检测理论的学习过程
- Nodejs+express+vue网上零食购物网站系统
- python毕业设计作品基于django框架 二手物品交易系统毕设成品(6)开题答辩PPT
- 斗牛(牛牛)概率计算器
- 简易波形发生器通过单片机的Proteus仿真
- linux poodle漏洞,Claws Mail 3.11.0发布 修复了POODLE 漏洞
- pythonmatplotlib绘图小提琴_python 箱线图和小提琴图
- 从循环条件的代码里,我能在面试中甄别程序员是否是高级
- 【Procmon教程2】如何揪出篡改注册表的元凶?
热门文章
- Tcl 语言 ——变量篇
- Paxos算法和Raft算法
- 分布式系统(2)——Paxos算法
- 大话Seq2Seq模型
- 【CS224n】(lecture1)课程介绍和word2vec
- 电子科技大学成都学院计算机考研,电子科大成都学院又双叒叕现学霸寝室,室友全考上研究生...
- 【Adobe Premiere Pro 2020】pr模板下载和pr使用模板创建视频、pr调色说明、pr全景视频编辑说明、pr无缝转场特效制作流程、pr保存预设效果和pr使用预设效果
- linux(ubuntu)下安装postgresql+pgAdmin4
- HTTP报文-请求方式
- 常用高性价比的LCD液晶屏驱动芯片VK1088B