HTML <link> 资源预加载
<link> 外部资源链接元素
HTML 外部资源链接元素(<link>)规定了当前文档与外部资源的关系。该元素常用于链接样式表,此外也可以被用来创建站点图标(比如 PC 端的 favicon 图标和移动设备用以显示在主屏幕的图标)
<link rel="stylesheet" href="/path/to/style.css">
<link rel="icon" href="favicon.ico">
<link rel="apple-touch-icon-precomposed" sizes="114*114" href="apple-icon-114.png" type="image/png">
preload
通过<link>
标签的rel
属性设置为preload
向浏览器声明一个需要提前加载的资源。加载完成后不会立即执行,在需要执行的时候再执行,将加载和执行分离开。
<link rel="preload" as="style" href="/path/to/style.css">
<link rel="preload" as="script" href="/path/to/script.js">
在页面加载的早期就开始获取隐藏在 CSS 或者 JS 中的资源(图片、字体、样式、视频等),更不容易阻塞页面的初步渲染,进而提升性能。
preload
将提升资源加载的优先级,不管资源是否使用都将提前加载。因此要避免滥用preload
,若不确定资源是必定会加载的,则不要错误使用preload
,给页面带来沉重的负担。
对跨域的文件进行预加载时,要给<link>
加上crossorigin
属性,若不指定crossorigin
属性,则会采用匿名模式的 CORS 去加载。预加载请求缺少Origin
请求头字段,在之后对该资源的请求中则无法命中,造成两次重复的请求。
<link rel="preload" as="font" crossorigin href="https://www.baidu.com/path/to/font.woff">
prefetch
通过将<link>
标签的rel
属性设置为prefetch
向浏览器声明一个可能需要加载的资源,它会将下载资源的优先级降到最低,浏览器会在闲时去加载对应的资源,并将其存储在缓存中。当用户访问时可以快速的从浏览器缓存中得到,与preload
不同的是,它会额外发起一次请求。
同时使用preload
和prefetch
会导致两次重复的请求。
实例:
<html>
<head>
<title>test</title>
<link rel="prefetch" as="font" href="http://at.alicdn.com/t/webfont_q7lddel88i.woff2">
<link rel="prefetch" as="style" href="https://unpkg.com/element-ui/lib/theme-chalk/index.css">
<link rel="prefetch" as="script" href="https://cdn.jsdelivr.net/npm/vue@2.6.14/dist/vue.js">
<link rel="prefetch" as="image" href="https://www.runoob.com/try/demo_source/smiley-2.gif">
<link rel="prefetch" as="audio" href="https://www.runoob.com/try/demo_source/horse.mp3">
<style>
@font-face {
font-family: 'webfont';
src: url('http://at.alicdn.com/t/webfont_q7lddel88i.woff2') format('woff2');
}
.font {
font-family: 'webfont';
}
</style>
</head>
<body>
<div>test</div>
</body>
<script>
setTimeout(() => {
const dom = document.createElement('link')
dom.setAttribute('rel', 'stylesheet')
dom.setAttribute('href', 'https://unpkg.com/element-ui/lib/theme-chalk/index.css')
document.head.append(dom)
const dom1 = document.createElement('div')
dom1.innerHTML = 'abc'
dom1.setAttribute('class', 'font')
document.body.append(dom1)
const dom2 = document.createElement('script')
dom2.setAttribute('src', 'https://cdn.jsdelivr.net/npm/vue@2.6.14/dist/vue.js')
document.head.append(dom2)
const dom3 = document.createElement('img')
dom3.setAttribute('src', 'https://www.runoob.com/try/demo_source/smiley-2.gif')
document.body.append(dom3)
const dom4 = document.createElement('audio')
dom4.setAttribute('src', 'https://www.runoob.com/try/demo_source/horse.mp3')
document.body.append(dom4)
}, 5000)
</script>
</html>
加载设置了 prefetch 的 link 标签上的字体文件时,chrome 浏览器向服务器请求了两次,没有使用缓存中的字体文件:
刷新页面后加载字体文件变成 disk cache 中加载之后才使用了 prefetch cache:
但是设置了 preload 的 link 标签没有这种情况。
参考文章:
1.用 preload 预加载页面资源