#tjhttp 一、《图解HTTP》- WEB和网络基础
1.1 本章重点
开头部分是关于WEB和网络历史介绍,所以没有多少需要理解和记忆的内容。网络基础 TCP/IP的部分是整个互联网的核心,建议多看几遍理解和消化。
WEB的传输依赖HTTP(HyperText Transfer Protocol,超文本传输协议 1 )的协议作为规范,HTTP的工作是完成从客户端到服务器端等一系列运作流程,为了保证两台不同的设备能正常沟通,两者需要遵守相同的规则。
目前HTTP已经发展到3.0了,但是这本书写下来的时候2.0还在起草,所以可以认为是一本比较“老”的书,很多地方需要查阅当前的资料进行纠正。
1.2 HTTP诞生
1989 年 3 月HTTP在少数几个人手中诞生。CERN(欧洲核子研究组织)的蒂姆 • 伯纳斯 - 李(Tim BernersLee)提出网络通信的设想。
1990 年 11 月,CERN 成功研发了世界上第一台 Web 服务器和 Web 浏 览器。
1990 年,大家针对 HTML 1.0 草案进行了讨论,因 HTML 1.0 中存在 多处模糊不清的部分,草案被直接废弃了。
1993 年 1 月,现代浏览器的祖先 NCSA(National Center for Supercomputer Applications,美国国家超级计算机应用中心)研发的 Mosaic 问世了。同年秋天发布Windows 版和 Macintosh 版面世。
1994 年 的 12 月,时代的眼泪网景通信公司发布了 Netscape Navigator 1.0,1995 年微软公司发布臭名昭著的 Internet Explorer 1.0 和 2.0,随后IE折磨开发人员数十年的历史开始。
这里有一个互联网比较知名的历史,那就是关于微软和网景之间的浏览器争夺,感兴趣的同学可以查查这一段历史,微软最终凭借Windows平台的客户粘性绑定以及免费赢得胜利,网景虽然赢了官司但是浏览器市场被Windows垄断逐渐没落,毕竟explore不收费谁奈何的了我。
现在的FireFox浏览器前身就是网景,不过浏览器内核却是谷歌一家独大,Edge在chrome内核以及自身优化的加持下也可圈可点,但是微软利用平台强制绑定客户的行为依旧可见一二,这都是现代的用户可以感知的。
另外值得一提的是3W的构建包含三种技术:
- SGML(Standard Generalized Markup Language,标准通用标记语言),是现时常用的超文本格式的最高层次标准,是可以定义标记语言的元语言,甚至可以定义不必采用< >的常规方式,因为太复杂因而难以普及。后续的HTTP和XML都可以看作这个协议的扩展和拆分和简化。
- HTML(HyperText Markup Language,超文本标记语言)。
- URL(Uniform12 Resource Locator,统一资源定位符)。
1.3 HTTP历史简述
HTTP发展到现在也基本所有网站都是HTTP1.1版本作为标准,自 1999 年发布的 RFC2616 之后再未进行过修订。
这部分内容在第二章中会再次重点扩展和讨论
RFC2616协议在线阅读:
RFC2616
历史发展
感兴趣可以点击协议号查看原文。
- HTTP/0.9:HTTP 于 1990 年问世,这个版本可以看作是1.0之前的雏形,因为没有作为标准正式版建立,所以被叫做为0.9。
- HTTP/1.0:HTTP 正式作为标准被公布是在 1996 年的 5 月,标准号为RFC1945(点击链接查看白皮书)。
- HTTP/1.1:1997 年 1 月公布,直到现在依然还有大量的网站在使用,最初标准为RFC2068,之后发布的修订版 RFC2616 就是当前的最新版本。
- HTTP/2.0:HTTP/2是HTTP协议自1999年HTTP 1.1的改进版RFC2616发布后的首个更新,主要基于SPDY协议。
它由[互联网工程任务组](https://zh.m.wikipedia.org/wiki/互联网工程任务组)(IETF)的Hypertext Transfer Protocol Bis(httpbis)工作小组进行开发。该组织于2014年12月将HTTP/2标准提议递交至[IESG](https://zh.m.wikipedia.org/w/index.php?title=IESG&action=edit&redlink=1)(英语:[Internet_Engineering_Steering_Group](https://en.wikipedia.org/wiki/Internet_Engineering_Steering_Group))进行讨论,于2015年2月17日被批准。
代码语言:txt复制HTTP2.0的标准号:[RFC 7540](https://datatracker.ietf.org/doc/html/rfc7540)
最后在网上找到一个关于HTTP协议的翻译网站,项目作者貌似弃坑很多年没有更新,但是对于英语基础较差的同学可以作为参考:
代码语言:txt复制[rfc7540-translation-zh_cn](https://github.com/abbshr/rfc7540-translation-zh_cn)
1.3.1 HTTP/2.0 的特点
这部分内容同样会在第二章详细介绍。
HTTP/2.0 的目标是改善用户在使用 Web 时的速度体验。
为了支撑这一实现,官方提出了三种技术:
- SPDY(SPDY HTTP Speed):谷歌提出用于提高HTTP访问效率以及解决HTTP1.X中管道化的缺陷,意图是缩短整个请求时间。
- Mobility Network-Friendly:由微软公司起草,是用于改善并提高移动端通信时的通信速度和性能的标准。见名知意它是被用来实现手机高速上网的一个协议。
- HTTP Upgrade (Network-Friendly HTTP Upgrade):
1.3.2 HTTP2.0题外话
这本书写于13,14年左右,HTTP2.0到现在都快接近十年了好像到现在才稍微好转不少,所以作为读者肯定好奇现在到底普及多少了,这里找到一个可供参考的网站,从纸面数据来看截止到目前国外的统计目前使用HTTP/2的还不到一半也就意味着还有一大半的服务器还在使用hTTP1.1。
这就引申了下一个话题,3.0都快要出来了为什么2.0还没全面普及?
这就要了解为什么2.0的普及这么难。
首先是HTTP1.0中请求非常纯粹,一个请求就是一次HTTP连接,请求完成就断开。
于是HTTP1.X 升级了一下,可以通过Keep-alive优化TCP的建立和断开,一次连接也可以对应多个请求。
然而谷歌是不会满足这样的效率的,谷歌推动了HTTP2.0的升级,针对HTTP1.X的请求响应必须要排队的问题处理,使用多路复用完成整个请求。
所以为什么协议在进步,看起来效率在显著提升,为什么HTTP的升级难以推进?
表层来看
真实的项目基本需要依赖框架完成,有一些旧系统旧版本的框架不是想升级就升级的,或者说压根懒得升级,因为没有显著的带来效益的好处。
更深层次的原因
HTTP2.0 自带HTTPS,这样实际上就导致一个冲突问题,实际的项目大多需要使用Nginx反向代理,但是Ngnix也可以开启Http2.0的支持呀,为什么依然坚持要用Nginx 做反向代理而不是直接使用HTTP2.0呢?
这样的原因可能来自TCP长链接,在Nginx部署的情况下,实际上请求不需要走一长串的路由而是直接和Nginx交互。但是HTTP2.0 可以通过多点部署以及多个请求顺序并行,通过集群和负载均衡可以很好的满足服务器要求。
在框架当中如果把请求发给本地,局限单台机器的核数量,并发效率实际上和HTTP1.X差不多,因为任务多起来依然需要排队。
如果开启HTTP2.0并且交给Nginx 拆分模块并且简化功能,不改变开发模式的情况下又可以利用集群。
最后HTTP2.0虽然解决了HTTP多路复用并发请求的问题,但是TCP的问题并没有被解决。
从上面的讨论来看,大体上是TCP的锅,其次是Nginx够强以及框架升级的高成本问题,最后是期待HTT P3.0一步到胃。
当然不要认为50% 普及率很低,从另一个角度来看访问量很大日常使用的网站基本都有HTT P2.0的加成。
1.4 TCP/IP
理解HTTP必然需要了解TCP/IP。
HTTP协议是应用层的协议,如果是金字塔结构它处于模型的顶层,但是实际上金字塔的核心是TCP/IP,HTTP是在此基础上做支撑的,现代的网络架构是基于TCP/IP模型建立的,HTTP也只是其中的一部分。
TCP/IP 是互联网相关的各类协议族的总称,这是一种说法,表示他单单只是字面意思的TCP协议和IP协议。但是另一种说法是只是代表了TCP 和 IP 这两种协议。
TCP/IP 协议族按层次分别分 为以下5 层:应用层、传输层、网络层和数据链路层,以及和硬件密切相关的物理层。
层次化的设计意味着便于修改,也就是常说的高内聚低耦合在TCP/IP
协议得到充分体现,但是实际上这种设计不是完全没有缺点的,那就是每一层虽然可以升级但是无法突破原有的框架,TCP协议本身也是导致HTTP协议难以推动的一个重要原因。
《TCP/IP 详解,卷 1》中开头介绍了OSI模型又是啥?实际上是早期互联网协议构建者的美好愿景,企图通过这一个模型实现一个极强扩展性的互联网架构,说难听点就是把标准给完全垄断掉,让以后的架构无牌可打你们都得听我的。
当然理想和美好现实很骨感,由于OSI模型结构的层级过多并且难以推动和维护,后续被更为精简好理解的TCP/IP 快速取代。
所以OSI模型是历史斗争的产物,不需要过多关注。
根据模型介绍各层都做了什么?
- 应用层:决定为用户提供服务的应用程序相关活动。
- 传输层:传输层主要是协议之间的数据传输,包含各种丰富多样的协议,包括但是不限于TCP协议,比如TCP(Transmission Control Protocol,传输控制协议)和 UDP(User Data Protocol,用户数据报协议)。
- 网络层:网络层用来处理在网络上流动的数据包,最终转化为网络包的最小单位进行传输。
- 数据链路层:也可以认为是看的见的硬件部分,比如网卡,硬件上的范畴均在链路层的作用范围之内。
- 物理层:也就是网线和集线器等网络传输支持设备,从粗略角度来看可以直接看作网线。
下面是整个网络数据包的封装过程,如果想要了解整个过程可以查看 《网络是怎么样连接的》这本书的第二章部分。
1.4.1 IP、TCP 和DNS
按照协议层次划分:IP(Internet Protocol)网际协议位于网络层,TCP位于传输层,所以TCP/IP 协议除了代表一个协议族群之外,TCP协议和IP协议本身其实就不在一个层级,所以不能混为一谈。
IP协议(Internet Protocol)
IP(Internet Protocol)网际协议位于网络层。
IP协议的主要工作是确保信息能准确传输,为了保证数据能正确的送达,IP协议需要确保MAC地址和IP地址的正确,IP 地址指明了节点被分配到的地址,MAC 地址是指网卡所属的固定地址。
IP地址由于内外网通信的缘故有可能会存在地址转化,地址转化依赖的是地址转化设备,但是MAC地址是从网卡生产之后就固定了世界上唯一的网卡MAC地址。
ARP 协议凭借 MAC 地址进行通信,接着便是通过类似快递导航寻找站点的方式进行通信传输,整个核心是通过“查表”方式进行。
ARP 协议(Address Resolution Protocol):ARP 是一种用以解析地址的协议,根据通信方的 IP 地址就可以反查出对应的 MAC 地址。
TCP协议
TCP协议位于传输层,提供字节流服务,所谓字节流服务是指大块数据拆分为报文段, 而可靠服务指的是把数据传输给对方,同时TCP为了保证大段数据的传输会进行数据切割。
为了确保数据准确传输,整个TCP还需要依赖三次握手,关于三次握手的过程这里也不做过多讨论,可以看《网络是怎么样连接的》读书笔记内容。
DNS 服务
用户通常使用主机名或域名来访问对方的计算机,而不是直接通过 IP地址访问。DNS是负责域名和IP转化的服务,在请求目标服务器之前,通常需要根据DNS服务获取域名对应的IP地址。
各协议和HTTP关系
注意在书中省略有关MAC头部的内容,另外整个图画算是最为入门级的角度,实际上稍微深入就会发现没有那么简单这幅图也是画的过于笼统,简单看看角色的基本职责即可。
1.4.2 URL和URI
区别和对比
首先得区分概念本身:
URL
:表示统一资源定位,也就是我们访问WEB 服务器在浏览器顶部的那一串数字。
URI
: 其实这里包含三个组件,URI全称 是 Uniform Resource Identifier,RFC2396在规范的1.1分别对于这三个单词进行下面的定义,整体来看URI 就是由某个协议方案表示的资源的定位标识符。
Uniform
:规定统一的格式可方便处理多种不同类型的资源,也就是常说的“习惯优于配置”,具体案例是比如ftp是ftp开头请求走协议,http开头请求走http协议。
Resource
:抽象定义资源是“任何可以访问的东西”,比如文档,图片,网络文件等等全都可以看做资源。
Identifier
:表示可以标识的对象,也叫做标识符。
URI属于互联网顶级规范的行列,只有符合URI规范的请求才能被识别,由隶属于国际互联网资源管理的非营利社团 ICANN(Internet Corporation forAssigned Names and Numbers,互联网名称与数字地址分配机构)的IANA(Internet Assigned Numbers Authority,互联网号码分配局)管理颁布。
关于规范的相关文本可以参考文末部分
最后是有关URL定义的两个直观例子:
代码语言:text复制 hierarchical part
┌───────────────────┴─────────────────────┐
authority path
┌───────────────┴───────────────┐┌───┴────┐
abc://username:password@example.com:123/path/data?key=value&key2=value2#fragid1
└┬┘ └───────┬───────┘ └────┬────┘ └┬┘ └─────────┬─────────┘ └──┬──┘
scheme user information host port query fragment
urn:example:mammal:monotreme:echidna
└┬┘ └──────────────┬───────────────┘
scheme path
当然官方在白皮书也给了一些案例:
代码语言:text复制 The following examples illustrate URI that are in common use.
ftp://ftp.is.co.za/rfc/rfc1808.txt
-- ftp scheme for File Transfer Protocol services
gopher://spinaltap.micro.umn.edu/00/Weather/California/Los Angeles
-- gopher scheme for Gopher and Gopher Protocol services
http://www.math.uio.no/faq/compression-faq/part1.html
-- http scheme for Hypertext Transfer Protocol services
mailto:mduerst@ifi.unizh.ch
-- mailto scheme for electronic mail addresses
news:comp.infosystems.www.servers.unix
-- news scheme for USENET news groups and articles
telnet://melvyl.ucop.edu/
-- telnet scheme for interactive services via the TELNET Protocol
最后我们简单来对比URL和URI,可以看到URI划定了URL的“分类”,所以URL可以看做是URI的子集。
URL 格式
这里主要介绍用的比较少的片段标识符,片段标识符表示已获取资源中的子资源。
注意互联网中并不是所有的请求都会符合RFC协议的,RFC指的是HTTP协议的意见修正书,这些内容多数情况下应用程序都会遵守,但是凡事总有特例。
如果不参考RFC协议进行通信那么就需要自己的协议完成客户端之间的通信,比较典型的例子比如RPC协议就是经典的非HTTP协议通信实现,当然这种方案存在不少的问题和争议。
1.5 总结
和多数技术书类似,第一章算是概览的一个章节,大致介绍了HTTP的基础背景,当然这本书确实很老,很多协议和标准到现在其实早就不在使用了,但是从另一个角度来看IP、TCP、DNS这些东西基本都是万年不变的,所以不需要担心会过时。
关于HTTP2.0的讨论是笔记中的扩展部分,在这一部分大致讨论了一下为什么HTTP2.0难以推进,但是实际上HTTP2.0在各大主流网站都有普及,国内的一些大厂商基本也是第一时间跟进的。