在查询组件之外显示 Apollo 客户端查询加载的最佳实践?
Posted
技术标签:
【中文标题】在查询组件之外显示 Apollo 客户端查询加载的最佳实践?【英文标题】:Best practice to show Apollo Client Query loading outside of Query Component? 【发布时间】:2019-11-02 17:36:25 【问题描述】:我想在我的查询组件之外显示加载指示器。
现在我正在使用 redux,当我开始从 api 加载数据时,我设置了 redux state 属性,然后我用它来显示加载器组件。
如何使用 Apollo 客户端查询/突变实现相同的目标? 每个示例都显示了 Query 内部的加载道具,但如何在此 Query 之外显示加载器?
假设我有这样的事情:
<Header><Loader/></Header>
<Content><Query><List /></Query></Content>
但我不想用 Query 包装所有内容并执行以下操作:
<Query>
<Header><Loader/></Header>
<Content><List ></Content>
</Query>
这甚至可能吗?
加载时我应该在 Query 中更改 @client
缓存吗?
编辑:我想用 apollo-link-state 替换 redux,所以解决方案不应该使用 redux。
【问题讨论】:
【参考方案1】:我建议使用react-apollo-hooks,它使 Apollo 的使用更加轻松有趣。
看看示例代码
import React from 'react';
import useQuery from 'react-apollo-hooks';
import get from 'lodash.get';
import SUBSCRIPTIONS_QUERY from './Subscriptions.graphql';
import s from './SubscriptionTable.scss';
const SubscriptionsTable = () =>
const data, loading, error = useQuery(SUBSCRIPTIONS_QUERY);
if (loading) return "Loading...";
if (error) return `Error! $error.message`;
return (
<div className=s.SubscriptionTable>
<div className=s.SubscriptionTable__Header>Email</div>
get(data, 'subscriptions', []).map(subscription => (
<div key=get(subscription, 'id') className=s.SubscriptionTable__Row>
get(subscription, 'email')
</div>
))
</div>
);
;
【讨论】:
虽然这看起来很有趣,但我认为它不会解决我的问题。如果我这样做: const data, loading, error = useQuery(SUBSCRIPTIONS_QUERY); const 数据:data1,加载:loading1,错误:error1 = useQuery(SUBSCRIPTIONS_QUERY);如果我然后以某种方式重新获取第一个,那么第二个可能不会显示加载? 这是方向,不是解决方案 @Lauri Apollo 基于查询和变量进行缓存。所以data1集永远不会上网。您需要部署 refetch 或使其成为 useLazyQuery。【参考方案2】:首先,没有理由将你的加载状态放在 Redux 中,但如果你真的想出于某种原因你应该在组件挂载时将你的 redux 状态设置为loading: true
,并在安装时将你的 redux 状态设置为loading: false
组件中的加载不再正确。这就是我的意思:
import React from 'react';
import
useQuery,
useEffect
from 'react-apollo-hooks';
import get from 'lodash.get';
import SUBSCRIPTIONS_QUERY from './Subscriptions.graphql';
import s from './SubscriptionTable.scss';
const SubscriptionsTable = () =>
const
data,
loading,
error
= useQuery(SUBSCRIPTIONS_QUERY);
useEffect(() =>
// set loading: true in redux state
// as soon as component mounts
// via action/reducer pattern
, [])
if (loading)
return "Loading..."
else
// set loading: false in redux state
// when query no longer loading
// via action/reducer pattern
if (error) return `Error! $error.message`;
return (<div>JSON.stringify(data)</div>);
;
【讨论】:
以上是关于在查询组件之外显示 Apollo 客户端查询加载的最佳实践?的主要内容,如果未能解决你的问题,请参考以下文章
Graphql,react-apollo如何在加载组件状态时将变量传递给查询
为啥 WebStorm 在 Vue 组件或 .graphql 文件中的 apollo 对象内的 gql 查询中显示错误