为啥它每秒都在不断地重新获取 graphQL?

Posted

技术标签:

【中文标题】为啥它每秒都在不断地重新获取 graphQL?【英文标题】:Why it is continuously re-fetching graphQL on every second?为什么它每秒都在不断地重新获取 graphQL? 【发布时间】:2020-05-27 18:28:13 【问题描述】:

在我的 NextJs 前端应用程序中使用带有 graphQL 的 Strapi 服务器上的 @apollo/react-hooks useQuery() 过滤当前日期时间的数据。 myComponent 在 _app.js 之后渲染为子组件

myComponent.js

import  useQuery  from "@apollo/react-hooks";
import  MY_QUERY  from "../apollo/queries/home/home";

export default () => 

  let currentDateTime = new Date(Date.now());
  let currentIsoDateTime = currentDateTime.toISOString();
  const  data, loading, error  = useQuery(MY_QUERY, 
    variables: 
      currentIsoDateTime: currentIsoDateTime
    
  );

  return <>data</>

查询

export const MY_QUERY = gql`

  query($currentIsoDateTime: DateTime)
    events(where:DateTime_gt:$currentIsoDateTime)
      id
      Title
      DateTime
    
  
`;

currentDateTime 随时间变化,从 graphQL 中获取数据,结果无限

【问题讨论】:

【参考方案1】:

查询消耗currentIsoDateTime 那么这是一个要在状态中定义的变量:

const [currentIsoDateTime] = React.useState(() => new Date(Date.now()).toISOString() );

【讨论】:

【参考方案2】:

数据加载完毕后,apollo 会更新loading 状态,这会重新渲染你的组件。现在因为 Date 是在 render 方法中创建的,它会在每次渲染时创建不同的时间。

这会更改 GraphQL API 的变量,并且 apollo 将使用新变量重新获取 API 调用。

您可以检查开发控制台中的网络选项卡,并查看每个查询都使用不同的currentISODateTime 值调用

为避免这种情况,您可以通过将其初始化为状态来重新使用初始日期时间。例如

const [currentDateTime] = React.useState(() => new Date(Date.now()));

【讨论】:

你解释的很完美,但在将currentDateTime 初始化为一个状态后,它仍然让我遇到同样的问题。有没有其他方法可以解决? 你可以试试 console.log currentIsoDateTime 看看每次渲染后值是否变化? 如果currentIsoDateTime 没有在查询中作为变量应用,则最多打印 2 次​​span> 如果它被渲染 2 次,那么它是正确的行为:1 次初始加载和 1 次获取数据后。但前提是你不使用currentIsoDateTime。 2 个打印的值是相同还是不同? 两个打印值相同

以上是关于为啥它每秒都在不断地重新获取 graphQL?的主要内容,如果未能解决你的问题,请参考以下文章

React Apollo - nodejs graphql后端返回异步响应后如何重新获取(更新)数据

每秒重新加载 Tableview 部分会导致闪烁

与 Socket.io 反应 - 在“socket.on”事件上不断地重新渲染

使用 Apollo 重新获取部分 GraphQL 查询的最佳实践?

GraphQL 和 Prisma:当它们已经是 Prisma 数据库模式的一部分时,为啥要在应用程序模式中重新定义类型?

当GraphQL遇到VSAM