prerender() hook

有关如何预渲染应用程序,请参阅 指南 > 预渲染 (SSG)

提供 URL

大多数时候,我们使用 prerender() hook 来提供参数化路由的 URL。

// /pages/movie.page.route.js
// Environment: Node.js

export default '/movie/@movieId`
// /pages/movie.page.server.js
// Environment: Node.js

export { prerender }

async function prerender() {
	const movies = await Movie.findAll()
	const moviePageURLs = movies.map((movie) => '/movie/' + movie.id)
	return moviePageURLs
}

如果我们没有参数化路由, 那么我们可以在不定义任何 prerender() hook 的情况下预渲染我们的应用程序

prerender() hook 在我们运行 $ vite build 时被调用。 (在开发中永远不会调用 prerender() hook)

提供 pageContext

如果我们有大量要预渲染的页面,那么运行命令 $ vite build 可能会变慢

我们可以通过在 prerender() hook 中提供页面的 pageContext 来显著加快速度

// /pages/movie.page.route.js
// Environment: Node.js

export default '/movie/@movieId`
// /pages/movie.page.server.js
// Environment: Node.js

export { prerender }

async function prerender() {
  const movies = await Movie.findAll()

  const moviePages = (
    movies
    .map(movie => {
      const url = '/movie/' + movie.id
      const pageProps = { movie }
      const pageContext = { pageProps }
      return {
        url,
        // 因为我们已经提供了 `pageContext`,
        // vite-plugin-ssr *不会* 为 `url` 调用 `onBeforeRender()` hook
        pageContext
      }
      /* 我们也可以只返回 `url` 而不提供 `pageContext`。
       * 在这种情况下,vite-plugin-ssr 会调用 `onBeforeRender()` hook。但是这会很浪费,
       * 因为我们已经从 `await Movie.findAll()` 调用中获得了所有电影的数据
       * 相反,我们可以提供 `pageContext` 来加快预渲染的构建
       */
      // return { url }
    })
  )


  // 我们也可以返回与页面路由不匹配的 URL。
  // 这样我们就可以提供其他页面的 `pageContext`。
  // 这里我们提供 `/movies` 页面的 `pageContext`,
  // 因为我们已经有了数据。
  const movieListPage = {
    url: '/movies', // 请注意 URL `/movies` 不是页面路径 `/movie/@movieId` 的一部分
    pageContext: {
      pageProps: {
        // 我们过滤掉不需要的数据,以尽量减少发送到浏览器的数据
        // 我们在 https://cn.vite-plugin-ssr.com/data-fetching 解释了这种做法
        movieList: movies.map(({id, title}) => ({id, title})
      }
    }
  }

  return [movieListPage, ...moviePages]
}

实际上,prerender() hook 允许我们一次预获取多个页面的数据

prerender() hook 中提供 pageContext 应该只被用于加快预渲染构建,我们建议不要将 prerender() hook 用于其他目的。

例如,我们应该避免在 prerender() hook 中提供额外的 pageContext

相反,我们应该确保我们的 onBeforeRender() hook 提供我们需要的所有 pageContext

因为在开发中永远不会调用 prerender() hook,我们应该使应用程序在开发和生产之间保持一致。

Examples

React Example:

Vue Example: