RESTful API浅谈

http://www.javashuo.com/article/p-kozeqets-my.htmlhtml


上半年时候,部门有组织的讨论了一下实践微服务的技术话题,主要内容是SOA服务和微服务各自的优点和难点,其中有提到关于RESTful API设计方法。git

正好最近在深刻的学习HTTP协议,也看了一些有关RESTful API的资料,这篇博客,就将本身的一些理解整理记录一下。github

PS:本篇博客主要谈一些概要的设计思想和方法,不谈具体的实现细节,若有偏差欢迎指出,谢谢!shell

想进一步了解RESTful API,建议学习下面列出的一些词条:数据库

HTTP协议、分布式系统架构原理(CAP)、操做系统原理。。。后端

参考资料:api

跟着Github学习RESTful HTTP API设计缓存

一种RESTful API接口的约定安全

RESTful API设计最佳实践服务器

知乎:如何用通俗易懂的语言解释RESTful API?

 

1、REST的由来

全称:REST,全称是Resource Representational State Transfer,即:资源在网络中以某种形式进行状态转移。————所谓状态的转移,可参考《HTTP权威指南》一书中对协议的详细解释,此处不过多赘述!

出现:REST最先是由Roy Fielding博士发表的论文中提到的,他也曾参与设计了HTTP协议。论文地址:http://www.ics.uci.edu/~fielding/pubs/dissertation/top.htm

定义:简单来讲REST是一种系统架构设计风格(而非标准),一种分布式系统的应用层解决方案。

背景:早期的网页端是先后台一块儿的,好比PHP、JSP等。而随着近几年移动端的快速发展和分布式架构的应用,各类Client层出不穷,这个时候就须要有个统一的机制,来为先后端通讯提供服务。

     而RESTful API就是目前比较成熟的的一套应用程序API设计理论。

目的:Client和Server端进一步解耦。

应用:最为经典的莫过于github API。

 

2、RESTful的特征和优势

一、客户端-服务器(Client-Server):提供服务的服务器和使用服务的客户端分离解耦;

   优势:提升客户端的便捷性(操做简单)

        简化服务器提升可伸缩性(高性能、低成本)

        容许客户端服务端分组优化,彼此不受影响

二、无状态(Stateless):来自客户的每个请求必须包含服务器处理该请求所需的全部信息(请求信息惟一性);

   优势:提升可见性(能够单独考虑每一个请求)

        提升可靠性(更容易故障恢复)

        提升了可扩展性(下降了服务器资源使用)

三、可缓存(Cachable):服务器必须让客户端知道请求是否能够被缓存?若是能够,客户端能够重用以前的请求信息发送请求;

   优势:减小交互链接数

        减小链接过程的网络时延

四、分层系统(Layered System):容许服务器和客户端之间的中间层(代理,网关等)代替服务器对客户端的请求进行回应,而客户端不须要关心与它交互的组件以外的事情;

   优势:提升了系统的可扩展性

        简化了系统的复杂性

五、统一接口(Uniform Interface):客户和服务器之间通讯的方法必须是统一化的。(例如:GET,POST,PUT.DELETE)

   优势:提升交互的可见性

        鼓励单独优化改善组件

六、支持按需代码(Code-On-Demand,可选):服务器能够提供一些代码或者脚本并在客户的运行环境中执行。

   优势:提升可扩展性

 

3、概要设计方法

一、协议

API与Client的通讯协议,老是使用HTTPS协议。

PS:使用HTTPS协议和RESTful API自己没有多大关系,可是对于增长网站的安全是很是重要的,特别是若是提供的是公开的API,那么HTTPS久更显得重要了。

二、域名

应该尽可能将API部署在专用的域名下面,好比:

 https://api.github.com 

若是API变化较大,能够把API设计为子域名,好比:

 https://example.com/api/v1 

三、版本(Versioning)

通常而言应该将API放入URL中,好比:

 https://example.com/api/v1 

还能够将版本号放入HTTP信息头中,但这样不如放入URL方便和直观。

