1.HTTP简介

http协议是一种超文本传输协议,主要应用在浏览器与服务器之间的通信,可以传输文本,图片,视频等。它是一种应用层协议,也是基于TCP协议,当然现在流行的Https协议是在TLS或SSL协议层上面。如下图所示:

http协议详解之请求篇(详解HTTP协议与RESTFUL)(1)

HTTP是一个应用层协议,是一个无状态协议,默认端口号是80.,HTTPS端口号为443。

HTTP的特性:

(1) 协议简单,只用传递请求方法和路径,程序规模小,通信速度快。

(2)可以指定传输类型,由Content-Type标记。

(3)HTTP0.9 和 1.0使用非持续连接,每次处理完请求,并收到客户端响应后,就断开连接。HTTP1.1是使用持续连接,一个连接可以传送多个对象,可以节省时间,由于负载多,真实数据少,实际网络带宽利用率不高,类似心跳包,所以这种对于带宽来说,实际利占用带宽并没有想象中高。

(4)HTTP是无状态协议,意味着如果要处理前面的信息,则必须重传,可能导致每次连接数据量增多,相反,这个时候不需要先前信息,响应比较快。

2.HTTP工作流程

(1).首先客户端与服务器之间建立连接,个 HTTP 客户端,通常是浏览器,与 Web 服务器的 HTTP 端口(默认为 80)建立一个 TCP套接字连接。例如http://www.baidu.com

(2).客户端发送请求给服务器,请求格式:URL,协议版本号,MIME信息包括修饰符,客户机信息,可能的内容。

(3).服务器收到请求,并给予回复,回复格式:状态行,协议版本,状态码,状态信息,后面包括服务器信息,实体信息和可能的内容。

(4).客户端并把接收到的信息,通过浏览器展示,然后客户机与服务器断开连接。

(5)客户端浏览器解析HTML内容。浏览器首先解析状态行,请求是否成功的状态码,解析每个响应头,可以查看下面的数据类型,如HTML文档和字符集,客户端浏览器读取响应HTML,然后根据HTML语言进行格式化,并在浏览器窗口中显示。

请求消息主要包括以下格式:

请求行,请求头,空行,数据。如下图:

http协议详解之请求篇(详解HTTP协议与RESTFUL)(2)

如通过Get请求方法:

GET /teacher_6.jpg HTTP/1.1

Host:www.baidu.com

User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, lik

e Gecko) Chrome/81.0.4044.113 Safari/537.36

Content-Type: application/x-www-form-urlencoded

Content-Length: 9

xxxx

第一部分:请求行,用来说明请求类型,要访问的资源以及所使用的 HTTP 版本。[/teacher_6.jpg]为要访问的资源,HTTP/1.1是协议版本。

第二部分:请求头部,主要是一些附加信息,使用key-value的形式展现。该信息由你的浏览器来定义,并且在每个请求中自动发送等。

第三部分:空行,请求头部后面的空行是必须的。

为什么是必须的呢?

空行实际就是\r\n\r\n,http协议也是基于tcp,tcp的粘包与分包,是通过包长度或结尾标识来设计,所以就用\r\n\r\n来隔离头部和真实数据,头部和数据包是可以一起发的,但是接收好,头部和数据是可以分开处理。

第四部分:请求数据也叫主体,可以添加任意的其他数据。

HTTP响应消息Response

HTTP 响应也由四个部分组成,分别是:状态行、消息报头、空行和响应正文。

http协议详解之请求篇(详解HTTP协议与RESTFUL)(3)

第一部分:状态行,由HTTP协议版本号,状态码,状态消息,3部分构成

第二部分为消息报头,说明客户端的一些附加信息。

第二行,第三行,第四行均为消息报头。

Date:生成响应的日期和时间;Content-Type:指定了 MIME 类型的 HTML(text/html),编码类型是ISO-8859-1。

第三部分:空行,消息报头后面的空行是必须的。

第四部分:响应正文,服务器返回给客户端的文本信息。空行后面的 html 部分为响应正文。

3.HTTP请求方法

HTTP1.0 定义了三种请求方法: GET、POST 和 HEAD 方法。

HTTP1.1 新增了六种请求方法: OPTIONS、PUT、PATCH、DELETE、TRACE 和 CONNECT 方法。

序号 方法 描述

(1) GET 请求指定的页面信息,并返回实体主体。

(2) HEAD 类似于 GET 请求,只不过返回的响应中没有具体的内容,用于获取

报头

(3)POST 向指定资源提交数据进行处理请求(例如提交表单或者上传文件)。

