《网络是怎样连接的》——第一章笔记

        以用户在客户端浏览器的地址栏中输入URL后发生了什么为引子,探讨了浏览器对URL的解析、HTTP报文的生成和发送、DNS服务器根据域名获取目标服务器的IP地址,以及协议栈在通信传输中扮演的角色和具体原理。

第一节 浏览器与服务器的交互

(1)解析URL

        用户在浏览器地址栏输入网址(URL)并按下回车键后,浏览器会对URL进行解析操作。首先浏览器会根据URL的开头部分字符来判断协议的类型。主要有HTTP(访问Web服务器)、FTP(访问文传服务器)、file(访问本地资源文件)和mailto(调用电子邮件服务)等,

        根据协议类型的不同,协议的URL内容也会有不同的组成格式。以HTTP协议为例子,HTTP协议类型的URL的主要格式为:服务器域名+文件资源路径。如http://(协议类型) + www.shareXXX.com(服务器域名) + /dir/index.html(文件资源路径)。

        浏览器对URL进行解析后,会根据协议类型来进行相应的操作。比如知道了HTTP协议主要用于访问Web服务器,浏览器会继续提取URL中的服务器域名和文件资源路径部分,生成相应的HTTP请求报文,并交由操作系统进行接下去的传输业务。

(2)生成HTTP报文

        HTTP协议用来定义客户端和服务器之间的消息内容和步骤。在HTTP协议下浏览器和服务器通过报文进行交互,HTTP报文可分为浏览器端发送的请求报文和服务器端发送的响应报文,并且这些报文内容的格式都有严格的限制。

        当用户在浏览器地址栏键入类型为HTTP协议类型的URL后,浏览器会相应的提取URL中的服务器域名用以确定目标对象的IP地址(这里涉及到下一节提到的DNS查询IP),和文件资源路径来生成请求报文。

        简单来说,请求报文就是用户希望服务器对什么进行怎样的操作。请求报文的格式由三部分组成:请求行(方法+URI+HTTP版号)、消息头(日期、客户端软件版本等附加信息)、消息体(对于GET方法来说为空,为POST方法则会附上用户提交的表单内容)。

       对什么:请求行中的URI部分,也就是服务器中的文件资源路径,可以是某个具体文件也可以是CGI程序。

        进行怎样的操作:请求行中的方法部分,主要有GET、POST,和PUT、DELETE。GET和POST是用途最广泛的方法,我们一般访问服务器网页资源时开始调用的是GET;而PUT和DELETE可以对服务器资源进行修改和删除,考虑到可能造成的安全问题所以并没有被广泛推行。

        需要注意的是,用户点击页面中的超链接和在浏览器地址栏输入网址一样调用的都是GET方法。而用户提交表单或点击某个按钮时,会根据表单form的实际method属性确定采用GET方法还是POST方法进行提交。

        服务器在接收到HTTP请求报文后会解析请求行,根据指定的方法类型去访问指定的URI,并将返回结果封装成响应报文发回给浏览器。响应报文的格式由三部分组成:状态行(HTTP版号+状态码+响应短语)、消息头(同上)、消息体(一般根据消息头中的Content-Type属性确定返回数据格式,比如text/html返回的就是HTML代码,image/jpeg返回的就是图片资源)。浏览器接收到响应报文后同样会进行解析操作,提取出其中消息体的响应内容,对页面进行数据渲染。

        由于每条请求报文只能写一个URI,所以获取到的响应报文中也只会有一个文件。如果希望从服务器获取多个文件就只能发送多条请求报文。

