API开发与管理规范v1.0
1. 协议规范
为了确保不同业务系统之间以及前后端的的数据交互的快捷性,通讯协议统一约定如下:
- 对内调用的API接口统一使用 HTTP协议
- 对外互联网发布的API建议使用HTTPS协议也可以使用HTTP
- 新的API接口必须使用标准的HTTP报文并使用JSON作为统一的数据传送标准
- 如无特殊情况禁止在新开发的API接口中使用XML格式传送数据,统一使用JSON格式作为数据包或者form键值对模式数据包。
- 请求输入输出数据要求诮遵循JSON 格式规范,优先采用小驼峰式的字段命名规范。
2. Method规范
- 在接口路径规范阅读之前必须先定义好Method规范,虽然Restful风格建议使用get、post、delete、put来区分和操作不同的资源,但是在实际项目开发的过程中全部使用Restful风格往往会造成开发效率的降低,而且在资源较多时API命名将给开发人员造成很大的困扰。
- 我们建议在Http Method标准上只允许使用get和post方法,禁止使用delete和put方法,很多企业和安全扫描工具不允许开放delete和put方法,有些web防火墙默认会拦载delete和put方法的请求。
- 使用了delete和put方法后tomcat安装后还需要进行配置才能支持此两种方法,delete和put方法在键值对提交模式下后端servlet接收参数必须要自已从流中接收开发难度增大。
- 前端使用delete和put方法时没有get和post快捷。
- 我们建议在API开发时只允许使用get和post方法,delete和update则放在url中。
- 更新用户使用:POST /appid/users/update
- 删除用户使用:POST /appid/users/delete
3. 安全性和幂等性
- 安全性:不会改变资源状态,可以理解为只读的,输入相同参数的情况下总是能查出相同的内容
- 幂等性:执行1次和执行N次,对资源状态改变的效果是等价的,适于用参与事务的API必须要具有幂等性的API
. | 安全性 | 幂等性 |
---|---|---|
GET | 底 | √ |
POST | 高 | 参与事务时必须支持 |
POST提交的API如果参与到API服务编排平台中时如果要支持补偿或事务时则必须支持幂等性,否则API服务编排平台在进行事务补偿执行时有可能会发生多次重复数据写入的可能。
4. 接口路径规范
API接口路径规范的原则是能从路径中清析的查看到此API所属的业务领域或应用,appid必须先在RestCloud平台中建立。
- 路径中必须包含所属的appid应用编号示例:/appid/api/delete
- 路径中的变量参数应尽量放在最后示例:
/appid/users/{id} 正确
错误: /appid/{id}/users
在RestCloud平台中路径变量越靠后性能越好,越靠前则所能匹配到的url会越多,系统需要一层一层分析比对才能最终确定所调用的API,在如果路径中没有{}变量的情况下,url的长短并不影响性能,但是过长的url不便于阅读。
- 如果路径中包含API的版本号,版本号应位于/appid/后面
正确示例:/appid/v1/api/update
错误示例:/v1/appid/api/query
- 路径中的所有字母建议使用小写,词语之间的分隔可以使用/路径或者_下划线,而不要在URL中使用驼峰格式,因为URL是区分大小写的,所以全部小写是比较好的策略。
正确示例:/appid/v1/user/username_info
错误示例:/appid/v1/user/usernameInfo
- 定义自定义路径部分时,使用名词的复数形式定义一个资源,如若有动词词性在url中考虑以下划线区分,在使用动词为前/后缀时,常见动词有:add、delete、update、query、get、send、save、detail、list等.
- 基本操作示例
GET /users 获取用户列表
GET /users/{userId} 查看某个具体的用户信息
POST /users/update 新建或更新一个用户
POST /users/delete 删除某一个用户信息
GET /users/search 搜索用户
- 避免层级过深的URI
/在url中表达层级,用于按实体关联关系进行对象导航,一般根据id导航。过深的导航容易导致url膨胀,不易维护,如 GET /zoos/1/areas/3/animals/4,可以尽量使用查询参数代替路径中的实体导航,如GET /animals?zoo=1&area=3;
- 对资源访问时的URL约定
服务器端的资源组合实体建议在uri中通过父实体的id导航访问,组合实体不是主实体,它的生命周期完全依赖父实体,无法独立存在,在实现上通常是对数据库表中某些列的抽象,不直接对应表,也无id。一个常见的例子是 User — Address,Address是对User表中zipCode/country/city三个字段的简单抽象,无法独立于User存在,则获取address的api的url为:
GET /user/addresses
5. 请求参数规范
请求参数字段,尽可能与数据库表字段、对象属性名等保持一致,因为保持一致最省事,最简单,对于敏感数据或安全性较高的API则可以与数据库字段或对像不一致。
分页参数约定:
当前页统一使用:pageNo参数
每页显示数统一使用:pageSize参数
搜索关键字统一使用:keywords参数
排序:?sort=age,desc
传入参数共分为 3 种类型
- 地址栏参数
restful 地址栏参数 /api/v1/product/00123 00123为产品编号,获取产品为 00123 的信息,其他示示例用法:
get 方式的查询字串,此种方式主要用于过滤查询,如下:
?limit=10:指定返回记录的最大数量
?pageNo=2&pageSize =100:指定第几页,以及每页的记录数。
?sortby=name&order=asc:指定返回结果按照哪个属性排序,以及排序顺序。
?producy_type=1:指定筛选条件
- 请求 body 数据
主要用于提交新建数据等,get请求应使用url参数,而非json 格式,post请求数据为RequestBody时请使用标准的JSON数据作为请求格式如下:
{
“userName”:”admin”, //认证token
“age”:”123”
}
- 请求头
用于存放请求格式信息、版本号、token 密钥、语言等信息。请求头根据项目需求添加配置参数。如:请求数据格式,accept=‘application/json’等。如有需要,请求头可根据项目需求要求传入用户token、唯一验签码等加密数据。
- 请求示例
对于Body请求的参数API接口必须提供JSON请求示例和返回示例,否则API的调用者很难知道Body参数的格式。
6. 返回数据规范
统一规范返回数据为json格式,返回数据应包含:返回状态码、返回状态信息、具体数据等。
格式规范如下:
{
"state":true, //表示成功,false表示失败
"msg":"success",
“ercode”:500 //如果有错误时返回错误状态码
"data": {
//json格式的具体数据
}
}
分页格式规范如下:
{
"state":true, //表示成功,false表示失败
"msg":"success",
“ercode”:500 //如果有错误时返回错误状态码
page:{//分布对象格式
"pageNo":1, //当前页码
"totalPages":1, //总页码
"pageSize":20, //分页大小
"total":2, //总记录数
}
"data": {
//json格式的具体数据
}
}
API执行过程中禁止发生了错误但给2xx响应,客户端可能会缓存成功的http请求;
正确设置http状态码,不要自定义;
Response body 提供
-
错误的代码(可协助用于进行日志/问题追查的编码);
-
错误的描述文本(展示给用户的提示信息);
-
API 可能抛出两类异常:业务异常和非业务异常。业务异常由自己的业务代码抛出,表示一个用例的前置条件不满足、业务规则冲突等,比如参数校验不通过、权限校验失败。非业务类异常表示不在预期内的问题,通常由类库、框架抛出,或由于自己的代码逻辑错误导致,比如数据库连接失败、空指针异常、除0错误等等,业务类异常统一设置 HTTP 响应状态码为:500;
7. 数据大小约定
单个API的请求及响应数据严格上不建议超过10M,超过10M的数据会严重影响网络以及JSON的序列化性能,如果超过10M的数据建议使用分页传输。
8. API超时时间约定
API的响应时间一般不建议超过180S即3分钟,如果时间太久会影响API网关性能,同时也容易出现问题,如果超过3分钟以上的API链接时间可以使用MQ等方式进行数据传输。