数据被包含在请求体中。POST 请求可能会导致新的资源的建立和/

或已有资源的修改。

(4)PUT 从客户端向服务器传送的数据取代指定的文档的内容。

(5)DELETE 请求服务器删除指定的页面。

(6)CONNECT HTTP/1.1 协议中预留给能够将连接改为管道方式的代理服务器。

(7)OPTIONS 允许客户端查看服务器的性能。

(8)TRACE 回显服务器收到的请求,主要用于测试或诊断。

(9)PATCH 是对 PUT 方法的补充,用来对已知资源进行局部更新 。

GET、POST区别

(1)GET提交的数据放在URL之后,以?分割URL和传输数据,参数间以&相连,如http://localhost:8600/user?name=test1&id=123456。POST方法是把提交的数据放在HTTP的Body中。

(2)GET 提交的数据大小有限制(因为浏览器对 URL 的长度有限制),而 POST 方法提交的数据没有限制.

(3) GET 方式需要使用 Request.QueryString 来取得变量的值,而 POST 方式通过 Request.Form来获取变量的值。

(4) GET 方式提交数据,会带来安全问题,比如一个登录页面,通过 GET 方式提交数据时,用户名和密码将出现在 URL 上,如果页面可以被缓存或者其他人可以访问这台机器,就可以从历史记录获得该用户的账号和密码。

4.响应头信息

http协议详解之请求篇(详解HTTP协议与RESTFUL)(4)

http协议详解之请求篇(详解HTTP协议与RESTFUL)(5)

http协议详解之请求篇(详解HTTP协议与RESTFUL)(6)

http协议详解之请求篇(详解HTTP协议与RESTFUL)(7)

http协议详解之请求篇(详解HTTP协议与RESTFUL)(8)

http协议详解之请求篇(详解HTTP协议与RESTFUL)(9)

http协议详解之请求篇(详解HTTP协议与RESTFUL)(10)

http协议详解之请求篇(详解HTTP协议与RESTFUL)(11)

http协议详解之请求篇(详解HTTP协议与RESTFUL)(12)

http协议详解之请求篇(详解HTTP协议与RESTFUL)(13)

http协议详解之请求篇(详解HTTP协议与RESTFUL)(14)

HTTP状态码:

第一个数字定义了响应的类别,共分五种类别:

1xx:指示信息--表示请求已接收,继续处理

2xx:成功--表示请求已被成功接收、理解、接受

3xx:重定向--要完成请求必须进行更进一步的操作

4xx:客户端错误--请求有语法错误或请求无法实现

5xx:服务器端错误--服务器未能实现合法的请求

http协议详解之请求篇(详解HTTP协议与RESTFUL)(15)

http协议详解之请求篇(详解HTTP协议与RESTFUL)(16)

http协议详解之请求篇(详解HTTP协议与RESTFUL)(17)

http协议详解之请求篇(详解HTTP协议与RESTFUL)(18)

http协议详解之请求篇(详解HTTP协议与RESTFUL)(19)

http协议详解之请求篇(详解HTTP协议与RESTFUL)(20)

http协议详解之请求篇(详解HTTP协议与RESTFUL)(21)

http协议详解之请求篇(详解HTTP协议与RESTFUL)(22)

http协议详解之请求篇(详解HTTP协议与RESTFUL)(23)

HTTP Content-Type:

内容类型,一般指网页中存在的Content-Type,定义网络文件类型和编码,决定浏览器以什么形式,什么编码读取这个文件。就决定了网页点击的结果却是下载一个文件或一张图片的原因。告诉客户端实际返回的内容的内容类型。

http协议详解之请求篇(详解HTTP协议与RESTFUL)(24)

text/html : HTML 格式

text/plain :纯文本格式

text/xml : XML 格式

image/gif :gif 图片格式

image/jpeg :jpg 图片格式

image/png:png 图片格式

以 application 开头的媒体格式类型:

application/xhtml xml :XHTML 格式

application/xml: XML 数据格式

application/atom xml :Atom XML 聚合格式

application/json: JSON 数据格式

application/pdf:pdf 格式

application/msword : Word 文档格式

application/octet-stream : 二进制流数据(如常见的文件下载)

application/x-www-form-urlencoded : <form encType=””>中默认的 encType,form 表单数据

被编码为 key/value 格式发送到服务器(表单默认的提交数据的格式)

ultipart/form-data : 需要在表单中进行文件上传时,就需要使用该格式。

http协议详解之请求篇(详解HTTP协议与RESTFUL)(25)

http协议详解之请求篇(详解HTTP协议与RESTFUL)(26)

http协议详解之请求篇(详解HTTP协议与RESTFUL)(27)

http协议详解之请求篇(详解HTTP协议与RESTFUL)(28)

http协议详解之请求篇(详解HTTP协议与RESTFUL)(29)

http协议详解之请求篇(详解HTTP协议与RESTFUL)(30)

http协议详解之请求篇(详解HTTP协议与RESTFUL)(31)

http协议详解之请求篇(详解HTTP协议与RESTFUL)(32)

http协议详解之请求篇(详解HTTP协议与RESTFUL)(33)

http协议详解之请求篇(详解HTTP协议与RESTFUL)(34)

http协议详解之请求篇(详解HTTP协议与RESTFUL)(35)

http协议详解之请求篇(详解HTTP协议与RESTFUL)(36)

http协议详解之请求篇(详解HTTP协议与RESTFUL)(37)

http协议详解之请求篇(详解HTTP协议与RESTFUL)(38)

http协议详解之请求篇(详解HTTP协议与RESTFUL)(39)

http协议详解之请求篇(详解HTTP协议与RESTFUL)(40)

http协议详解之请求篇(详解HTTP协议与RESTFUL)(41)

http协议详解之请求篇(详解HTTP协议与RESTFUL)(42)

http协议详解之请求篇(详解HTTP协议与RESTFUL)(43)

5.HTTP链接

当单击某个链接时,其中<a>标签就会使用类似href属性值,指向一个网络地址<a href="lastpage.html">Last Page</a>。一个完整的网址遵循以下规则:

protocol、host、port、path、parameter、anchor。

scheme://host.domain:port/path/filename

Scheme 定义因特网服务的类型。最流行的类型是 http。

domain(域)定义因特网域名,比如:3wschool.com.cn。

host(主机)定义此域中的主机。如果被省略,缺省的支持 http 的主机是 www。

:port(端口)定义主机的端口号。端口号通常是被省略的。缺省的端口号是 80。

path(路径)定义服务器上的路径(一个辅助的路径)。如果路径被省略,则资源会被定位到网站的根目录。

filename是文档名称,缺省的文件名一般是default.jsp或index.html,根据web服务器设置的其它文件名。

大部分URL遵循一种标准格式,该格式包括三个部分;

(1)以怎样的方式访问资源

(2)服务器的位置,客户端资源在何处

(3) 指定服务器上某个特定资源

大多数 URL 的语法都建立在下面 9 个部分构成的通用格式上:

<scheme>://<user>:<password>@<host>:<port>/<path>;<params>?<query>#<frag>

其中最重要的 3 个部分是:方案(scheme)、主机(host)和路径(path)

6.RESTful

REST 指的是一组架构约束条件和原则。" 如果一个架构符合 REST 的约束条件和原则,就称它为 RESTful 架构。隐藏在 RESTful 背后的理念就是使用 Web的现有特征和能力,更好地使用现有 Web 标准中的一些准则和约束。虽然 REST 本身受 Web技术的影响很深, 但是理论上 REST 架构风格并不是绑定在 HTTP 上,只不过目前 HTTP 是唯一与 REST 相关的实例。 所以我们这里描述的 REST 也是通过 HTTP 实现的 REST。

关于REST原则,从以下这几个方面去理解。

资源与 URI

统一资源接口

资源的表述

资源的链接

状态的转移

资源与 URI

资源可以是实体(例如手机号码),也可以只是一个抽象概念(例如价值) 。下面是一些资源的例子:

某用户的手机号码

某用户的个人信息

最多用户订购的 GPRS 套餐

两个产品之间的依赖关系

某用户可以办理的优惠套餐

URI(Uniform Resource Identifier)就是标识资源,并且是唯一标识。URI 既可以看成是资源的地址,也可以看成是资源的名称。如果某些信息没有使用 URI 来表示,那它就不能算是一个资源, 只能算是资源的一些信息而已。以 github 网站为例,给出一些还算不错的 URI:

https://github.com/git

https://github.com/git/git

https://github.com/git/git/blob/master/block-sha1/sha1.h

https://github.com/git/git/commit/e3af72cdafab5993d18fae056f87e1d675913d08

https://github.com/git/git/pulls

https://github.com/git/git/pulls?state=closed

https://github.com/git/git/compare/master…next

统一资源接口

RESTful 架构应该遵循统一接口原则,统一接口包含了一组受限的预定义的操作,不论什么

样的资源,都是通过使用相同的接口进行资源的访问。如使用GET,PUT,POST,并遵循这些方法的语义。

RESTful 架构的主要原则

网络上的所有事物都被抽象为资源。

