REST API
问题
最近在项目中单独负责一个组件的开发,这个组件的输出是通过api的方式输出。虽然接口不多,也就15个api左右,但是越往后写就越感觉不太对劲。在和同时联调沟通的时候也发现了很多的问题。一直都想要好好总结下,趁着今天下班早有时间就反思一下吧。
我总结了目前我发现的这个项目的一些问题
- API风格混乱
- API设计不好,不能更加友好的支持API升级
- 返回状态码的滥用
- 接口返回数据结构不一致
- 接口太碎片化
- 由于是go语言写的,基本每个接口都用到了defer
站在现在的角度来看,其实这个组件的api是想当失败,可以说是不忍直视。当然有一小部分原因是项目紧急的缘故。但是不可否认的是主要还是因为我的原因才导致了这样的结果。所以我决定新开一个分支,在下班时间重构这个组件的API。虽然这个新重构后的API上线的可能性不大(因为好多项目已经集成了该组件,改动起来花费的资源很大)。但也算是对自己的一个交代吧。
自己算了算之前也参与过三个项目相关业务API的开发。但是都是在别人的基础上进行开发,看到别人没有过多的去关注这些东西。所以自己也就自然而然的没有过多的去思考,就顺着那种思路开发下去了。总之该来的还是会来的。这次的更改可能对这个组件起不了多大的作用。但是希望能够给自己敲响警钟,避免下次出现同样的问题。
REST API的一些规范
实现REST API标准比较好的例子就是https://developer.github.com/v3/#current-version
-
在API中指定版本
一种是可以放在url中,另外一种就是将版本放在HTTP请求头中。还是放在url中比较方便
-
url中不能出现动词,名词也应该使用复数
因为RESTful面向的都是资源,所以在url中不能包含动词。
-
对资源的操作都是用HTTP动词
常用到的HTTP动词
动词 作用 返回结果 GET 从服务器获取资源 获取单个资源对象或者资源对象数组 POST 新建资源 新生成的资源对象 PUT 更新整个对象,需要客户端提供完整的对象 更新后的资源对象 PATCH 更新对象的某个部分,需要客户端提供更新的部分 更新后的资源对象 DELETE 删除整个对象 返回一个空文档
一些例子
GET /zoos:列出所有动物园
POST /zoos:新建一个动物园
GET /zoos/ID:获取某个指定动物园的信息
PUT /zoos/ID:更新某个指定动物园的信息(提供该动物园的全部信息)
PATCH /zoos/ID:更新某个指定动物园的信息(提供该动物园的部分信息)
DELETE /zoos/ID:删除某个动物园
GET /zoos/ID/animals:列出某个指定动物园的所有动物
DELETE /zoos/ID/animals/ID:删除某个指定动物园的指定动物
-
过滤信息
一些例子
?limit=10:指定返回记录的数量 ?offset=10:指定返回记录的开始位置。 ?page=2&per_page=100:指定第几页,以及每页的记录数。 ?sortby=name&order=asc:指定返回结果按照哪个属性排序,以及排序顺序。 ?animal_type_id=1:指定筛选条件其中 GET /zoo/ID/animals 与 GET /animals?zoo=ID都是REST的风格。一直都以为只有第一种才是
-
状态码
200 OK - [GET]:服务器成功返回用户请求的数据,该操作是幂等的(Idempotent)。 201 CREATED - [POST/PUT/PATCH]:用户新建或修改数据成功。 202 Accepted - [*]:表示一个请求已经进入后台排队(异步任务) 204 NO CONTENT - [DELETE]:用户删除数据成功。 400 INVALID REQUEST - [POST/PUT/PATCH]:用户发出的请求有错误,服务器没有进行新建或修改数据的操作,该操作是幂等的。 401 Unauthorized - [*]:表示用户没有权限(令牌、用户名、密码错误)。 403 Forbidden - [*] 表示用户得到授权(与401错误相对),但是访问是被禁止的。 404 NOT FOUND - [*]:用户发出的请求针对的是不存在的记录,服务器没有进行操作,该操作是幂等的。 406 Not Acceptable - [GET]:用户请求的格式不可得(比如用户请求JSON格式,但是只有XML格式)。 410 Gone -[GET]:用户请求的资源被永久删除,且不会再得到的。 422 Unprocesable entity - [POST/PUT/PATCH] 当创建一个对象时,发生一个验证错误。 500 INTERNAL SERVER ERROR - [*]:服务器发生错误,用户将无法判断发出的请求是否成功。 -
返回结果
GET /collection:返回资源对象的列表(数组) GET /collection/resource:返回单个资源对象 POST /collection:返回新生成的资源对象 PUT /collection/resource:返回完整的资源对象 PATCH /collection/resource:返回完整的资源对象 DELETE /collection/resource:返回一个空文档 -
Hypermedia API
个人认为这个在公司这种项目中是可以省略的,毕竟公司项目中的API都是面向特定的用户,而且有安全限制,不会把所有的API都暴露出去。
-
API的用户认证使用OAuth 2.0框架
这个单独拿出来写一写
其实RESTful规范也不多,在实际中除非有特殊情况,都要尽量的遵守规范。
参考链接: