-
-
Notifications
You must be signed in to change notification settings - Fork 454
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
(core/next) Only restore uncached operation data into ssr-cache #1775
Conversation
|
ssr.restoreData = (restore: SSRData) => { | ||
// Only restore data for uncached operations | ||
const uncached = {}; | ||
Object.entries(restore).forEach(([key, value]) => { | ||
if (false === key in data) { | ||
uncached[key] = value; | ||
} | ||
}); | ||
return Object.assign(data, uncached); | ||
}; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Hmm, this kinda feels weird to me. Generally the same key in the cache should have the same result across different pages, I'm curious how and why this would deviate.
This would be a breaking change if we were to go for this.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Maybe it would make more sense to put this in
https://github.com/FormidableLabs/urql/blob/891a17a0a22e3b4d5b301a779330336efc79d1b0/packages/next-urql/src/with-urql-client.ts#L58-L60
so it only affects the next integration?
Considering your specific issue wouldn't it be better to make a distinction between public and private resources from a schema perspective? Then the SSG'd data could be considered |
If the SSR data is present and restored synchronously on mount, and more data then comes in later, how would they ever interfere, i.e. in your case the more up-to-date runtime data would override it. All data in the
This can only happen if the SSR'd data is never accessed, which means that there's a discrepancy between what's in the SSR cache due to what's rendered on the server and what's on the client. The reason why I'm bringing this up is that obviously SSR != SSG in a lot of cases. If you're manually populating the |
Thanks for the feedback, I'll try and explain further, hopefully there is a simpler way to implement my use-case.
We are using
I'm not sure I follow. We are only populating the This is all as intended. The problem arises when the user navigates around the application and then later returns to the resource listing page. At this point the cache has a bunch of runtime data (including that of the listing page query), and I would expect this runtime data to be used when returning to the listing page. Instead the SSG data is briefly shown and then shortly afterwards overriden with the runtime data (as the query is performed again due to the I assumed this was due to #1602 which @JoviDeCroock we do consider fields related to the authenticated user Thanks for the help! |
Ok, gotcha, I believe what's happening here is specific to Next SSG as when we switch the page, we may inject data from Next again into the So if I don't misunderstand this, your intention is to not use the SSG data on navigation? Because I'm not convinced then that this PR will work. It may also break existing non-SSG use cases of next-urql, so I'm thinking what we really want here is more control over when data is used "past" the initial runtime page and when we don't |
Yes I think you are right. However, my intention is to still use SSG on first navigation (when the What are your thoughts on putting the logic in such that server state is only merged when no result is already present in the cache? Something like } else if (ssr && typeof window !== 'undefined') {
// Only restore data for uncached operations
const cached = ssr.extractData();
const uncached = {};
Object.entries(urqlServerState).forEach(([key, value]) => {
if (false === key in cached) {
uncached[key] = value;
}
});
ssr.restoreData(uncached);
} |
Ok, actually, I talked about this with @JoviDeCroock and we did find that it's an even more specific case than stated above. So, we realised what the implementation you have here is trying to do. Unfortunately, it isn't effective as it still needs another line in Hence, I've added a test case and rewrote this a little: #1776 |
Fantastic! Thanks for helping out and for a great library 🥇 |
Superseded by #1776 |
Fix is shipped in |
Summary
We are attempting to improve our nextjs SSG strategy. We recently figured out how to statically generate pages for public resources while allowing non-public resources to not result in a temporary 404 while being fetched on the client (see discussion #1771).
The final issue we are facing is that the statically generated data hydrates client cache, due to #1602. While this preferable for most pages, it is a problem for our resource listings, where the statically generated version only includes public data, which then updates locally when a user has access to additional resources.
As far as I can tell, what happens is that when the cache has been updated with resources visible to the user, and they navigate back to the listing page, the cache is overwritten with the statically generated data (and then updated again when the client query is fetched).
Set of changes
I've changed the
ssr.restoreData
function to only merge operations into the cache that have not been cached yet.I'm not entirely sure if this should be fixed in the
ssrExchange
or I should be focusing onnext-urql
, please let me know your thoughts on how best to handle this.