-
Notifications
You must be signed in to change notification settings - Fork 28
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
RFC: return cached data for a known type/id #155
Comments
Updated title and description. /cc @mattkrick @jordanh |
Intriguing proposal @dustinfarris. A suggested name for such a feature "progressive querying." I'll let met respond with his thoughts before adding mine... |
I think the goal of cashay is to have a declarative API (except for mutations, but that's for v2). In other words, you should tell it what you want to do, not how to do it. Declaratively, you want data. You shouldn't have to sorry how that's achieved. Unfortunately, to do that means we'd have to make certain assumptions about the user defined queries on the server (like how they're named), or we'd have to be more verbose. |
@mattkrick ok, if adding lowish-level hooks are a no-go (à la v2), then I think my alternative proposal should be considered, perhaps in a separate issue. In a nutshell: modify existing Something like:
☝️ adding "refresh: true" instructs Cashay to "give me whatever you have for the resolved id, but kick off a server request and update the information". To your point, @mattkrick, this assumes that the name of the field, From my understanding, current
so it would be necessary to either make this illegal (doubt anyone would go for that), or require the user to specify the server query field explicitly if it is not the same, e.g.
in the absence of
|
if we know the name of the query, then do we even need to use a directive? Why not just make it a standard query & then diff out the fields that we already have? If we have all the fields, then we don't send a request to the server. |
Yep, that works too. The goal, though, is to use data that potentially came from other queries—you mentioned in another issue something about not making assumptions about type/id uniqueness. I'm still fuzzy about what you meant by that. Yes, ideally I would love for Cashay to "just do it" when I write,
☝️
|
here are the embedded assumptions in that:
These assumptions are all probably safe, heck relay makes these assumptions & that's why you write relay queries in such a funny way... the relay server basically has an |
The difference here is that Cashay knows in advance what Type will be returned. Relay and others do not. In my view, this is a clear differentiator that makes those assumptions plausible, without any goofy GUIDs. Server access not required, only the schema. |
definitely, i hear ya, it's a solid proposal. what would you propose to do about arrays of todos? For example let's say on 1 page you have a |
Interesting question. My gut reaction is the (optional) list of ids.
Aside: There are other caveats such as interfaces and unions where it may not be easy to determine to exact Type. I'd say the hard-and-fast rule should be: "we will try, but if we can't resolve the Type and id, we're going to the server". We can potentially add more tools here in the future, but I think sticking to known type+id is a good starting point. |
"other tools" might include a way to specify which Types have UUIDs when cashay is initialized. e.g. cashay.create({
types_with_uuid: ["Todo", "Project"] and then use that to decide whether uniqueness can be inferred from a particular Union query. If so, great. If not, existing operation/key in cache? Ok, still great. Otherwise, server. But I digress... |
|
tl;dr the abbreviated proposal is: If the Object Type and ID of a query can be determined in advance, Cashay will attempt to find existing data in cache, and backfill missing subfields with a server request. |
preFetch
hook
UPDATED 1/3/17
The prefetch hook described below is not in-line with the desired style of Cashay. See discussion and tl;dr in comments.
DISCLAIMER
I am still learning about cashay implementation details and it's possible one or more of my assumptions are wrong. Please push back.
Summary
Add a hook to allow users to access the cache while a query is in-flight.
Reason
When the user requests data, it is possible that some or all of the data already exists in cashay's cache. It would be beneficial from a performance standpoint to utilize that cache.
Note: the goal is not to reduce network traffic, but to display the data we already have, if we have it.
Cashay does this already under certain circumstances:
@cached
decoratorThere is an additional scenario, however, not covered by these—when the user is requesting a GraphQL field subset for which partial data already exists in the cache.
Consider this query from a project detail page:
The project detail gets all todos under it, selecting their individual ids and names. Now suppose the user clicks a specific todo, and is taken to a todo detail page which might have the following query:
Cashay sees this as a totally new query, yet some of the data is already in the cache from the project page! Namely, the todo's
id
andname
.The
@cached
decorator cannot be used here for two reasons:@cached
assumes the entire shape can be found in cache and kicks back null for the pieces it doesn't find@cached
provides no fallback behavior if an id is not found.Implementation
Add a new hook for
cashay.query
that gives the user access to the cache. In my mind, this will behave similar to the way mutationHandlers and "optimisticVariables" work currently, with the following flow:Pseudo (using the todo query above as
todoQuery
):With such an API, the component will be able to display the
name
of the todo, while the rest of the content is loading.Drawbacks
This opens the door for possible cache misuse and anti-pattern.
Alternatives
Modify
@cached
insteadPotentially,
@cached
could be modified to implement the same flow above, where it returns cached data, but fires a server request anyway if the cached data is not found. This would need to account for missing subfields—e.g. if the entire requested shape does not exist in cache, the server must be consulted.additional context in #154
The text was updated successfully, but these errors were encountered: