为了搞清楚 DNS,我花了 1.99 买了一个域名

前言: 转眼已经工作两年有余,最近也是补习了一下计算机网络基础这方面的知识。于是打算开一个新坑,尽可能详细地把前端八股文之一的-----在浏览器搜索栏输入一个 url 地址之后发生了什么? 这件事说清楚。一方面把零碎的知识点整合到一起,另一方面是算是总结自己最近学习到的网络相关知识。

☕️由于本篇内容不是介绍你的计算机是如何接入互联网的,所以忽略一切 NAT 等其它相关知识。

🎁那么让我们开始吧,本篇作为开篇,首先介绍 DNS(Domain Name System)域名解析系统。

附:购买凭证,我购买了一个 fffang.lol 的域名。
image.png


一. 我们在浏览器搜索栏输入了什么?

  1. 假设我们现在想访问百度首页, www.baidu.com 这段文字像是被刻在了 DNA 里了一样,我们几乎是条件反射的打出了这段字符。也正因为像人的本能一样,在此之前我从没考虑过 www.baidu.com 这段文字到底是什么?就好像一切就本该这样似的。不行,我得研究研究🤔。
    1.gif

  2. 要想接着聊下去,我们首先得知道什么是ip(internet protocol)。想必你或多或少听说过 IP 地址这个概念,并且我敢保证你现在一定在使用某一个 ip 地址在看我的这篇文章。你可以在百度搜索栏 ip地址 这几个关键词,它的搜索结果会显示出一个本机 ip 地址。这个 ip 就是百度服务器可以找到你的原因,它相当于你家的门牌号,百度就是依靠它把首页的页面返回给你的。
    image.png

  3. 聪明的你可能想到了,那对应着百度是不是也应该会有一个 ip 呢?没错,如果你要访问百度,首先你的计算机也得先找得到百度才可以。我们可以在终端输入 ping www.baidu.com。下面这段 153.3.238.110 就是百度的 ip 地址。

  4. 其实 153.3.238.110 这串数字才是 www.baidu.com 的真身,你在地址栏上输入的 www.baidu.com 最终会被转换成 153.3.238.110 ,然后根据这串数字和百度服务器交互。

    你可能会去地址栏直接输入这串数字来验证,但是由于现在绝大部分网站都不允许直接 ip 访问,所以你可能会收到一个 403 的警告)

  5. 上面这个例子中的 www.baidu.com 被我们称为域名(domain name),域名常常需要配合 ip来一起使用。先有域名没有 ip 是可以的,也正因为这个特性,也衍生出了抢注域名这个行业。想当初 qq.com 这个域名就是腾讯做大以后花了十几万美元从外国人手中买回来的。

  6. 很显然,相比于记下 153.3.238.110 这段毫无记忆规律的数字来讲,www.baidu.com 就显得格外亲切。所以域名最大的用处就是帮助人们减轻记忆负担。

  7. 让我们举一反三,某一天百度服务器升级,需要更新成另外一台不同 ip 的服务器,那么对于用户来讲,我们压根不用考虑百度更换 ip 这件事的,只需要记住 www.baidu.com 就行了,这也是使用域名的优势之一。

  8. 那么到底谁帮我们做了域名自动转化为 ip 这件事呢?别着急,我们再仔细研究一下域名。

二. 域名的组成

  1. 我们依旧拿 www.baidu.com 这个域名来分析。其实我们平常拼写的域名有一个很重要但是很不起眼的组成部分: “.” ,其实完整的域名应该是 www.baidu.com.注意: 这里的 com. 尾部多了一个点,这个点被称为根域名。 什么?一个就是根域名了?是的,你没听错。根域名服务器是 13个 固定 ip 所组成服务器群的简称。
    image.png
    根域名服务器不保存具体 ip 和完整域名的信息对照表,它保存的只是所有一级域名服务器ip 地址信息。

  2. 上面提到的 .com ,这一段被称为一级(或顶级)域名一级域名服务器同理,也只保存 二级域名 的服务器 ip 信息。

  3. 紧接着就是 .baidu 这一部分被称为二级域名,在此之后,我们对二级域名之后等级的操作,都将由二级域名服务器来进行管理。

  4. 对,你现在脑子里浮现的结论是对的。 .www 这部分被称为 三级域名,只不过它前面没有四级域名罢了。

  5. 实际上 DNS 整套体系架构的是类似于下面这样的结构,好像一个树根逐渐向外扩散。
    image.png

三. 购买域名亲自体验

  1. 纸上得来终觉浅,不如你花一元来亲自体验一下整个过程,你会对 DNS 有一个全新的理解。

  2. 由于一些魔法原因,无法演示我在国外的购买方式,但是国内阿里云是一样可以的。

  3. 百度搜索:阿里云、域名关键词即可,我们会来到阿里云的域名购买界面。注册域名第一步就是让你选择 一级 域名的字符。你需要在这里先验证你想要注册的域名是否已经被申请了。
    image.png

  4. 假如你输入 baidu,你会发现 .com 的一级域名服务器已经保存了 baidu 的二级域名相关信息。
    image.png
    我们试着换一个二级域名,如果想购买,方法也很简单,页面上已经写的很清楚了。这里省略如何购买等步骤,(避免有打广告的嫌疑🥱)
    image.png

  5. 当你点击购买 pbkfang.com 这个域名,确认付款的一瞬间,背后发生了什么?这是你需要清晰知道的:

    1. 首先阿里云会通知 .com 这个一级域名服务器,说:“.pbk 这个二级域名 已经被注册了,你们不要再使用了!”
    2. 接着世界各地的 .com 服务器就会互相转告“.pbk不能用了,请互相通知。” 直到所有的.com 一级域名服务器全都知道这个消息。
    3. 阿里云服务器此时就中保存着对你 xxx.pbkfang.com 的翻译权。(也就是域名转真实 ip 这一步)此时的阿里的 DNS 服务器就被称为 pbk.com权威域名服务器
    4. 以后全世界的人访问 pbk.com 的时候,最终都会走向阿里云这个服务器来进行查询请求。
  6. 你是否真正购买域名其实不重要,在这一步我主要是想让大家理解为什么域名要从后往前看,不要按照人类直觉从 www 看起。其实 www 只不过是很已经被大众认知,大家为了方便自家网站容易被浏览才设置为 www 的,其实 wwwwwwxxxyy 任意字母组合都可以,随你喜欢,只不过不容易被大家接受罢了。

  7. 所以你可能已经看出来了,域名最关键的部分就是 一级域名和二级域名,后面三级四级随你喜欢怎么填写都可以,接下来我将演示为什么是这样的。

三. 域名配置和解析的过程

  1. 由于我没有购买云服务器,所以只能开启本地的 vite 打包项目,来作为 DNS 解析演示,随后我会在后台配置一个 test 的三级域名。

  2. 我首先 npm run 了一个 vite 项目,所以我可以在在局域网下的192.168.124.5:4399 地址访问一个 http-server ,浏览器可以即可访问这个项目。
    2.gif
    如果你不理解这句话的含义,那么这个过程的基本原理我也写过一篇文章,感兴趣可以查阅
    🎁前端代码是如何与后端服务器的交互的

  3. 我现在在浏览器地址栏输入 test.fffang.lol:4399。我们分析一下接下来发生的事情(我们暂时忽略所有缓存查询)此时一条 DNS 查询的请求将发往你的网关(可以粗略地理解为你家光猫或者路由器)

    1. 网关向根域名服务器询问 .lol 一级域名服务器ip 是什么?
    2. 根服务器告诉网关:“ .lol服务器的 ip 是 x.x.x.x
    3. 网关接着去问 .lol服务器:“fffang.lol 域名服务器在哪?”
    4. .lol服务器 最后告诉网关,在阿里云的一个 ip 为 x.x.x.x 的服务器上
    5. 此时阿里作为你的权威服务器,一定保存着 fffang.lol 的所有域名信息。
    6. 但由于你并没有配置 .test 这个二级域名的相关信息,所有你的网关没有拿到相关域名的任何信息。
    7. 此时网关告诉浏览器,“我找了一圈,但是没找到相关 ip 地址信息。”
    8. 然后浏览器很无奈的返回 502 给你
      3.gif
  4. 接下来我在后台配置一下 DNS 服务器的相关信息,关于配置的细节问题,这里不过多展开。当我点击保存以后,正确的说法应该是:

    .fffang.lol 域名下,会多一条 A 类型的记录,记录的名称是 test,所映射的 ipv4 类型地址是 192.168.124.5

    image.png

  5. 此时我们再访问一下 test.fffang.lol:4399,页面已经可以正常展示了。
    4.gif

四. 使用 dig 命令验证

  1. 这里有一个命令行工具可以帮我们更加清晰的观测到以上发生的一切步骤。dig +trace test.fffang.lol 这里的 “+” 不能省略,这里我清除了一些无用的数据,打印结果如下:

    ; <<>> DiG 9.10.6 <<>> +trace test.fffang.lol
    ;; global options: +cmd
    .			66328	IN	NS	e.root-servers.net.
    .			66328	IN	NS	h.root-servers.net.
    .			66328	IN	NS	d.root-servers.net.
    .			66328	IN	NS	i.root-servers.net.
    .			66328	IN	NS	b.root-servers.net.
    .			66328	IN	NS	l.root-servers.net.
    .			66328	IN	NS	a.root-servers.net.
    .			66328	IN	NS	c.root-servers.net.
    .			66328	IN	NS	g.root-servers.net.
    .			66328	IN	NS	f.root-servers.net.
    .			66328	IN	NS	j.root-servers.net.
    .			66328	IN	NS	k.root-servers.net.
    .			66328	IN	NS	m.root-servers.net.
    ;; Received 228 bytes from 192.168.124.1#53(192.168.124.1) in 18 ms
    
    lol.			172800	IN	NS	a.nic.lol.
    lol.			172800	IN	NS	b.nic.lol.
    lol.			172800	IN	NS	c.nic.lol.
    lol.			172800	IN	NS	d.nic.lol.
    ;; Received 623 bytes from 192.58.128.30#53(j.root-servers.net) in 26 ms
    
    fffang.lol.		3600	IN	NS	coraline.ns.cloudflare.com.
    fffang.lol.		3600	IN	NS	cash.ns.cloudflare.com.
    fffang.lol.		900	IN	NSEC	fffbaa.lol. NS RRSIG NSEC
    ;; Received 234 bytes from 212.18.249.146#53(d.nic.lol) in 94 ms
    
    test.fffang.lol.	300	IN	A	192.168.124.5
    ;; Received 60 bytes from 173.245.59.81#53(cash.ns.cloudflare.com) in 206 ms
    
    
  2. 如果你够仔细的话,会发现上面所有关于域名的展示,末尾都加上了一个 “.”
    image.png

    我接下来会解释一下这串回复的关键信息,请结合上面的代码块的行数继续往下看。

  3. 第 16 行:dig 尝试向网关的 DNS 服务器查询相关信息,命令首先收到(Received) 192.168.124.1(我家的光猫)这台服务器上 53端口返回的数据包,包中记录了 13 个根节点的地址信息,对应第3行至15行代码。

  4. 然后 dig 会同时向这 13 台根服务器发起查询请求,谁最先回应就采用谁的答复。第 22 行代码验证了这件事,表示 dig 最先接收到了来自 j.root-servers.net 这台根服务器的回应。数据内容为: 18-21 行代码。一共有四个 a、b、c、d 四台 .lol. 的一级域名服务器。

  5. 然后 dig 继续并发向这四台服务器发起查询请求。在 27 行代码中表明最先收到的回复是来自d.nic.lol 这台一级域名服务器。

  6. 紧接着最后一步查询发送给了我的权威域名服务器 cash.ns.cloudflare.com 查询到的结果为第 29 行代码所对应的信息。

       test.fffang.lol.	300	IN	A	192.168.124.5
    ;; Received 60 bytes from 173.245.59.81#53(cash.ns.cloudflare.com) in 206 ms
    

    可以看到,这个信息和我之前在后台配置的数据完全一致。
    image.png

  7. 至此 DNS 解析过程结束, dig 返回结果打印到终端上。

五. 思维拓展

  1. 如果简单用我们前端开发容易理解的方法去思考上面的过程的话,那么就可以用下面这样的代码来表示。首先我们的 DNS 就需要设计成下面的数据结构:

    // 抽象的解释
    const DNS = {
      ".root": {
        自己本身地址: "0.0.0.0",
        一级域名服务器地址: [
          {
            ".lol": {
              自己本身地址: "1.1.1.1",
              二级域名服务器信息: [
                {
                  ".fffang": {
                    服务器地址: "1.1.1.2",
                    域名记录: [{ 类型: "A", ip: "192.168.124.5" }],
                  },
                },
              ],
            },
          },
        ],
      },
    };
    
  2. 那么查找域名的过程就是:请你设计一个函数,查询 .fffang 这个二级域名的服务器地址,那么你必须得从 root 开始,一层一层查询到 .lol ,最终找到 ffffang

  3. 有没有觉得这个很像一个东西?没错,请打开你项目的路由表结构看一下,这两个有异曲同工之妙。
    image.png

  4. 我们在配置路由的时候,也是从 / 路由开始配置,然后就是 childrenchildren 里面又包含子路由子路由还可以嵌套子路由。那么在页面上输入路由地址的时候,也是 / 路径开始,然后输入根路径下的 /test/page/index 这样的形式,只不过和的查找顺序域名恰好相反而已。路由是从左到右,域名是从右向左

六. 关于 DNS 缓存

  1. DNS 解析的过程还牵扯到许多缓存的问题,和缓存更新的问题,为了简化主旨内容,在文中并没有涉及到相关内容。

  2. 浏览器其实本身也会做一层 DNS 缓存,如在 chrome 浏览器输入 chrome://net-internals/#dns 即可查看你浏览器所做的相关 DNS 缓存,它是浏览器查询 DNS 的第一个本地查询点,此时没有任何网络请求产生。
    image.png

  3. 当浏览器进程发起的请求发现自身没有缓存后,一条查询请求会发向操作系统本身的存根解析器(Stub resolver),存根解析器也没有查询到后,该请求才会被转发给你的网关(你家的猫或者路由器)。

  4. 然后运营商接收到这条请求后,也会在自身 DNS 服务器 的缓存中查询,最后不断转发不断查询,直到根服务器,然后一级域名

  • 27
    点赞
  • 27
    收藏
    觉得还不错? 一键收藏
  • 1
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值