每个资源都有一个唯一的资源标识符。

同一个资源具有多种表现形式(xml,json 等)。

对资源的各种操作不会改变资源标识符。

所有的操作都是无状态。

符合 REST 原则的架构方式即可称为 RESTful。

REST 主要对以下两方面进行了规范

定位资源的URL风格,如

https://www.baidu.com/v/web/first/course

https://www.baidu.com/v/web/second/course

采用HTTP协议规定的GET、POST、PUT、DELETE动作处理资源的增删改查操作。

http协议详解之请求篇(详解HTTP协议与RESTFUL)(44)

RESTful API 设计

API 与用户的通信协议,总是使用 HTTPs 协议。尽量将 API 部署在专用域名之下,https://api.example.com,如果API很简单,不会有进一步扩展,可以考虑放在主域名下。https://example.org/api/

版本

应该将 API 的版本号放入 URL。

https://api.example.com/v1/

另一种做法是,将版本号放在 HTTP 头信息中,但不如放入 URL 方便和直观。Github 采用这

种做法。

路径(Endpoint)

表示 API 的具体网址。在 RESTful 架构中,所用的名词往往与数据库的表格名对应。一般来说,数据库中的表都是同种记录的"集合"(collection)。

如通过API提供动物园信息,包括动物和雇员信息,则路径应该设计成如下:

https://api.example.com/v1/zoos

https://api.example.com/v1/animals

https://api.example.com/v1/employe

常用的 HTTP 动词有下面五个(括号里是对应的 SQL 命令)。

GET(SELECT): 从服务器取出资源(一项或多项)。

POST(CREATE): 在服务器新建一个资源。

PUT(UPDATE): 在服务器更新资源(客户端提供改变后的完整资源)。

PATCH(UPDATE): 在服务器更新资源(客户端提供改变的属性)。

DELETE(DELETE): 从服务器删除资源。

还有两个不常用的 HTTP 动词。

HEAD: 获取资源的元数据。

OPTIONS: 获取信息,关于资源的哪些属性是客户端可以改变的。

举例说明:

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: 删除某个指定动物园的指定动物

过滤信息(Filtering)

如果记录数量很多,服务器不可能都将它们返回给用户。API 应该提供参数,过滤返回结果。下面是一些常见的参数

?limit=10:指定返回记录的数量。

?offset=10:指定返回记录的开始位置。

?page=2&per_page=100:指定第几页,以及每页的记录数。

?sortby=name&order=asc:指定返回结果按照哪个属性排序,以及排序顺序。

?animal_type_id=1:指定筛选条件

允许 API 路径和 URL 参数偶尔有重复。比如,GET /zoo/ID/animals与 GET /animals?zoo_id=ID 的含义是相同的。

错误处理(Error handling)

如果状态码是 4xx,就应该向用户返回出错信息。一般来说,返回的信息中将 error 作为键名,出错信息作为键值即可。

{

error: "Invalid API key"

}

返回结果

针对不同操作,服务器向用户返回的结果应该符合以下规范。

GET /collection: 返回资源对象的列表(数组)

GET /collection/resource: 返回单个资源对象

POST /collection: 返回新生成的资源对象

PUT /collection/resource: 返回完整的资源对象

PATCH /collection/resource: 返回完整的资源对象

DELETE /collection/resource: 返回一个空文档

Hypermedia API

返回结果中提供链接,连向其他 API 方法,使得用户不查文档,也知道下一步应该做什么。当用户向 api.example.com 的根目录发出请求,会得到这样一个文档。

{ "link": {

"rel": "collection https://www.example.com/zoos",

"href": "https://api.example.com/zoos",

"title": "List of zoos",

"type": "application/vnd.yourformat json"

}

}

link 属性,用户读取这个属性就知道下一步该调用什么 API 了。href 表示 API 的路径,title 表示 API 的标题,type 表示返回类型。

Hypermedia API 的设计被称为 HATEOAS。Github 的 API 就是这种设计,访问 api.github.com会得到一个所有可用 API 的网址列表。

{ "current_user_url": "https://api.github.com/user", "authorizations_url": "https://api.github.com/authorizations", // ... }

如果想获取当前用户的信息,应该去访问 api.github.com/user,然后就得到了下面结果。

{

"message": "Requires authentication",

"documentation_url": "https://developer.github.com/v3"

}

上面代码表示,服务器给出了提示信息,以及文档的网址。

(1) API 的身份认证应该使用 OAuth 2.0 框架。

(2) 服务器返回的数据格式,应该尽量使用 JSON,避免使用 XML。

,