DNS Prefetching的小实践
in Tutorial with 22 comments
DNS Prefetching的小实践
in Tutorial with 22 comments

在实践之前,我们先介绍一下“资源预拉取”的性能优化的技术,这是一种通过预拉取可以告诉浏览器用户在未来可能用到哪些资源的技术。

而预取,一共有两部分:一部分是资源的预取;还有一部分是DNS的预解析。

以前这种实践也被称为“prebrowsing”,但这并不是一种单一的技术,实际上可以拆分成很多小点:dns-prefetch, preconnect, prefetch, subresource, prerender等等。

而今天要讲的“DNS prefetching”就是DNS的预解析的一小部分。

它有什么用

DNS prefetching通过指定具体的URL来告知客户端未来会用到相关的资源,告诉客户端可以尽早的解析DNS。

比如我们需要让example.com的静态资源提前加载域名解析,在<head>就可以这么写:

<link rel="dns-prefetch" href="//example.com">

当请求这个域名下的文件时就不需要等待DNS查询了。

它怎样用

如chromium的官方文档所说,chrome 会自动把当前页面的所有带href的link的dns都prefetch一遍:

Manual Prefetch
Chromium uses the "href" attribute of hyperlinks to find host names to prefetch. However, some of those hyperlinks may be redirects, for example if the site is trying to count how many times the link is clicked. In those situations, the "true" targeted domain is not necessarily discernible by examining the content of a web page, and so Chromium not able to prefetch the final targeted domain.

再根据官方文档发现,a标签的默认启动在HTTPS不起作用:

DNS Prefetch Control
By default, Chromium does not prefetch host names in hyperlinks that appear in HTTPS pages. This restriction helps prevent an eavesdropper from inferring the host names of hyperlinks that appear in HTTPS pages based on DNS prefetch traffic. The one exception is that Chromium may periodically re-resolve the domain of the HTTPS page itself.

<head>就加上下面的一句代码,就可以强制启动:

<meta http-equiv="x-dns-prefetch-control" content="on">

它能带来什么

合理的dns prefetching能对页面性能带来50ms ~ 300ms的提升,有人做了这方面的统计。

再如chromium的官方文档所说,dns prefetching的网络消耗是极低极低的:

Each request typically involves sending a single UDP packet that is under 100 bytes out, and getting back a response that is around 100 bytes. This minimal impact on network usage is compensated by a significant improvement in user experience.

实践

这次实践是在lpisme主题上实现,主要是对header.php文件操作。而DNS prefetching的实践对象就是www.linpx.com用的CDN上的静态资源,当然我博客只是CDN了图片资源和公共JS

打开header.php,在<meta charset="<?php $this->options->charset(); ?>">后面,添加:

<meta http-equiv="x-dns-prefetch-control" content="on">
<link rel="dns-prefetch" href="<?php $this->options->cdn_add(); ?>" />
<link rel="dns-prefetch" href="//cdn.bootcss.com" />

其中<?php $this->options->cdn_add(); ?>是主题设置里的七牛云存储域名

还有,如果你没有开启HTTPS,<meta http-equiv="x-dns-prefetch-control" content="on">这句是可以删掉的

为了更严谨,还需要添加一个条件判断来圈住上面的代码

<?php if ($this->options->cdn_add): ?>
···
<?php endif; ?>

至此lpisme主题完成DNS prefetching的功能的添加。如果嫌麻烦,我已经push到github上了,直接clone或fetch项目即可。

更新

在上面的代码中再添加一句,如下

<link rel="dns-prefetch" href="//secure.gravatar.com" />

参考

国内的

国外的

Responses
  1. 分享是美德,谢谢博主的分享。

    Reply
    1. @凯哥自媒体

      谢谢 :)

      Reply
  2. 一直想换Typecho,今天看到你这主题终于有动力了
    有一个问题想问一下,文章post-cover是怎么是设置的=、=

    Reply
    1. @予而不语

      post-cover? 是指文章标题前面的小图标吧?还是指缩略图?

      如果是小图标,则:进入文章编辑,在最后可以看到上面的自定义字段
      其中,有lamp 、 eye 、 code 、 list 、 quote 、 share 、 chat 、 locked 、 images 、 ad 和 不填

      如果是缩略图,则:进入文章编辑,自定义字段 thumb ,后面跟着的值带上你的图片URL,或者是第一个附件图片 ---> 文章内图片 ---> 默认缩略图 ---> 无

      Reply
      1. @Chakhsu Lau

        非常感谢~

        Reply
        1. @予而不语

          不用 :)

          Reply
  3. 亲你的配图哪里找的啊

    Reply
    1. @macbolo

      百度或者的谷歌的识图搜图的功能就可以找到一堆 :)

      Reply