什么是 @apollo/react-ssr?
@apollo/react-ssr 是一个为了在服务器端使用 React 和 Apollo 客户端库而设计的 npm 包。通常情况下,React 应该只在客户端进行渲染,但服务器端渲染 (server-side rendering, SSR) 可以使得你的应用在第一次加载时更快地呈现,并更好地配合 SEO(搜索引擎优化)。
如何使用 @apollo/react-ssr?
在开始使用 @apollo/react-ssr 之前,需要确保你已经安装了 @apollo/client 和 react-dom 以及 react-router-dom,它们是这个 npm 包的前置依赖。
然后,在你的服务器端代码中,你可以按照下面的方式使用 @apollo/react-ssr 来执行一个查询并渲染出来:
------ - --------------- - ---- -------------------- ------ - -------------- - ---- ----------------- ------ - -------------- - ---- ------------------- ------ - ------------ - ---- ------------------- -- --- ---- ---- -- ------ ---- ------ ------ -------- --- ---- --- --------- -- --- ------------ ----- ----- ---- -- - ----- ------- - --- ----- ----------- - - --------------- ---------------- ------------- ------------------ ------------------ ---- -- --------------- ----------------- -- ----- ----------------------------- ----- ------- - ---------------------------- -- --- ---
这个例子中,我们使用到了 getDataFromTree
函数,它将会执行我们的数据查询并等待请求的结果。只有等到所有的查询都完成了,才会渲染出我们的应用。这样可以确保我们的服务器端渲染包含了完整的数据。
ApolloProvider
组件将会对我们的应用提供 Apollo 的 client 实例,这将包含我们的 GraphQL API 端点的地址以及一些其他配置项。
StaticRouter
组件则是在服务器端上用来处理路由匹配的一种方式。该组件会接收 location
和 context
两个属性,其中 location
是当前 URL 的路径,而 context
则在渲染期间包含了我们的服务器端信息。
最后,我们使用 renderToString
函数将 React Element 转换成字符串,使得它可以在我们的客户端进行交互。
示例代码
这里我们将举一个例子来说明如何使用 @apollo/react-ssr。在这个例子中,我们使用了 React 和 Apollo 客户端库来从 GraphQL API 获取账户信息和账户余额。我们也将使用 React Router 来实现客户端上的路由。
安装依赖
--- ------- ----- --------- ---------------- -------------- ----------------- -------
创建 Apollo Client
------ - ------------- ------------- - ---- ----------------- ------ ----- ------------ - --- -------------- ---- -------------------------------- ------ --- ---------------- ---
在这里,我们创建了一个 Apollo Client 的实例,指向了我们的 GraphQL API 端点。我们也创建了一个 InMemoryCache 对象,它将会被用来保存我们的 GraphQL 数据。
创建 App
------ ----- ---- -------- ------ - ------- ------ ---- - ---- ------------------- ------ - -------- - ---- ----------------- ------ - --- - ---- -------------- ----- ----------- - ---- ----- ---------- - ---- ------- - -- -------- ------ - ----- - -------- ------ ---- - - ---------------------- -- --------- ------ ------------------ -- ------- ------ -------- ------- ------ - ----- ------------- ------- ------- ---- --- --------------- ------- ------- ------- ------- --- ------------------ ------ -- - -------- ------- - ------ - ----- -------------- ------- -- --- ----- --------- ------ -- - ------ ------- -------- ----- - ------ - ----- ----- ---- ---- ----- ------------------ ----- ---- ----- ------------------------ ----- ----- ------ -------- ------ -------- ------ ----- -- -------- ------ -------------- ------ -- -------- --------- ------ -- -
在这里,我们使用了 useQuery
钩子来执行我们的 GraphQL 查询。我们还为我们的应用提供了两个迷你组件,一个是 Home 组件,会渲染我们账户信息和余额,另一个是 About 组件,在这个例子中,它并没有执行任何查询。
创建服务器端代码
------ ------- ---- ---------- ------ - -------------- - ---- ------------------- ------ - -------------- - ---- ----------------- ------ - ------------ - ---- ------------------- ------ - --------------- - ---- -------------------- ------ --- ---- -------- ------ - ------------ - ---- ------------------ ----- --- - ---------- -------------------------------- ------------ ----- ----- ---- -- - ----- ------- - --- ----- ----------- - - --------------- ---------------------- ------------- ------------------ ------------------ ---- -- --------------- ----------------- -- ----- ----------------------------- ----- ------- - ---------------------------- ----- ---- - - ------ ------ --------- ----------- ------- ------ ---- ------------------------- ------- --------------------------------- ------- ------- -- --------------- --- ---------------- -- -- - ------------------- ------- -- ------------------------ ---
我们首先创建了一个 Express 应用。然后,我们使用 getDataFromTree
函数来异步执行我们的查询,这样就可以在服务器端获取到所有的数据了。我们将这些数据提供给我们的 React 组件,这将使得我们的组件在渲染期间具有了完整的数据。
ApolloProvider
和 StaticRouter
组件的作用与上面介绍的是一样的。
最后,我们使用 renderToString
函数将我们的 React Element 转换成字符串,然后将其发送到客户端。我们也在 HTML 中加入了一个 bundle.js 文件,这个文件包含了我们的客户端 JavaScript 代码。
来源:JavaScript中文网 ,转载请联系管理员! 本文地址:https://www.javascriptcn.com/post/5eedc27ab5cbfe1ea0612086