apollographql / react-apollo

:recycle: React integration for Apollo Client
https://www.apollographql.com/docs/react/
MIT License
6.85k stars 787 forks source link

onError callback fired twice when GraphQL error is thrown too quickly #3557

Open mastilver opened 5 years ago

mastilver commented 5 years ago

Hi

This issue is related to #2559 but it's happening in different circumstances

When the error is too quick to come back - for example when it doesn't need to talk to the server for it to be thrown - the onError callback will be called twice

When I run a query and I'm on offline mode this is what happening:

Init

After query resolved:

Intended outcome:

During the initialisation both the hook state and QueryData state should be the same

Actual outcome:

During the initialisation the hook is in a loading state and QueryData is in an error state

I believe the hook should give to QueryData its state rather than let QueryData retrieve it and risking a race condition

How to reproduce the issue:

Copy and use Root as your component

function Root() {
  const [loaded, setLoaded] = useState(false)

  return (
    <>
      <button onClick={() => setLoaded(true)}>RUN</button>
      {loaded && <Child>}
    </>
  )
}

function Child() {
  useQuery(CAR_QUERY, {
    onError() {
      console.log('error')
    }
  })

  return null
}

You should get two console logs

Version

System: OS: Linux 4.15 Linux Mint 19.2 (Tina) Binaries: Node: 10.16.3 - ~/.nvm/versions/node/v10.16.3/bin/node Yarn: 1.17.3 - ~/Code/AdStream/frontend/node_modules/.bin/yarn npm: 6.9.0 - ~/.nvm/versions/node/v10.16.3/bin/npm Browsers: Chrome: 77.0.3865.90 Firefox: 69.0.1 npmPackages: @apollo/react-testing: ^3.1.0 => 3.1.0 apollo: ^2.6.2 => 2.16.1 apollo-cache-inmemory: ^1.5.1 => 1.6.2 apollo-client: ^2.5.1 => 2.6.3 apollo-link: ^1.2.11 => 1.2.12 apollo-link-context: ^1.0.17 => 1.0.18 apollo-link-error: ^1.1.10 => 1.1.11 apollo-link-http: ^1.5.14 => 1.5.15 apollo-storybook-react: ^0.2.1 => 0.2.1 react-apollo: ^3.1.2 => 3.1.2

dylanwulf commented 5 years ago

I'm experiencing something which may be related: I have a test that returns an error, then calls refetch and returns a second error. I'm expecting onError to be called twice, but it's only getting called once. It seems to depend on which version of node i use (v12 does not work correctly, v10 works correctly) @mastilver Do you have a runnable reproduction of this issue that you could post here? Like a github repo or a codesandbox?

Tellirrium commented 4 years ago

The same problem. Can you help ? I used different node.js versions, such as 10,11 and 12, but this is not a solution to this problem.