HTTP请求中GET和POST的分析

作者: NickYang 分类: 技术文章,程序开发 发布时间: 2012-10-27 11:00

近期一位朋友想写iOS上的应用,打算从微博应用做起,第一步先做一个微博客户端出来,然后做一个手机微博应用出来,具体做什么还不甚清楚,其实是在尝试中。而我正好在用asio写网络库,于是主动提出了承担web服务器网络库的部分,也是为了给我自己封装的网络库中增加一个http模块。

http大家都不陌生,每天打开网页,地址栏前大多数显示的都是http,当然还有https等等,以前跟rangerlee讨论curl的时候有说过post和get,不是很清楚,查阅了众多文章和资料,有点小懂了。

统一资源定位符(URL,英语 Uniform / Universal Resource Locator 的缩写)也被称为网页地址,是因特网上标准的资源的地址(Address)。其实URL就是代表一个特定地址的因特网标准资源URI。http请求中的get post put delete就是对这个资源进行 查 增 改 删 ,有点类似于数据库中的四大操作。get和post最主要的区别是前者是查询,后者是修改,get类似于C++中const函数,而post类似于set或者add函数。

原理:

GET

根据HTTP标准,GET用于信息的获取,并且是安全和幂等的。

安全:GET操作用于获取信息/资源,并非修改信息/资源。主要表现在不能修改信息。

幂等:这是一个数学/计算机上的概念。对于单目运算来说,如果一次运算和多次运算的结果是一样的,则该运算是幂等的,例如:C++中的abs(abs(a)) = abs(a),所以abs函数运算就是幂等的;对于双目运算,两个相等的参与运算的值在运算之后的结果仍然等于这个值,则该运算是幂等的,例如:C++中的max(a, a) = a,所以max函数的幂等的。

而GET是在同一个地址下获取到的资源是相同的,并且没有改变,所以GET是安全的、幂等的。

不过,有些特殊情况也会认为是幂等的。例如:新闻某门户网站的头条新闻,可能在不断的更新,用户可能在不同的时间看到的内容不尽相同,但是这也认为是幂等的,因为对用户来说,他们访问的资源是同一个地址的。

POST

根据HTTP标准,POST用于可能修改服务器资源的请求。并没有什么特殊规定。

例如:最常见的就是留言了,留言完之后页面会刷新,不管是整体刷新还是Ajax局部刷新,这时候用的请求就是POST。

 

表现形式:

HTTP格式为:

<request line>

<headers>

<blank line>

[<request-body>]

先是一个请求行(request line),用来说明请求类型、请求地址、HTTP版本;然后是头部(headers),用来说明服务器的一些附加信息;下来是一个空行(blank line);再下来是数据主体(request-body)。

GET格式

GET / HTTP/1.1
Host: www.cppfans.org
Connection: keep-alive
Cache-Control: max-age=0
User-Agent: Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.10 (KHTML, like Gecko) Chrome/23.0.1262.0 Safari/537.10 AlexaToolbar/alxg-3.1
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8
Accept-Encoding: gzip,deflate,sdch
Accept-Language: zh-CN,zh;q=0.8
Accept-Charset: GBK,utf-8;q=0.7,*;q=0.3

 

POST格式

POST /api/posts/create.json HTTP/1.1
Host: duoshuo.com
Connection: keep-alive
Content-Length: 283
Origin: http://duoshuo.com
X-Requested-With: XMLHttpRequest
User-Agent: Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.10 (KHTML, like Gecko) Chrome/23.0.1262.0 Safari/537.10 AlexaToolbar/alxg-3.1
Content-Type: application/x-www-form-urlencoded
Accept: */*
Referer: http://duoshuo.com/cors/index.html?xdm_e=http%3A%2F%2Fjkirin.com&xdm_c=default693&xdm_p=1
Accept-Encoding: gzip,deflate,sdch
Accept-Language: zh-CN,zh;q=0.8
Accept-Charset: GBK,utf-8;q=0.7,*;q=0.3

以上数据是通过Chrome的元素审查中的Network抓取到的。

1.地址的区别

举个例子:

百度搜索的地址:

http://www.baidu.com/s?tn=monline_4_dg&ie=utf-8&bs=http&f=8&rsv_bp=1&wd=http+get+post&rsv_sug3=9&rsv_sug1=7&rsv_sug4=325&inputT=2533

Get请求会把数据附在URL之后,以?分割URL和传输数据,多个参数用&连接,上述URL地址可以堪为URL是http://www.baidu.com/s,后面的tn=monline_4_dg ie=utf-8 bs=http等都是参数。

遇到空格用+替代,上述URL中的搜索词是http get post,而URL表现出来的是wd=http+get+post。

数字和字母原样不变。wd=http+get+post

中文和其他字符用Base64加密,例如有些URL表现为%D4%E3%A0%BD,其中%XX中XX表示该符号的16进制ANSII码。

POST请求:把修改的数据放置在是HTTP包的包体中进行发送。

Get请求的URL会在地址栏中显示出来,而Post只是修改,并不会改变URL。

2.传输数据的限制

HTTP协议对URL长度和传输的数据长度没有任何限制,不过在实际开发中会根据浏览器的限制条件做一些规定。

GET:根据浏览器和操作系统有一些限制。例如:IE(包含IE内核)浏览器的URL限制是2K+35个字节长度,而其他浏览器理论没有限制,但却取决于操作系统支持的长度。

POST:理论没有传输数据的限制,但总不能提交一个过大的数据,这样会很慢,所以Web服务器一般都会做限制的。

3.安全性

POST的安全性高于GET,这里是指Security而不是Safe,因为Get的URL可以通过分析得出一些数据出来,还有Cookie和历史记录等等都会造成一些恶意攻击或破解。

 

好了,关于GET和POST就说这么多了,下来就是要写一个处理这些请求的http服务器了。有人会说为什么要自己写,而不是用Apache或者nginx等已经成熟的Web服务器?因为他们太复杂了,功能繁杂,而我却不需要这么多功能,所以我写一个简单实用的http server就可以了,不过可以借鉴成熟Web服务器的主要功能代码。敬请期待吧,估计测试和投入使用会时挺长时间的。

如果觉得我的文章对您有用,请随意打赏。您的支持将鼓励我继续创作!

发表评论

电子邮件地址不会被公开。 必填项已用*标注