第二节 DNS服务器

        实际上,在浏览器生成HTTP请求报文准备委托给操作系统的协议栈进行下一步传输操作时,会存在这么一个问题:虽然我们已经知道了目标服务器的域名,但是我们无法直接通过域名将消息发送给目标服务器。这里我们需要通过某种手段根据服务器域名来获取到服务器在互联网中的公网IP地址,这个IP地址才是服务器的实际位置。可以将域名理解为服务器的别名,只是为了方便人们进行记忆,而域名对应的公网IP地址才是它真正的名字。

        于是引出了DNS(Domain Name System)这个概念,可以简单理解成它存储着一张映射表,这张映射表中存放着每个域名对应的IP地址。我们只需要将域名发送给它,DNS服务器就会向我们返回一条IP地址。每台计算机上都安装有DNS客户端,里面包含着DNS解析器(实际上就是一段程序代码:gethostbyname(params...))。用户将域名作为程序代码的参数,调用程序就可以获取到IP地址了。

        但是DNS的实际工作原理比我们想象的更加复杂,首先世界上不可能存在一台DNS服务器直接记录有所有的域名和对应IP地址的映射表。所以DNS服务器采取了一种分层级的架构模式:根域服务器(.)、顶级服务器(.com、.jp、.cn等)和权威服务器(.bilibili、.baidu等)。当我们调用DNS解析器时,首先会访问离用户最近的一台DNS服务器(可能有疑问,计算机怎么会知道这台服务器的IP地址?这是因为服务提供商一开始就写死在计算机的网络相关配置文件里了,所以用户可以直接访问,当然用户也可以自己修改成别的DNS服务器的地址)。

        访问最近的一台DNS服务器就会尝试在它的映射表中查询是否存在域名对应的IP地址,有的话就会直接将IP地址返回给客户端,否则就会开始一场全球性的DNS服务器大接力(分层架构的设计开始体现)。该DNS服务器首先会去直接询问根域服务器是否有域名对应的IP地址,根域服务器会从右往左解析域名(例:www.baidu.com),然后发现是(.com)结尾的域名,于是通知该DNS服务器可以去找 .com 对应的顶级DNS服务器,并把 .com 顶级域名服务器的IP地址发给了该DNS服务器,接着该DNS服务器就根据根域服务器给的IP地址去询问 .com 顶级服务器,.com 顶级服务器也从右往左解析域名(例:www.baidu.com,此时由于它自己是.com,就会忽略掉.com的一部分只看www.baidu),发现是(.baidu)结尾的域名,于是通知该服务器可以去找 .baidu 对应的权威DNS服务器,并把 .baidu权威DNS服务器的IP地址发给了该DNS服务器,接着该DNS服务器就根据 .com 顶级服务器给的IP地址去询问 .baidu 权威域名服务器,最终得到目标服务器的IP地址,并将IP地址写进该DNS服务器的映射表中作为缓存(缓存具有时效性,以确保注册信息的准确性)。

        由此就完成了借助DNS服务器来通过服务器域名获取服务器公网IP地址的操作。

第三节 委托协议栈收发数据

        在通过DNS服务器获取到Web服务器的公网IP地址以后,生成的HTTP请求报文终于有了实际的“寄件地址”,能进入下一步的传输阶段。由于浏览器本身作为应用程序并不直接负责对数据进行收发,而是委托了操作系统的协议栈进行和服务器的通信工作(实际上在这一层是由协议栈、网卡驱动和物理网卡进行协作的,这部分的具体内容会在下一章展开)。本节将协议栈的工作抽象化成了构建一个联通了源主机和目标服务器的数据管道,数据能在这个管道中进行双向传输

        协议栈操作这个数据管道主要分为四个阶段:创建阶段连接阶段通信阶段断开阶段。这四个阶段的具体实现都是由协议栈调用Socket库中的程序组件完成的,每个阶段都对应有一个程序组件,协议栈会按照一定顺序调用这些程序组件以实现整体的通信过程(这里采用的是TCP模式)。

        创建阶段:服务器会首先创建一个套接字,创建完成后该套接字就自动进入了等待连接的状态。客户端接着会创建自己的套接字对象,这时双方就都有了套接字对象。

        连接阶段:客户端协议栈会调用Socket库的connect()函数程序(将目标服务器的IP地址和开放的端口号作为函数参数。这里可能会有个问题,IP地址好理解,但是为什么需要多加一个端口号呢?这是因为有IP地址就只能确定通信主机的位置,而无法确定主机中的具体通信对象,一台主机可能同时存在多个通信对象同时工作,为了防止混淆于是用端口号加以区分。),函数程序执行成功会返回目标服务器的IP地址和通信端口并存储在内存中,接下来再进行数据收发操作时会自动使用这个目标服务器返回回来的IP地址和通信端口,至此源主机和目标服务器成功进入了连接阶段。

        通信阶段:连接完成后,客户端主机就可以对目标服务器进行数据的发送和接收操作了,这里主要通过两个函数程序来实现(writeread)。调用write函数程序用户就可以将之前生成的HTTP请求报文转换成数字信息(digital data)进行网络传输。服务器接收到信息后回传响应信息(同样是调用Socket的相关程序组件),这时协议栈会调用read函数程序进行数据的接收,read的参数有两个:socket通信对象和接收缓存地址。接收成功后会将接收到的数据信息存放在接收缓存区中,以供下一步的使用。

        断开阶段:如果双方确认数据收发工作已经完成,那么就可以由任意一方(通常是Web服务器确认发送完响应信息后)断开连接,于是客户端在继续执行read()函数程序时发现Web服务器已经断开,客户端也执行断开程序(close函数),并将套接字对象销毁,双方的连接断开。

        

        

       

  • 8
    点赞
  • 7
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值