1.http无连接:限制每次连接只处理一个请求,服务端完成客户端的请求后即断开连接(优点:传输速度快,减少不必要的连接。缺点:每一次访问都要建立一次连接,效率降低)
2.http无状态:对事物处理没有记忆能力,每一次请求都是独立的,不记录客户端的任何行为(优点:解放服务器。缺点:每次请求都会传输大量重复的内容信息)
3.客户端/服务端模型:客户端支持web浏览器和其他任何客户端,服务端通常是apache或者iis等
4.简单快速
5.灵活:可以传输任何类型的数据
客户端请求消息
客户端发送一个请求到服务器的请求消息包括以下格式:
请求行,请求头部,空行,请求数据
服务器响应消息:
服务器响应包括如下格式:
状态行,消息报头,空行,响应正文
按照HTTP/1.1 RFC文档中的定义,HTTP报文包括起始行,头域和消息体三个部分。其中起始行又分为请求行和状态行,请求行是HTTP请求中的起始行,它又包含了三个部分:请求方法,请求URI和HTTP协议版本。下面是HTTP请求中的请求方法。
序号 | 方法 | 描述 |
---|---|---|
1 | GET | 像特定资源发出请求,本质上是发送一个请求来请求服务器上的某一个资源。资源通过一组HTTP头和呈现数据(如HTML文本,或者图片或者视频等)返回给客户端。请求体中不会包含请求数据,请求数据放在协议头中。另外GET支持快取、缓存、可保留书签。 |
2 | POST | 与get一样常见,向服务器提交资源让服务器处理,比如提交表单、长传文件等,可能会导致建立新的资源或者对原有资源的修改。提交的资源放在请求体中。不支持快取。 |
3 | HEAD | 本质和get相同,但是响应中没有呈现数据,而是http头信息,主要用来检查资源或超链接的有效性或是否可达、检查网页是否被串改或者更新,获取头信息等,特别适用在有限的速度和带宽下。这一方法可以在不必传输整个响应内容的情况下,就可以获取包含在响应小消息头中的元信息。 |
4 | PUT | 和post类似,html表单不支持,发送资源与服务器,并存储在服务器指定位置,要求客户端事先知道该位置;比如post是在一个集合上(/province),而put是具体某一个资源上(/province/123)。所以put是安全的,无论请求多少次,都是在123上更改,而post可能请求几次创建了几次资源。 |
5 | DELETE | 请求服务器删除某资源。和put都具有破坏性,可能被防火墙拦截。如果是https协议,则无需担心。 |
6 | CONNECT | HTTP/1.1协议中预留给能够将连接改为管道方式的代理服务器。就是把服务器作为跳板,去访问其他网页,然后把数据返回回来,连接成功后,就可以正常的get、post了。 |
7 | OPTIONS | 获取http服务器支持的http请求方法,允许客户端查看服务器的性能,比如ajax跨域时的预检等。 |
8 | TRACE | 回显服务器收到的请求,主要用于测试或诊断。一般禁用,防止被恶意攻击或盗取信息。 |
常见请求方法GET和POST的区别:
GET | POST | |
---|---|---|
点击返回/刷新按钮 | 没有影响 | 数据会重新提交 |
缓存/添加书签 | 可以 | 不可以 |
历史记录 | 有 | 没有 |
编码类型 | application/x-www-form-urlencoded | application/x-www-form-urlencoded 或 multipart/form-data。为二进制数据使用 |
多重编码 | ||
请求体 | get请求无消息体,只能携带少量数据 | post请求有消息体,可以携带大量数据 |
携带数据的方式 | get请求将数据放在url地址中 | post请求将数据放在消息体中 |
是否幂等 | 幂等 | 非幂等 |
长度限制 | http协议没有限制,但是实际浏览器或服务器有(最大2048) | 理论上没有,可能会收到服务器配置或内存限制 |
数据类型限制 | 只能ASCII,非ascii都要编码传输 | 没有限制,允许二进制数据 |
安全性 | 数据全部展示在url中,不安全 | 相比get,通过request body传递数据,比较安全 |
可见性 | 可见 |
在RFC 2068中,讨论了请求方法的两类属性,安全性和幂等性,在RFC 7231中,又增加了方法的可缓存性。
一个安全的请求方法(safe method),指的是这个方法在语义上是只读的,它不会对服务器产生任何预期修改,一个安全的请求(safe request)指的是这条请求的请求方法是安全的。
当客户端对某个资源(URI)执行了一个安全的请求方法,在语义上来说,表示它期望获得一些信息,而不是去主动改变服务端上的数据。对安全方法的合理使用,不应当对服务端产生有害的结果。这里对安全方法的定义特别强调了它是一个语义上的安全,区别于实现安全。站在客户端的角度来看,一个安全的请求应当是只读的,无害的。然而这并不能保证它在服务端的实现就一定是只读的,一个安全的请求方法在实现上可能会对服务器数据进行一些修改,这类修改通常是为了满足一定的业务需求,但如果没有恰当的实现,就可能会产生一些有害的结果。例如,大部分的服务端程序都会将请求信息写入到日志文件中,即使是一个安全的请求方法,仍然会在日志文件中写入这条请求。再比如,用户点击了网页上的一个广告,在产生一个安全的请求的同时,还需要对后台的广告账户进行计费操作。
在数学和计算机科学中,一项操作被称为幂等的表示这项操作执行任意多次和执行一次的结果是完全一样的。例如求绝对值的运算就是幂等的abs(abs(x))≡ abs(x)。
对一个HTTP请求来说,如果一个请求方法多次独立执行和只执行一次对服务器产生的预期效果完全相同,则称这个请求方法是幂等的,同样的,如果一个请求的请求方法是幂等的,则称这个请求是幂等的请求。根据此定义,PUT,DELETE是幂等的方法,此外所有安全的请求方法也都是幂等的。
可缓存的请求方法指的是该方法对应的响应消息能够在客户端被存储,并在之后的请求中被直接使用,而不再需要从服务端重新获取。可缓存的方法有GET,HEAD和POST,但大部分的时候都只实现了GET和HEAD的缓存。
GET :
GET https://testrail-tools.trendmicro.com/portal/admin/getTimerInitStatus HTTP/1.1
Accept: application/json, text/javascript, */*; q=0.01
X-Requested-With: XMLHttpRequest
Referer: https://testrail-tools.trendmicro.com/portal/admin/toLicenseTimerConfig?id=7
Accept-Language: zh-CN
Accept-Encoding: gzip, deflate
User-Agent: Mozilla/5.0 (Windows NT 10.0; WOW64; Trident/7.0; rv:11.0) like Gecko
Host: testrail-tools.trendmicro.com
Connection: Keep-Alive
Cookie: _ga=GA1.2.1909963682.1524537669; _gid=GA1.2.563928490.1529501401
第1行 请求行:
请求方法(GET)+空格+url(https://testrail-tools.trendmicro.com/portal/admin/getTimerInitStatus)+空格+协议版本(HTTP/1.1)
第2-10都是请求头部
Accept:表示客户端接受的内容类型,按照先后顺序表示客户端接收数据的先后次序
X-Requested-With:以x开头的是非http标准,一般是某种技术的出现而定义的;这里是用来判断是http请求还是ajax请求。
Referer:从这个页面访问请求行里的url
Accept-Language:客户端接受内容返回优先选择的语言
Accept-Encoding:客户端可以接受的服务器对返回内容进行编码压缩的格式。
User-Agent:客户端运行的浏览器类型信息。
Host:头域指定请求的服务器的地址和端口,HTTP/1.1必须包括Host,否则返回400
Connection:表示是否需要持久连接。如果web服务器端看到这里的值为“Keep-Alive”,或者看到请求使用的是HTTP 1.1(HTTP1.1默认进行持久连接),它就可以利用持久连接的优点,当页面包含多个元素时(例如Applet,图片),显著地减少下载所需要的时间。要实现这一点,web服务器需要在返回给客户端HTTP头信息中发送一个Content-Length(返回信息正文的长度)头,最简单的实现方法是:先把内容写入ByteArrayOutputStream,然后正式写出内容之前计算它的大小。
Cookie:http请求时,会把保存的cookie也发送服务器。cookie是保存在客户端里的,分为内存cookie和硬盘cookie。前者随着浏览器关闭而消失,后者由过期时间或者用户手动清除。因为http请求是无状态的,所以服务器为了认证,会生成sessionid,让浏览器setcookie保存起来,每次请求携带上认证信息。
下面是响应示例:
HTTP/1.1 200 OK
Server: Apache-Coyote/1.1
Cache-Control: private
Expires: Wed, 31 Dec 1969 16:00:00 PST
X-Application-Context: application:prod
Content-Type: application/json;charset=UTF-8
Transfer-Encoding: chunked
Date: Wed, 20 Jun 2018 15:00:16 GMT
{"advancewarn":"1","userstatus":"1","ldap":"1","licensealarm":"1","deltempzipfile":"1","sctmlicense":"0","user":"1"}
第1行状态行
第2-8消息报头
Server:包含处理请求的服务器信息,包含多个产品注释和标识
Cache-Control:告知缓存机制是否缓存和类型,private是指只能当前用户,不能被共享
Expires:响应过期时间
X-Application-Context:application配置,这里表示读取的是application-prod.properties
Content-Type:返回的数据类型和字符编码格式
Transfer-Encoding:告知接收端,报文采取了何种编码。chunked表示服务器无法确定消息大小,一般比如下载等,就采用chunked。
Date:返回消息的时间
第9行:空行
第10行:响应正文,消息报头指定了是返回json字符串。
POST:
请求示例:
POST https://testrail-tools.trendmicro.com/portal/admin/editTimer HTTP/1.1
Host: testrail-tools.trendmicro.com
Connection: keep-alive
Content-Length: 35
Accept: application/json, text/javascript, */*; q=0.01
Origin: https://testrail-tools.trendmicro.com
X-Requested-With: XMLHttpRequest
User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/67.0.3396.87 Safari/537.36
Content-Type: application/x-www-form-urlencoded; charset=UTF-8
Referer: https://testrail-tools.trendmicro.com/portal/admin/toAdminTimerConfig?id=7
Accept-Encoding: gzip, deflate, br
Accept-Language: zh-CN,zh;q=0.9
Cookie: _ga=GA1.2.199305797.1501211992; _ga=GA1.1.199305797.1501211992; _gid=GA1.2.56449187.1529562439; _gat_gtag_UA_111346521_2=1
type=del&interval=1200&timelag=7200
第1行同get
第2-15行请求头部
Content-Length:告知服务器,请求数据的大小
Origin:origin类似referer,但比referer更人性化,origin只出现在post中,而origin也不携带敏感信息和具体url路径。
Content-Type:http请求提交内容的编码类型,一般只有post需要设置。application/x-www-form-urlencoded(缺省)和multipart/form-data。
第14行 空行
第15行 请求数据
了解这六种方法的本质仍然是很有作用的。大家将会发现,原来web也是很简洁明了的。下面再次依次说明这六种方法。
1,GET:GET可以说是最常见的了,它本质就是发送一个请求来取得服务器上的某一资源。资源通过一组HTTP头和呈现据(如HTML文本,或者图片或者视频等)返回给客户端。
GET请求中,永远不会呈现数据。
2,POST:向服务器提交数据。这个方法用途广泛,几乎目前所有的提交操作都是靠这个完成。
3,HEAD:HEAD和GET本质是一样的,区别在于HEAD不含有呈现数据,而仅仅是HTTP头信息。有的人可能觉得这个方法没什么用,其实不是这样的。
想象一个业务情景:欲判断某个资源是否存在,我们通常使用GET,但这里用HEAD则意义更加明确。
4,PUT:这个方法比较少见。HTML表单也不支持这个。本质上来讲, PUT和POST极为相似,都是向服务器发送数据,但它们之间有一个重要区别,
PUT通常指定了资源的存放位置,而POST则没有,POST的数据存放位置由服务器自己决定。举个例子:如一个用于提交博文的URL,/addNew。
如果用PUT,则提交的URL会是像这样的”/addNew/abc123”,其中abc123就是这个博文的地址。而如果用POST,则这个地址会在提交后由服务器告知客户端。
目前大部分博客都是这样的。显然,PUT和POST用途是不一样的。具体用哪个还取决于当前的业务场景。
5,DELETE:删除某一个资源。基本上这个也很少见,不过还是有一些地方比如amazon的S3云服务里面就用的这个方法来删除资源。
6,OPTIONS:这个方法很有趣,但极少使用。它用于获取当前URL所支持的方法。若请求成功,则它会在HTTP头中包含一个名为“Allow”的头,值是所支持的方法,如“GET, POST”。