资源计时

资源时序 (Resource Timing) 是 Performance API 的一部分,它能检索和分析应用程序资源加载的详细网络时序数据。应用程序可以使用这些时序指标来确定,例如,加载特定资源(如图片或脚本)所需的时间,无论是隐式地作为页面加载的一部分,还是显式地通过 JavaScript,例如使用 fetch() API。

文档中的每个资源都将由一个 PerformanceResourceTiming 条目表示(继承自 PerformanceEntry 接口),其 entryType"resource"

对于每个 PerformanceResourceTiming 条目,将记录一个资源加载时间线,其中包含网络事件的高精度时间戳,例如重定向开始和结束时间、DNS 查询开始和结束时间、请求开始、响应开始和结束时间等。除了时间戳之外,还包括提供资源信息的其他属性,例如获取的资源大小,或者发起获取的资源类型。

资源加载时间戳

时间戳图,按获取资源时记录的顺序显示时间戳 图 1. 资源加载时间戳(来源)。

应用程序可以获取资源加载各个阶段的时间戳。此 API 提供的时间戳是:

  1. startTime:资源加载过程开始前的即时时间戳。
  2. redirectStart:发起重定向的获取操作的时间戳。
  3. redirectEnd:在收到最后一个重定向响应的最后一个字节后的即时时间戳。
  4. workerStart:Service Worker 线程开始前的即时时间戳。
  5. fetchStart:浏览器开始获取资源前的即时时间戳。
  6. domainLookupStart:浏览器开始为资源进行域名查找前的即时时间戳。
  7. domainLookupEnd:浏览器完成为资源进行域名查找后的即时时间戳。
  8. connectStart:用户代理开始建立与服务器连接以检索资源前的即时时间戳。
  9. secureConnectionStart:如果资源是通过安全连接加载的,则在浏览器开始握手过程以保护当前连接前的即时时间戳。
  10. connectEnd:浏览器完成与服务器建立连接以检索资源后的即时时间戳。
  11. requestStart:浏览器开始从服务器、缓存或本地资源请求资源的即时时间戳。
  12. responseStart:浏览器从服务器、缓存或本地资源接收到响应的第一个字节后的即时时间戳。
  13. responseEnd:浏览器接收到资源的最后一个字节后的即时时间戳,或者传输连接关闭前的即时时间戳,以较早者为准。

资源大小

PerformanceResourceTiming 接口有三个属性可用于获取资源的尺寸数据。transferSize 属性返回获取资源的大小(以字节为单位),包括响应头字段和响应体内容。

encodedBodySize 属性返回从获取(HTTP 或缓存)中接收到的内容体的大小(以字节为单位),在移除任何应用的编码之前。decodedBodySize 返回从获取(HTTP 或缓存)中接收到的消息体的大小(以字节为单位),在移除任何应用的编码之后。

其他属性

PerformanceResourceTiming 接口提供了额外的资源信息。请参阅参考文档以获取完整的属性列表。

典型的资源时序指标

PerformanceResourceTiming 条目提供的信息通常用于以下类别的计算:

  • 测量 TCP 握手时间 (connectEnd - connectStart)
  • 测量 DNS 查询时间 (domainLookupEnd - domainLookupStart)
  • 测量重定向时间 (redirectEnd - redirectStart)
  • 测量请求时间 (responseStart - requestStart)
  • 测量 TLS 协商时间 (requestStart - secureConnectionStart)
  • 测量获取时间(不含重定向)(responseEnd - fetchStart)
  • 测量 ServiceWorker 处理时间 (fetchStart - workerStart)
  • 检查内容是否被压缩 (decodedBodySize 应不等于 encodedBodySize)
  • 检查是否命中本地缓存 (transferSize 应为 0)
  • 检查是否使用了现代快速协议 (nextHopProtocol 应为 HTTP/2 或 HTTP/3)
  • 检查资源是否是渲染阻塞的 (renderBlockingStatus)

PerformanceResourceTiming 参考页面包含测量所有这些指标的示例代码。通常,测量这些指标的代码如下所示:

js
const observer = new PerformanceObserver((list) => {
  list.getEntries().forEach((entry) => {
    const request = entry.responseStart - entry.requestStart;
    if (request > 0) {
      console.log(`${entry.name}: Request time: ${request}ms`);
    }
  });
});

observer.observe({ type: "resource", buffered: true });

跨域计时信息

当启用 CORS 时,许多时序属性的值将返回零,除非服务器的访问策略允许共享这些值。这要求提供资源的服务器发送 Timing-Allow-Origin HTTP 响应头,其值指定了允许访问受限制时间戳值的来源或来源。

默认情况下,当从与网页本身不同的来源加载资源时,返回值为 0 的属性包括:redirectStart, redirectEnd, domainLookupStart, domainLookupEnd, connectStart, connectEnd, secureConnectionStart, requestStart, 和 responseStart

例如,为了允许 https://mdn.org.cn 查看资源时序信息,跨域资源应发送:

http
Timing-Allow-Origin: https://mdn.org.cn

管理资源缓冲区大小

如果您的网站或应用程序获取的资源超过 250 个,并且您想记录超过 250 个 PerformanceResourceTiming 条目,您需要增加资源时序缓冲区的大小。

要设置浏览器性能资源数据缓冲区的大小,请使用 Performance.setResourceTimingBufferSize() 方法,要清除浏览器性能资源数据缓冲区,请使用 Performance.clearResourceTimings() 方法。

要接收浏览器资源时序缓冲区已满的通知,请监听 resourcetimingbufferfull 事件。

以下调用允许浏览器性能时间线中最多容纳 500 个 "resource" 性能条目。

js
performance.setResourceTimingBufferSize(500);

有关更多信息,请参阅 管理缓冲区大小

另见