数据URI会减慢页面加载速度

6

我写了一个脚本,将所有内联图像替换为数据URI,以减少HTTP请求并加快移动设备的加载时间。

不幸的是,我发现加载速度更慢了。我觉得这取决于HTML文件的大小(大约100KB而不是5KB左右):)?还是数据URI还有其他会拖慢页面加载的问题吗?

浏览器是否必须在完全下载整个文档后才能加载其中链接的资源?或者说,例如在文档顶部的CSS和JavaScript之类的链接资源会在浏览器完成下载整个文档之前加载吗?

CSS如何工作?浏览器是否必须在读取所有CSS设置之前加载完整个CSS文件?

如果是这样,是否最好为数据URI单独创建CSS文件:

  1. 加载结构的CSS(没有数据URI)
  2. 加载背景图像的CSS(所有背景图像都以URI格式)

“单独缓存的jpg文件”是否比“包含在缓存的CSS文件中的URI图像”加载更快?

对于如何使用数据URI还有其他建议吗?

3个回答

7
发表了一篇博客文章:在移动设备上,数据 URI 的加载速度比源链接(例如使用带有 src 属性的 img 标记)平均慢6倍

[...]
因此,可以想象当测量数十万次移动页面浏览时,我惊讶地发现使用数据 URI 加载图像平均比使用二进制源链接 img 标记慢6倍

虽然我没有深入研究这篇文章,但我认为问题的一部分可能是解码 base64 编码的数据 URI 所需的 CPU 功率。

作者建议仅“偶尔使用小图像”的数据 URI。


2
谢谢。我还发现了这个:https://dev59.com/YnNA5IYBdhLWcg3wBo9m。我不会使用URI,甚至不会在单独的CSS文档中使用,因为它会消耗CPU...谢谢。 - user1087110
我想主要问题在于对于每个图像,您都增加了整体下载的大小,因为base64编码的字符串比二进制等效字符串要大得多。 - Rob Evans

1
HTML内容按照它们在HTML文件中出现的顺序加载。 大尺寸的Data URI会减缓页面速度。 IE浏览器(IE6)不支持大尺寸的Data URI。 推荐并通常使用图像大小小于20KB的Data URI。 您可以选择压缩图像、js和css以提高页面速度。

1
谢谢回答!您知道为什么大尺寸的URI会减慢页面吗?我不关心低于EI9版本的问题 :) 为什么200kb的数据URI比分离的200kb的jpg文件更糟糕?您知道浏览器是否必须在加载HTML文件之前完成其加载的链接资源吗?您知道CSS文件是否必须完全加载才能设置所有CSS设置吗? - user1087110

0

简而言之:如果图像很大,使用数据URI将延迟HTML的加载时间。

我编写了一个脚本,用数据URI替换所有内联图像,以减少HTTP请求并加快移动设备的加载时间。

如果执行请求的时间大于下载图像的时间,则这是一个好主意,因为浏览器无论如何都需要下载图像数据(无论是否使用数据URI)。如果将图像嵌入HTML中作为数据URI,则会增加HTML的总大小,其大小为所有图像的大小之和(加上数据URI编码约33%)。

例如,如果打开新请求的连接时间为1秒,您的图像每个需要0.2秒下载,您有10个图像,您的HTML需要0.5秒下载,则需要:

  • 仅HTML需要1秒+0.5秒=1.5秒
  • 图像需要10 x (1 + 0.2)秒=12秒

如果将图像编码为HTML中的数据URI(大小增加33%):

  • 1s + 0.5s + (10 x 0.2s x 1.33) = 4.2s
  • (并且没有外部请求图片)

这里的一个重要因素是获取整个页面HTML源代码所需的时间(1.5秒与3.5秒)。如果在绘制页面时必须拥有图片,则数据URI将是一种良好的优化方式。如果可以异步加载大部分带有图片的页面,那么最好优化完全下载HTML。

如果您的图片很大,将它们编码为数据URI会更糟糕。如果每张图片需要1秒钟下载,并且其他因素相同:

使用外部图片:

  • 仅用1.5秒+0.5秒下载HTML
  • 10 x(1秒+1秒)=20秒下载图片

使用数据URI:

  • 1秒+0.5秒+(10 x 1秒x 1.33)=14.8秒直到HTML下载完成!
我猜这取决于HTML文件的大小(大约100kb而不是5kb左右):)?
当浏览器下载页面的HTML源代码时,它开始解释和显示它。当它到达引用单独资源的元素时,例如具有外部URI(而不是数据URI)和(异步)脚本标记的图像,它将开始或排队下载它们,但继续下载和处理页面的HTML。
这意味着随着页面的下载,用户看到越来越多的内容,尽管没有加载图像和有时字体。
当浏览器到达带有数据URI的图像标记时,它必须在处理HTML源代码中该标记后面的任何内容之前下载和解析整个数据URI字符串。因此,如果您的原始HTML为1kb,并嵌入了1MB的图像数据URI,则当浏览器到达该图像标记时,会暂停,因为它下载了由数据URI编码的图像占用的1MB HTML源代码,然后才能处理页面的HTML的更多内容。
浏览器是否必须在完全下载完整个文档之前才能加载其中的链接资源?或者链接的资源,例如文档顶部的CSS和JavaScript,在浏览器完成完整文档之前就已经加载了吗?

链接的资源有自己的加载和解析逻辑。 <script> 标签将同步加载 - 阻止浏览器解析 HTML 源代码,直到引用的脚本被加载并执行 - 除非它们具有 async 属性。外部样式表将并行下载,但会阻塞渲染,直到它们被加载。

这里有一个很好的解释

如果是这样,是否最好为数据 URI 单独使用 CSS 文件,像这样:

  1. 为结构加载 CSS(没有数据 URI)
  2. 为背景图像加载 CSS(所有背景图像都以 URI 格式) “单独缓存的 jpg 文件” 是否比 “包含在缓存的 css 文件中的基于 URI 的图像” 加载更快?

如何使用数据 URI 的其他建议?

这取决于您要优化什么。您更关心首次呈现时间,即使页面不完整吗?还是更关心整个页面,包括所有图像,完全呈现的时间?

像任何工具一样,没有适用于所有情况的普遍规则,比如“总是使用数据URI”或“永远不要使用数据URI”。一个好的经验法则是对于小图标等小图片使用数据URI。Webpack的url-loader会自动实现这个逻辑,对于指定大小以下的文件使用数据URI,否则使用外部URL。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接