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

Unify EntityStore#{get,getFieldValue} methods. #5772

Merged
merged 2 commits into from
Jan 10, 2020

Conversation

benjamn
Copy link
Member

@benjamn benjamn commented Jan 10, 2020

When I originally wrote this code, I was motivated to keep the get and getFieldValue methods separate because they had different return types. Method signature overloading solves that problem using just the type system, so we can have one method implementation rather than two.

At the same time, I was able to eliminate unnecessary inheritance and method overriding in the Layer subclass by using an instanceof check in EntityStore#get.

When I originally wrote this code, I was motivated to keep the get and
getFieldValue methods separate because they had different return types.
Method signature overloading solves that problem using just the type
system, so we can have one method implementation rather than two.

At the same time, I was able to eliminate unnecessary inheritance and
method overriding in the Layer subclass by using an instanceof check in
EntityStore#get.
Copy link
Member

@hwillson hwillson left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Always be ✂️ - love it!

@benjamn benjamn merged commit abfef50 into master Jan 10, 2020
@benjamn benjamn deleted the unify-EntityStore-get-methods branch January 10, 2020 15:56
benjamn added a commit that referenced this pull request Jan 16, 2020
Should fix #5793, which was due to a bug I introduced in #5772.
benjamn added a commit that referenced this pull request Jan 23, 2020
One of the most important internal changes in Apollo Client 3.0 is that
the result caching system now tracks its dependencies at the field level,
rather than at the level of whole entity objects: #5617

As proof that this transformation is complete, we can finally remove the
ability to read entire entity objects from the EntityStore by ID, so that
the only way to read from the store is by providing both an ID and the
name of a field. The logic I improved in #5772 is now even simpler,
without the need for overloading multiple EntityStore#get signatures.

In the process, I noticed that the EntityStore#has(ID) method was
accidentally depending on any changes to the contents of the identified
entity, even though store.has only cares about the existence of the ID in
the store. This was only a problem if we called store.has during a larger
read operation, which currently only happens when InMemoryCache#read is
called with options.rootId. The symptoms of this oversight went unnoticed
because the caching of readFragment results was just a little more
sensitive to changes to the given entity. The results themselves were
still logically correct, but their caching was not as effective as it
could be. That's the beauty and the curse of caching: you might not notice
when it isn't working, because all your tests still pass, and nobody
complains that their application is broken.

Fortunately, we can model this dependency with an ID plus a fake field
name called "__exists", which is only dirtied when the ID is newly added
to or removed from the store.
@github-actions github-actions bot locked as resolved and limited conversation to collaborators Feb 16, 2023
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants