1.解读URL
从浏览器中输入网址( URL )开始 , 即以 http://( Web 服务器 ) 开头的。根据需求不同也会以 “ftp:”( FTP 服务器 )“file:” “mailto:” 等开头。
根据访问目标的不同,URL 的写法也会不同。如访问 Web 服务器和 FTP 服务器时,URL 中会包含服务器的域名和要访问的文件的路径名等,而发邮件的 URL 则包含收件人的邮件地址。此外,根据需要,URL 中还会包含用户名、密码、服务器端口号等信息。
之后对 URL 进行解析 ,以访问 Web 服务器的情况为例 ,进行拆分分析
包含 Web 服务器名称 www.lab.glasscom.com,以及**文件的路径**名 /dir1/file1.html,表示要访问 www.lab.glasscom.com 这个 Web 服务器上路径名为 /dir/file1.html 的文件,也就是位于 /dir/ 目录 D 下的 file1.html 这个文件
后面的文件名会有省略的情况,如 www.lab.glasscom.com/dir/ ,会在服务器上事先设置好文件名省略时要访问的默认文件名。index.html 或者 default.htm 之类的文件名。因此会访问 /dir/index.html 或者 /dir/default.htm。
URL只有 Web 服务器的域名的,也是一种省略文件名的形式。www.lab.glasscom.com/
也是以“/”结尾的,表示访问一个名叫“/”的目录(根目录)。由于省略了文件名,所以结果就是访问 /index.html 或者 /default.htm 。 “/” 也省略时情况相同。
www.lab.glasscom.com/whatisthis 由于末尾没有“/”,所以 whatisthis 应该理解为文件名才对。但实际上,如果 Web 服务器上存在名为 whatisthis 的文件,则将 whatisthis 作为文件名来处 理;如果存在名为 whatisthis 的目录,则将 whatisthis 作为目录名来处理 (不会都有)。
2.HTTP请求与响应
HTTP协议指的是超文本传输协议。 定义了客户端和服务器之间交互的消息内容和步骤,****
首先,客户端会向服务器发送请求消息。请求消息中包含的内容是 “对什么” 和“进行怎样的操作”两个部分。
其中“对什么”的部分称为 URI。URI 的内容是一个存放网页数据的文件名或者是一个 CGI 程序 的文件名,例如“/dir1/file1.html” “/dir1/program1.cgi”等 。URI 不仅限于此,也可以直接用“http:” 开头的 URL来作为 URI。这里可以写各种访问目标,而这些访问目标统称为 URI。
CGI 程序:对 Web 服务器程序调用其他程序的规则所做的定义就是 CGI, 而按照 CGI 规范来工作的程序就称为 CGI 程序。
接下来“进行怎样的操作”的部分称为方法 。方法表示需要让 Web 服务器完成怎样的工作,其中典型的例子包括读取 URI 表示的数据、 将客户端输入的数据发送给 URI 表示的程序等。
Web服务器根据要求来完成工作,将结果放在响应消息中。在响应消息的开头有一个状态码, 用来表示操作的执行结果是成功还是发生了错误。 如 404 Not Found
状态码后面就是头字段和网页数据。响应消息会被发送回客户端,客户端收到之后,浏览器会从消息中读出所需的数据并显示在屏幕 上。
生成 HTTP 请求消息,格式上有规定的。 请求消息的第一行称为请求行。最开头是方法, 选用哪个方法根据 浏览器的工作状态 决定。
在地址栏中输入网址并显示网页,因此应该使用 GET 方法。点击超级链接中也是使用 GET 方法。如果是表单,在 HTML 源代码中会在表单的属性中指定使用哪种方法来发送请求,可能是 GET 也可能是 POST
GET 方法能够发送的数据只有几百个字节,如果表单中的数据超过这一长 度,则必须使用 POST 方法来发送。
写好方法之后,加一个空格,然后写 URI。URI 的格式一 般是文件和程序的路径名。
/< 目录名 >/…/< 文件名 >
路径名一般已经包含在 URL 中了,因此只要从 URL 中提取出来写上去就好了。
第二行消息头。第一行可以大致理解请求的内容,但有些情况需要一些额外的详细信息,消息头用来存放这些信息。
消息头定义了很多项目,如日期、客户端支持的数据类型、语言、压缩格式、客户端和服务器的软件名称和版本、数据有效期和最后更新时间等。通用头,请求头,响应头,实体头
当使用 POST 方法时,需要将表单中填写的信息写在消息体中。
当请求消息发送出去之后,Web 服务器会返回响应消息。 响应消息的格式以及基本思路和请求消息是相同的,差别只在第一行上。
在响应消息中,第一行的内容为状态码和响应短语,用来表示请求的执行结果是成功还是出错。状态码和响应短语表示的内容一致,但它们的用途不同。状态码是一个数字,它主要用来向程序告知执行的结果。相对地,响应短语则是一段文字,用来向人们告知执行的结果。
返回响应消息之后,浏览器会将数据提取出来并显示在屏幕上。如果网页的内容只有文字,那么到这里就全部处理完毕了。
但如果网页中还包括图片等资源,会在网页中的相应位置嵌入表示图片文件的标签的控制信息。当遇到图片相关的标签时,会在屏幕上留出用来显示图片的空间,然后再次访问 Web 服务器,按照标签指定的文件名向 Web 服务器请求获取相应的图片并显示在预留的空间中。
每条请求消息中只能写 1 个 URI,所以每次只能获取 1 个文件, 如果需要获取多个文件,对每个文件单独发送 1 条请求。比如 1 个 网页中包含 3 张图片,那么获取网页加上获取图片,一共需要向 Web 服务 器发送 4 条请求。
3.域名解析
生成 HTTP 消息之后,会委托操作系统将消息发送给 Web 服务器 ,必须要提供的不是的域名,而是它的 IP 地址。在生成 HTTP 消息之后,下一个步骤是根据域名查询 IP 地址。
互联网和公司内部的局域网都是基于 TCP/IP 的思路来设计的 。在网络中,所有的设备都会被分配一个地址。通过 IP 地址我们可以判断出访问对象服务器的位置,从而将消息发送到服务器。
主机号部分全部为 0 代表整个子网而不是子网中的某台设备
查询 IP 地址的方法非常简单,只要询问最近的 DNS 服务器“www. lab.glasscom.com 的 IP 地址是什么”就可以了,DNS 服务器会回答说“该 服务器的 IP 地址为 xxx.xxx.xxx.xxx”。
对于 DNS 服务器,计算机上一定有相应的 DNS 客户端,称为 DNS 解析器。 解析器实际上是一段程序,它包含在操作系统的 Socket 库中,是用于调用网络功能的程序组件集合 。
Socket 库中的程序都是标准组件,只要从应用程序中进行调用就可以了。在编写浏览器等应用程序的时候,只要写上解析器的程序名称“gethostbyname”以及 Web 服务器 的域名“www.lab.glasscom.com”就可以了,这样就完成了对解析器的调用 。
解析器向 DNS 服务器发送查询消息,然后 DNS 服务器返回响应消息。响应消息中包含查询到的 IP 地址,解析器会取出 IP 地址,写入浏览器指定的内存地址中。 浏览器在向Web 服务器发送消息时,只要从该内存地址取出 IP 地址,并将它与 HTTP 请求消息一起交给操作系统就可以了。
网络应用程序(浏览器)调用解析器时, 程序的控制流程就会转移到解析器的内部。 解析器会生成要发送给 DNS 服务器的查询消息。解析器会根据 DNS 的规格,生成一条表示“请告诉我 www.lab. glasscom.com 的 IP 地址”的数据,并将它发送给 DNS 服务器 。
发送消息是委托给操作系统内部的协议栈来执行。 协议栈会执行发送消息的操作,然后通过网卡将消息发送给 DNS 服务器 。然后其 IP 地址会被写入响应消息并返回给客户端 ,经过协议栈被传递给解析器,然后取出 IP 地址,并将 IP 地址写入应用程序指定的内存地址中。
协议栈:操作系统内部的网络控制软件,也叫“协议驱动”“TCP/IP 驱动”等。
DNS 服务器来自客户端的查询消息包含以下 3 种信息。
(a)域名
服务器、邮件服务器(邮件地址中 @ 后面的部分)的名称
(b) Class
在最早设计 DNS 方案时,DNS 在互联网以外的其他网络中的应用也考虑到了,用来识别网络的信息。如今除了 互联网并没有其他的网络了,因此 Class 的值永远是代表互联网的 IN
(c)记录类型
表示域名对应何种类型的记录。当类型为 A 时,表示域名对应的是 IP 地址;当类型为 MX 时,表示域名对应的是邮件服务器。对于不同的记录类型,服务器向客户端返回的信息也会不同
DNS 服务器中的所有信息都是按照域名以分层次的结构来保存的。 用句点来分隔的,比如 www.lab.glasscom.com,这里的句点代表了不同层次之间的界限 。这种具有层次结构的域名信息会注册到 DNS 服务器中,每个域都作为一个整体来处理。 即一个域的信息是作为一个整体存放在 DNS 服务器中的,不能将一个域拆开来存放在多台 DNS 服务器中。 但一台 DNS 服务器中也可以存放多个域的信息。
互联网中的域通过创建下级的域来分配给不同的国家、公司和组织使用。如www.nikkeibp.co.jp ,最上层的 jp 代表分配给日本的域;下一层的 co 是日本国内进行分类的域;再下层的 nikkeibp就是分配给某个公司的域,最下层的 www 就是服务器的名称。
如何寻找相应的 DNS 服务器并获取 IP 地址
首先,将负责管理下级域的 DNS 服务器的 IP 地址注册到它们的上级 DNS 服务器中,然后上级 DNS 服务器的 IP 地址再注册到 更上一级的 DNS 服务器中,以此类推。
com 和 jp 的上面还有一级域,称为根域。根域没有自己的名字,因此在一般书写时经常省略,如果要明确表示根域,应在域名的最后再加上一个句点,这个最后 的句点就代表根域。根域的 DNS 服务器中保管着 com、jp 等的 DNS 服务器的信息。根域的 DNS 服务器信息会被保存在互联网中所有的 DNS 服务器中。
通过缓存加快 DNS 服务器的响应
现实中上级域和下级域有可能共享同一台 DNS 服务器。访问上级 DNS 服务器时就可以向下跳过 一级 DNS 服务器,直接返回再下一级 DNS 服务器的相关信息。
DNS 服务器有一个缓存功能,可以记住之前查询过的域名。如果要查询的域名和相关信息已经在缓存中,那么就可以直接返回响应,接下来的查询可以从缓存的位置开始向下进行。当要查询的域名不存在时,“不存在”这一响应结果也会被缓存。
DNS 服务器中保存的信息有一个有效期,当缓存中的信息超过有效期后,数据就会从缓存中删除。DNS 服务器也会告知客户端这一响应的结果是来自缓存中还是来自该域名的 DNS 服务器。
4.委托协议栈发送消息
知道 IP 地址之后,就可以委托操作系统内部的协议栈向这个目标 IP 地址发送消息了。 发出委托时,需要按照指定的顺序来调用 Socket 库中的程序组件 。
首先,服务器一方先创建套接字,然后等待客户端向该套接字连接管道 。当服务器进入等待状态时,客户端就可以连接管道了。
客户端会创建一个套接字,然后从该套接字延伸出管道,最后管道连接到服务器端的套接字上。
当数据全部发送完毕之 后,连接的管道将会被断开。断开 时可以由客户端或服务器任意一方发起 。其中一方断开后,另一方也会随之断开,套接字也会被删除。
(1)创建套接字(创建套接字阶段)
(2)将管道连接到服务器端的套接字上(连接阶段)
(3)收发数据(通信阶段)
(4)断开管道并删除套接字(断开阶段)
首先是套接字创建阶段。调用Socket 库中的 socket 程序组件,协议栈会返回一个描述符。
接下来,委托协议栈将客户端创建的套接字与服务器那边的套接字连接起来。调用connect的程序组件。需要指定描述符、 服务器 IP 地址和端口号这 3 个参数
描述符是和委托创建套接字的应用程序进行交互时使用的,并不是用来告诉网络连接的另一方的,因此另一方并不知道这个描述符。
当套接字连接起来之后,只要将数据送入套接字,数据就会被发送到对方的套接字中。要通过 Socket 库委托协议栈来完成这个操作。使用 write 这个程序组件。 指定描述符和发送数据,然后协议栈就会将数据发送到服务器,套接字中已经保存了已连接的通信对象的相关信息,所以只要通过描述符指定套接字,就可以识别出通信对象。 接着,数据通过网络到达要访问的服务器。 接下来,服务器执行接收操作,解析收到的数据内容并执行相应的操作,向客户端返回响应消息 。
当消息返回后,通过 Socket 库中的 read 程序组件委托协议栈来完成的。需要指定存放响应消息的内存地址,接收缓冲区。接收缓冲区是一块位于应用程序内部的内存空间。
接下来,调用 Socket 库的 close 程序组件进入断开阶段。最终,连接在套接字之间的管道会被断开,套接字本身也会被删除。 Web 使用的 HTTP 协议规定,当 Web 服务器发送完响应消息之后,应该主动执行断开操作,因此 Web 服务器会首先调用 close 来断开连接(也可能相反)。
HTTP 协议将 HTML 文档和图片都作为单独的对象来处理,每获取一次数据,就要执行一次连接、发送请求消息、 接收响应消息、断开的过程。如果一个网页中包含很多张图片,就必须重复进行很多次连接、收发数据、断开的操作。对于同一台服务器来说,重复连接和断开显然是效率很低的,因此后来人们又设计出了能够在一次连接中收发多个请求和响应的方法。在 HTTP 版本 1.1 中就可以使用这种方法,当所有数据都请求完成后,浏览器会主动触发断开连接的操作。
5.https
对称加密
整个加密过程中只使用一个密钥。所谓对称其实就是使用一把密钥加密,使用同一把密钥解密。对称加密由于加解和解密使用的是同一个密钥算法,故而在加解密的过程中速度比较快,适合于数据量比较大的加解密。
对称加密的主要有优点就是算法公开、计算量小、加密速度快、加密效率高;但是它也存在强大的缺点,缺点就是密钥协商过程中,一旦密钥泄露,别人可以获取到密钥,这样也能对密文进行解密。 另外,每对用户每次使用对称加密算法时,都需要使用其他人不知道的独一密钥,这会使得收、发双方所拥有的钥匙数量巨大,密钥管理成为双方的负担。
非对称加密
该技术是针对私钥密码体制(对称加密算法)的缺陷被提出来的,非对称加密会产生两把密钥,分别为公钥(Public Key)和私钥(Private Key),其中一把密钥用于加密,另一把密钥用于解密。非对称加密的特征是算法强度复杂、安全性依赖于算法与密钥但是由于其算法复杂,而使得加密解密速度没有对称加密解密的速度快。对称密码体制中只有一种密钥,并且是非公开的,如果要解密就得让对方知道密钥。所以保证其安全性就是保证密钥的安全,而非对称密钥体制有两种密钥,其中一个是公开的,这样就可以不需要像对称密码那样传输对方的密钥了。这样安全性就高了很多。
① 证书验证阶段
- 浏览器发起 HTTPS 请求
- 服务端返回 HTTPS 证书
- 客户端验证证书是否合法,如果不合法则提示告警
② 数据传输阶段
- 当证书验证合法后,在本地生成随机数
- 通过公钥加密随机数,并把加密后的随机数传输到服务端
- 服务端通过私钥对随机数进行解密
- 服务端通过客户端传入的随机数构造对称加密算法,对返回结果内容进行加密后传输