返回介绍

使用流式处理来提升页面性能

发布于 2024-06-05 21:19:56 字数 3036 浏览 0 评论 0 收藏 0

Astro 的 SSR 使用 HTML 流式处理来在组件可用时将其发送到浏览器,以便更快地加载页面。为了进一步提升你的页面性能,你可以策略性地构建你的组件,即通过避免阻塞的数据获取来优化它们的加载速度。

如下的重构示例演示了如何通过将获取调用移动到其他组件,并将它们从阻塞页面渲染的组件中迁移出来,以提高页面性能。

以下页面在 frontmatter 中会 await 一些数据。而 Astro 会等待所有的 fetch 调用解决后,再将 HTML 发送到浏览器。

src/pages/index.astro
---
const personResponse = await fetch('https://randomuser.me/api/');
const personData = await personResponse.json();
const randomPerson = personData.results[0];
const factResponse = await fetch('https://catfact.ninja/fact');
const factData = await factResponse.json();
---
<html>
  <head>
    <title>A name and a fact</title>
  </head>
  <body>
    <h2>A name</h2>
    <p>{randomPerson.name.first}</p>
    <h2>A fact</h2>
    <p>{factData.fact}</p>
  </body>
</html>

现在可将 await 调用移入粒度较小的组件可以让你充分利用 Astro 的流式处理。使用以下组件来执行数据获取,Astro 可以先渲染一些 HTML,例如标题,然后在数据准备好时渲染段落。

src/components/RandomName.astro
---
const personResponse = await fetch('https://randomuser.me/api/');
const personData = await personResponse.json();
const randomPerson = personData.results[0];
---
<p>{randomPerson.name.first}</p>
src/components/RandomFact.astro
---
const factResponse = await fetch('https://catfact.ninja/fact');
const factData = await factResponse.json();
---
<p>{factData.fact}</p>

下面的 Astro 页面使用这些组件可以更早地渲染页面的部分内容。<head><body><h2> 标签则不再被数据获取所阻塞。接着,服务器将并行获取 RandomNameRandomFact 的数据,并将生成的 HTML 流式传输到浏览器上。

src/pages/index.astro
---
import RandomName from '../components/RandomName.astro';
import RandomFact from '../components/RandomFact.astro';
---
<html>
  <head>
    <title>A name and a fact</title>
  </head>
  <body>
    <h2>A name</h2>
    <RandomName />
    <h2>A fact</h2>
    <RandomFact />
  </body>
</html>

直接包含 Promises

你也可以直接在模板中包含 promises。它不会阻塞整个组件,而是会并行地解决 promise,并只阻塞其后的标记。

src/pages/index.astro
---
const personPromise = fetch('https://randomuser.me/api/')
  .then(response => response.json())
  .then(arr => arr[0].name.first);
const factPromise = fetch('https://catfact.ninja/fact')
  .then(response => response.json())
  .then(factData => factData.fact);
---
<html>
  <head>
    <title>A name and a fact</title>
  </head>
  <body>
    <h2>A name</h2>
    <p>{personPromise}</p>
    <h2>A fact</h2>
    <p>{factPromise}</p>
  </body>
</html>

在这个例子中,A name 会在 personPromisefactPromise 加载时渲染。一旦 personPromise 解决了,A fact 就会出现,factPromise 也将在完成加载时渲染。

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。
列表为空,暂无数据
    我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
    原文