四、路径(Endpoint)

在协议中,每一个网址表明一种资源的存放地址,因此网址终不能有动词,只能有名词,并且名词通常都应该与数据库的表字段对应,且API中的名词应该使用复数。例如:

/users/:username/repos/users/:org/repos/repos/:owner/:repo/repos/:owner/:repo/tags/repos/:owner/:repo/branches/:branch

PS:根据RFC3986定义,URL是大小写敏感的,因此应该尽可能使用小写字母来命名!

五、方法(Method)

有了资源的URL设计,全部针对资源的操做都是使用HTTP方法指定的,常见的方法有(括号中为对应的SQL命令):

Verd 描述
HEAD(SELECT) 只获取某个资源的头部信息
GET(SELECT) 获取资源
POST(CREATE) 建立资源
PATCH(UPDATE) 更新资源的部分属性(不多用,通常用POST代替)
PUT(UPDATE) 更新资源,客户端须要提供新建资源的全部属性
DELETE(DELETE) 删除资源

好比:

GET /user:列出全部的用户POST /user:新建一个用户PATCH /user/ID:更新某个指定用户的信息DELETE /user/ID:删除全部用户

六、数据过滤(Filtering)

若是数据量太大,服务器不可能将全部数据返回给用户。API应该提供参数(好比Query),过滤返回结果。好比:

?limit=10:指定返回记录的数量?offset=10:指定返回记录的开始位置?page=2&per_page=100:指定第几页,以及每页的记录数?sortby=name&order=asc:指定返回结果按照哪一个属性排序,以及排序顺序?state=close:指定筛选条件

七、状态码

在HTTP报文构成中,有个字段很重要:status code。它说明请求的大体状况,是否正常处理、出现了什么错误等。状态码都是三位数,大概分为了一下几个区间:

状态码 描述
2XX 请求正常处理并返回
3XX 重定向,请求的资源位置发生变化
4XX 客户端发送的请求有误
5XX 服务器端的错误

关于状态码,具体的介绍能够去我以前的博客HTTP状态码或者参考其余资料,这里不过多赘述。

八、错误处理

若是出错的话,在response body中应经过message字段,以键值对的格式,给出明确的错误信息。

最基本的思路应该是:尽量提供准确的错误信息,好比数据格式不正确、缺乏某个字段......而不是直接说“请求错误”之类的信息。

九、Hypermedia API

Restful API的设计最好作到Hypermedia:即在返回结果中提供相关资源的连接,连向其余API方法,使用户不须要查文档也知道下一步作什么。

这样作的好处是,用户能够根据返回结果就能获得后续操做须要访问的地址。

十、身份验证

通常来讲,让任何人随意访问公开的 API 是很差的作法,验证和受权是两件事情:

验证(Authentication):肯定用户是其申明的身份,好比提供帐户的密码。否则的话,任何人伪形成其余身份(好比其余用户或者管理员)是很是危险的;

受权(Authorization):保证用户有对请求资源特定操做的权限。好比用户的私人信息只能本身能访问,其余人没法看到;有些特殊的操做只能管理员能够操做,其余用户有只读的权限等。

若是没有经过验证,须要返回401 Unauthorized状态码,并在 body 中说明具体的错误信息;而没有被受权访问的资源操做,须要返回403 Forbidden状态码,还有详细的错误信息。

PS:Github API 对某些用户未被受权访问的资源操做返回404 Not Found,目的是为了防止私有资源的泄露(好比***能够自动化试探用户的私有资源,返回 403 的话,就等于告诉***用户有这些私有的资源)。

十一、编写文档

API最终是给人使用的,不管是对内仍是对外,即便遵循上面提到的全部规则,API设计的很优雅,但有时候用户仍是不知道该如何使用这些提供的API。

所以,编写清晰可读的文档是很必要的事情。

并且编写文档也能够做为产出物的一部分,以及用来作记录,以方便查询参考。

相关文章
相关标签/搜索