HTTP
1. http 0.9/1.0
0.9和1.0这两个版本,就是最传统的 request – response的模式了,HTTP 0.9版本的协议简单到极点,请求时,不支持请求头,只支持 GET 方法,1.0扩展了几点
- 在请求中加入了HTTP版本号,如:
GET /coolshell/index.html HTTP/1.0 - HTTP 开始有 header了,不管是request还是response 都有header了。
- 增加了HTTP Status Code 标识相关的状态码。
- 还有
Content-Type可以传输其它的文件了。
2. http 1.1
HTTP/1.1 主要解决了HTTP 1.0的网络性能的问题,以及增加了一些新的东西:
- 可以设置
keepalive来让HTTP重用TCP链接,重用TCP链接可以省了每次请求都要在广域网上进行的TCP的三次握手的巨大开销。这是所谓的“HTTP 长链接” 或是 “请求响应式的HTTP 持久链接”。 - 然后支持pipeline网络传输,只要第一个请求发出去了,不必等其回来,就可以发第二个请求出去,可以减少整体的响应时间。
- 还增加了 cache control 机制。
- 协议头注增加了 Language, Encoding, Type 等等头,让客户端可以跟服务器端进行更多的协商。
- 还正式加入了一个很重要的头——
HOST这样的话,服务器就知道你要请求哪个网站了。因为可以有多个域名解析到同一个IP上,要区分用户是请求的哪个域名,就需要在HTTP的协议中加入域名的信息,而不是被DNS转换过的IP信息。 - 正式加入了
OPTIONS方法,其主要用于 CORS – Cross Origin Resource Sharing 应用。
3. http2.0
- 多路复用 允许同时通过单一的 HTTP/2 连接发起多重的请求-响应消息。在 HTTP/1.1 协议中浏览器客户端在同一时间,针对同一域名下的请求有一定数量限制。超过限制数目的请求会被阻塞
- 首部压缩 HTTP/1.1并不支持 HTTP 首部压缩,HTTP/2 的出现,加快了请求速度
- 二进制分帧
- 服务器推送
4.从输入一个 URL 地址到浏览器完成渲染的整个过程
- 浏览器地址栏输入 URL 并回车加载
- 浏览器查找当前 URL 是否存在缓存,并比较缓存是否过期
- DNS 解析 URL 对应的 IP,判断本地对此IP是否有缓存
- 根据 IP 建立 TCP 连接(三次握手)
- 发送 http 请求
- 服务器处理请求,浏览器接受 HTTP 响应
- 浏览器解析并渲染页面
- 关闭 TCP 连接(四次挥手)
上述讲到TCP,我们来区分下TCP和UDP?
- TCP是面向连接的,UPD是无连接的,也就是发送数据前不需要建立连接。
- TCP提供可靠的服务,通过TCP连接传送的数据,无差错,不丢失,不重复,且按序到达,UDP尽最大努力交付,即不保证可靠交付;
- TCP面向字节流,UDP是面向报文的,UDP没有拥塞控制,因此,网络出现拥塞不会使原主机的发送速率降低,因此会出现丢包,对实时的应用很有用,比如视频会议等
- 每一条TCP连接,只能是1对1的,UDP支持1对1,1对多,多对1,多对多的交互通讯;TCP的首部开销为20字节,而UDP的只有8字节;TCP面向连接的可靠性传输,而UDP是不可靠的。
5. HTTP缓存 --- 强制缓存和协商缓存
- Expires
响应头,代表该资源的过期时间。
- Cache-Control
请求/响应头,缓存控制字段,精确控制缓存策略。
- If-Modified-Since
请求头,资源最近修改时间,由浏览器告诉服务器。
- Last-Modified
响应头,资源最近修改时间,由服务器告诉浏览器。
- Etag
响应头,资源标识,由服务器告诉浏览器。
- If-None-Match
请求头,缓存资源标识,由浏览器告诉服务器。
- 强制缓存通过HTTP的cache-control 和 Expires字段进行判断,不再向服务器发起请求
Expires是一个绝对时间,即服务器时间。浏览器检查当前时间,如果还没到失效时间就直接使用缓存文件。但是该方法存在一个问题:服务器时间与客户端时间可能不一致。因此该字段已经很少使用。
Cache-control中的max-age保存一个相对时间。例如Cache-Control: max-age = 484200,表示浏览器收到文件后,缓存在484200s内均有效。如果同时存在cache-control和Expires,浏览器总是优先使用cache-control。
- 协商缓存则通过HTTP的last-modified和Etag字段进行判断。
last-modified是第一次请求资源时,服务器返回的字段,表示最后一次更新的时间。下一次浏览器请求资源时就发送if-modified-since字段。服务器用本地Last-modified时间与if-modified-since时间比较,如果不一致则认为缓存已过期并返回新资源给浏览器;如果时间一致则发送304状态码,让浏览器继续使用缓存。
Etag:资源的实体标识(哈希字符串),当资源内容更新时,Etag会改变。服务器会判断Etag是否发生变化,如果变化则返回新资源,否则返回304。相对应的字段是IF-NONE-MATCH.
6. DNS解析过程
DNS解析是一个递归查询的过程
7.CDN
CDN(Content Delivery Network,内容分发网络)将源站的内容发布到接近用户的网络“边缘”,用户可以就近获取所所需要的数据,比如我们请求的静态资源css,js等,不仅降低了网络的拥塞状况、提高请求的响应速度,也能够减少源站的负载压力。
- 没有使用CDN前
如上图所示,如果要访问的网站名为:"baidu.com",客户端首先会在本机的hosts文件和hosts缓存中查找该域名对应的IP地址;如果本机中没有此信息,则会到我们的
本地DNS进行询问该域名对应的IP地址;如果本地DNS中仍然没有该域名的IP信息时,则会由本地DNS依次向根DNS、顶级域DNS、权威DNS进行询问,最终本地DNS将IP地址发送给客户端。客户端通过IP地址向远程的源站服务器发出HTTP请求并获取相应的数据内容。
- 使用cdn后
如图所示是通过CDN进行请求响应的过程图。通过图中可以看出,在DNS解析域名时新增了一个全局负载均衡系统(GSLB),GSLB的主要功能是根据用户的本地DNS的IP地址判断用户的位置,筛选出距离用户最近的本地负载均衡系统(SLB),并将该SLB的IP地址作为结果返回给本地DNS。SLB主要负责判断缓存服务器集群中是否包含用户请求的资源数据,如果缓存服务器中存在请求的资源,则根据缓存服务器集群中节点的健康程度、负载量、连接数等因素筛选出最优的缓存节点,并将HTTP请求重定向到最优的缓存节点上。
8. 跨域
-
JSONP(JSON Padding)
JSON只支持get,因为script标签只能使用get请求;JSONP需要后端配合返回指定格式的数据。客户端请求受同源策略影响,不允许进行跨域请求,而 script 标签 src 属性中的链接却可以访问跨域的 js 脚本,利用这个特性,服务端不再返回 JSON 格式的数据,而是返回一段调用某个函数的 js 代码,在 src 中进行了调用,这样实现了跨域。 -
CORS 浏览器会自动进行 CORS通信,实现CORS通信的关键是后端。只要后端实现了CORS,实现了跨域。服务端设置 Access-Control-Allow-Origin 就可以开启CORS。该属性表示哪些域名可以访问资源,如果设置通配符则表示所有网站都可以访问资源。
当然,使用cors请求时还分简单请求和复杂请求
简单请求
只要同时满足以下两个条件,就属于简单请求
条件1 : 使用下列方法之一:
- GET
- HEAD
- POST
条件2 :Content-Type 的值仅限于下列三者之一 :
- text/plain
- multipart/form-data
- application/x-www-form-urlencoded
复杂请求
不符合以上条件的请求就肯定是复杂请求了。复杂请求的CORS请求,会在正式通信之前,增加一次HTTP查询请,称为"预检"请求,该请求是option方法的 , 通过该请求来知道服务端是否允许跨域请求,这也是对服务器数据的一层保护。
- Nginx 反向代理