Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Cannot read properties of undefined (reading 'data') #12053

Closed
julianCast opened this issue Sep 4, 2024 · 22 comments
Closed

Cannot read properties of undefined (reading 'data') #12053

julianCast opened this issue Sep 4, 2024 · 22 comments
Labels
🏓 awaiting-contributor-response requires input from a contributor

Comments

@julianCast
Copy link

julianCast commented Sep 4, 2024

Issue Description

Hi! We are getting these error randomly:

// node_modules/@apollo/client/react/hooks/useQuery.js in InternalState.prototype.toQueryResult at line 440:27
InternalState.prototype.toQueryResult = function (result) {
        var queryResult = this.toQueryResultCache.get(result);
        if (queryResult)
            return queryResult;
      // Next line, where result could be undefined ?
        var data = result.data, partial = result.partial, resultWithoutPartial = __rest(result, ["data", "partial"]);
        this.toQueryResultCache.set(result, (queryResult = __assign(__assign(__assign({ data: data },

Link to Reproduction

None

Reproduction Steps

No response

@apollo/client version

3.9.11

@phryneas
Copy link
Member

phryneas commented Sep 4, 2024

All of that code has been rewritten from the ground in newer versions of Apollo Client - could you please update to a current version? :)

@julianCast
Copy link
Author

All of that code has been rewritten from the ground in newer versions of Apollo Client - could you please update to a current version? :)

Oh! I'm updating now, thanks! I'll let you know the results after

@Cattari
Copy link

Cattari commented Sep 5, 2024

Guys, we are on the v3.11.4 and this code does not differ from the latest one (v3.11.8).
But we are still getting the Cannot read properties of undefined (reading 'data') error.

Attaching the stacktrace (lines may be incorrect):

TypeError: Cannot read property 'data' of undefined
at anonymous (address at /usr/local/var/jenkins/workspace/our_app/node_modules/@apollo/client/react/hooks/hooks.cjs:353:null)
at complete (address at /usr/local/var/jenkins/workspace/our_app/node_modules/@apollo/client/react/hooks/hooks.cjs:199:null)
at call (native)
at notifySubscription (address at /usr/local/var/jenkins/workspace/our_app/node_modules/zen-observable/lib/Observable.js:153:null)
at onNotify (address at /usr/local/var/jenkins/workspace/our_app/node_modules/zen-observable/lib/Observable.js:17:null)
at complete (address at null:null:null)
at anonymous (address at /usr/local/var/jenkins/workspace/our_app/node_modules/@apollo/client/utilities/utilities.cjs:1270:null)
at forEach (native)
at iterateObserversSafely (address at /usr/local/var/jenkins/workspace/our_app/node_modules/@apollo/client/utilities/utilities.cjs:1248:null)

I think we are getting the same error, I may be wrong.
We are still investigating what is causing the issue.
But if you think that the issue is here - we would be happy to get any feedback about this.

@jerelmiller
Copy link
Member

@Cattari that looks very similar but its difficult to tell. If you're able to reproduce this, would you be able to put together a runnable reproduction for us? That would be super helpful to understanding whats happening here.

That result should never be undefined, but we haven't been able to pinpoint exactly why sometimes it is. We were hoping the useQuery rewrite with 3.11 would have helped, but alas seems that we still run into this issue from time to time.

@phryneas
Copy link
Member

phryneas commented Sep 5, 2024

@Cattari line 353 of hooks.cjs in 3.11.4 is

    var globalDefaults = client.defaultOptions.watchQuery;

no access to data there.
Are you sure you are on 3.11.4 and there's not also some other installation of @apollo/client thrown in the mix here?

To verify, try npm ls @apollo/client or yarn why @apollo/client, depending on the package manager you are using.

@Cattari
Copy link

Cattari commented Sep 5, 2024

@phryneas as I said, lines maybe wrong. I got this stacktrace from a symbolication from the release build in React Native. I checked the lining before, it's wrong. But the stacktrace with function naming and paths are correct. So, ignore the lines here, please.

The question is: May the result in toQueryResult function be undefined?
If yes - then that's the issue.

@phryneas
Copy link
Member

phryneas commented Sep 5, 2024

There are currently two code paths in useQuery to toQueryResult (the original InternalState.prototype.toQueryResult this issue was opened over doesn't exist anymore)

  const currentResultOverride = React.useMemo(
    () =>
      resultOverride &&
      toQueryResult(resultOverride, previousData, observable, client),
    [client, observable, resultOverride, previousData]
  );

As you can see, this does a check on resultOverride, so it cannot be undefined.

The other call is

  resultData.current = toQueryResult(
    unsafeHandlePartialRefetch(nextResult, observable, partialRefetch),
    resultData.previousData,
    observable,
    client
  );

And here, unsafeHandlePartialRefetch accesses properties on nextResult, so it would already crash before reaching toQueryResult.

There are two more call sites from useLazyQuery, so maybe we should narrow it down a bit: are you using useQuery or useLazyQuery here?

@phryneas
Copy link
Member

phryneas commented Sep 5, 2024

Checking these real quick:

          toQueryResult(
            observable.getCurrentResult(),
            resultData.previousData,
            observable,
            client
          )

observable.getCurrentResult() never returns undefined.

This would only leave

   concast.subscribe({
     next: (value) => {
       result = value;
     },
     complete: () => {
       resolve(
         toQueryResult(result, resultData.previousData, observable, client)
       );
     },
   })

This could in theory have result undefined, if you have a link that prevents a next call and as a result, complete is called before complete.

Could that be the case?

@julianCast
Copy link
Author

julianCast commented Sep 5, 2024

I believe result can be undefined when the request hook is interrupted, for example if while fetching we make a different request that will interrupt the previous one.

@jerelmiller
Copy link
Member

Related: #11846. I knew this looked familiar but couldn't find the issue until just moments ago 😅.

@phryneas
Copy link
Member

phryneas commented Sep 6, 2024

I believe result can be undefined when the request hook is interrupted, for example if while fetching we make a different request that will interrupt the previous one.

That is an interesting thought, but I don't think that is the cause:
An old request will only be cancelled if there are no more subscribers to the observable. useLazyQuery's execute function creates a subscription for the returned promise, so the request should never be cancelled.
And for useQuery, this code path is never reached.

Related: #11846. I knew this looked familiar but couldn't find the issue until just moments ago 😅.

Yeah, I also had that in mind, but we fixed that in 3.11.4, so it can't be that :/


I'm a bit out of ideas. Could you share a replay of this happening with one of us privately?

@julianCast
Copy link
Author

I'm a bit out of ideas. Could you share a replay of this happening with one of us privately?

We are updating Apollo client first like you said, we are running tests now. Since it happens very often in one of our Cypress tests we'll soon know if it's fixed. I'll be back with the results. Thank you again

@Cattari
Copy link

Cattari commented Sep 6, 2024

Guys, we have an update. Sorry, for confusing. It was our fault. We were using fromPromise utility and our promise was returning undefined.

So, guys, who faces the same issue, make sure your promise you put inside fromPromise @apollo/client func does not return undefined.

@phryneas @julianCast FYI

@puneetkansal04
Copy link

puneetkansal04 commented Sep 25, 2024

Screenshot 2024-09-25 at 12 02 01 PM

Getting same issue attaching a screenshot of IOS Simulator that may help to analyse it.

Error is like this
TypeError: undefined is not an object (evaluating 'result.data')

@julianCast @Cattari @phryneas @jerelmiller have a look

@jerelmiller
Copy link
Member

@puneetkansal04 what version of Apollo Client are you using?

@puneetkansal04
Copy link

apollo version 3.11.8 @jerelmiller

@jerelmiller
Copy link
Member

@puneetkansal04 any chance you could provide a reproduction of the issue? This one has been difficult to track down without a way to reproduce it since we haven't been able to narrow down why result can be undefined in the first place. Unfortunately the screenshot doesn't provide anything new to understand 🙁

@puneetkansal04
Copy link

@jerelmiller for reproducing i think if you will hit multiple queries and then you will expire the token then in that queries i think you will get this error. Because i don't know deep about this.

@jerelmiller
Copy link
Member

@puneetkansal04 I'm not sure what you mean by "expire the token". Can you explain further? Better yet, can you put together a reproduction? You can use our error template as a starting point to help demonstrate the issue.

@jerelmiller jerelmiller added the 🏓 awaiting-contributor-response requires input from a contributor label Nov 7, 2024
Copy link
Contributor

github-actions bot commented Dec 8, 2024

We're closing this issue now but feel free to ping the maintainers or open a new issue if you still need support. Thank you!

@github-actions github-actions bot closed this as not planned Won't fix, can't repro, duplicate, stale Dec 8, 2024
@ValeriiMalynovskyi
Copy link

Hi @julianCast
We also had the same error in ~50% of cases after first login. It seems that timing of the token passed to client was the issue. I have just changed how the token is memoized, checked ~20 logouts/logins - the issue is no longer reproducible.
Double check it in your project.

@julianCast
Copy link
Author

Hi @julianCast We also had the same error in ~50% of cases after first login. It seems that timing of the token passed to client was the issue. I have just changed how the token is memoized, checked ~20 logouts/logins - the issue is no longer reproducible. Double check it in your project.

Thank you for the hint, I'll try that!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
🏓 awaiting-contributor-response requires input from a contributor
Projects
None yet
Development

No branches or pull requests

6 participants