-
Notifications
You must be signed in to change notification settings - Fork 87
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
fix: update cache handler to accomodate changes in next@canary #2480
fix: update cache handler to accomodate changes in next@canary #2480
Conversation
…d content for APP_PAGE
…ored, because it no longer exist in newest major, but we still have to set it for older next versions
📊 Package size report 0.04%↑
Unchanged files
🤖 This report was automatically generated by pkg-size-action |
f8b8d9c
to
c60ac69
Compare
@@ -79,7 +79,7 @@ | |||
"memfs": "^4.9.2", | |||
"mock-require": "^3.0.3", | |||
"msw": "^2.0.7", | |||
"next": "^14.0.4", | |||
"next": "^15.0.0-canary.28", |
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.
I did this to get updated Cache related types from next
, otherwise all the APP_PAGE
related additions were causing a lot of TS issues.
I'm not sure if doing this is the best or wether I should maybe copy over relevant types until those become available in latest next
?
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.
I think we're only using the next
dependency for types, so I think this approach is okay
// @ts-expect-error incrementalCacheHandlerPath was removed from config type | ||
// but we still need to set it for older Next.js versions | ||
incrementalCacheHandlerPath: cacheHandler, |
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.
one of type changes in next canary/rc :(
2b4eb38
to
7da721e
Compare
…version after build command finished
7da721e
to
01168ef
Compare
1eb088f
to
bb734c0
Compare
// Note: at time of writing this code, released 15@rc uses old kind for App Router pages, while 15.0.0@canary.13 and newer canaries use new kind. | ||
// Looking at 15@rc release branch it was merging `canary` branch in, so the version constraint assumes that future 15@rc (and 15@latest) versions | ||
// will use new kind for App Router pages. | ||
const shouldUseAppPageKind = ctx.nextVersion | ||
? satisfies(ctx.nextVersion, '>=15.0.0-canary.13 <15.0.0-d || >15.0.0-rc.0', { |
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.
This is a bit tricky as it tries to predict what future rc/stable releases of Next would likely contain and this is my best guess in hope that version released with this code would be usable with future next versions.
The alternative I was wondering about is doing a test by checking some internal modules, but the Next.js change only added some helper exports ( i.e. https://github.com/vercel/next.js/pull/65988/files#diff-17519b0578e6b6493027a0faa49f2aaab1a70d81216339a93a8d87c68a861f0d ) and only clear APP_PAGE
things were types which I can't check in runtime :/ But also this test would have to maintained into the future, so this overall is not that great of an idea (IMO)
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.
I agree with you about this being difficult to maintain. I did a bit of spelunking and found this util that we could potentially use to ascertain whether APP_PAGE
is supported https://github.com/vercel/next.js/blob/658037358cf4c9813648e3a9b1c70d7e414c87ff/packages/next/src/server/response-cache/utils.ts#L5
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.
How would we use that to test it? This helper was added long ago so it couldn't be just testing if there is export like that?
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.
We could pass a mock ResponseCacheEntry
object to it with value.kind = 'APP_PAGE'
and value.rscData
set. If APP_PAGE
is supported it will return an IncrementalCacheItem
with value.rscData
still set (canary behaviour) and if not it will return a IncrementalCacheItem
without value.rscData
(stable behaviour).
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.
Ok, that makes sense, but do we want to introduce test like (relying on specific behavior of Next.js internal helper) that that we will need to possibly maintain (including finding alternatives if it ever changes)? It feels like more work over-time than possibly adjusting version range above if expectation of the change shipping with -rc.1
will be incorrect?
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 a better alternative would be to abstract out the version management, so we can just call something like hasAppPage()
in the cache handler (and subsequent other parts of the code) and the abstraction takes care of the version detection and mapping to version numbers. Then we just accept that we'll need to monitor versions and make changes, but at least it would just be in one place? This could be a follow up PR, so I'm approving this one.
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.
CacheHandler
doesn't need to have such check. The PAGE
kind
is the same so all the handling for that remain and APP_PAGE
kind
has separate handling. The only place that needs conditional logic like that would be when we prepare cache entries from prerendered content when deciding which kind
the content should be and where to put rsc data in the cache entry + wether it should be plain text or encoded content.
I can still move the check to some better place, but it's only needed once in single place at build time right now
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.
I think this is ready to go, albeit with a new comment below about the version handling.
// Note: at time of writing this code, released 15@rc uses old kind for App Router pages, while 15.0.0@canary.13 and newer canaries use new kind. | ||
// Looking at 15@rc release branch it was merging `canary` branch in, so the version constraint assumes that future 15@rc (and 15@latest) versions | ||
// will use new kind for App Router pages. | ||
const shouldUseAppPageKind = ctx.nextVersion | ||
? satisfies(ctx.nextVersion, '>=15.0.0-canary.13 <15.0.0-d || >15.0.0-rc.0', { |
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 a better alternative would be to abstract out the version management, so we can just call something like hasAppPage()
in the cache handler (and subsequent other parts of the code) and the abstraction takes care of the version detection and mapping to version numbers. Then we just accept that we'll need to monitor versions and make changes, but at least it would just be in one place? This could be a follow up PR, so I'm approving this one.
Description
There were quite a bit of changes in
next@canary
that we currently don't handle:APP_PAGE
- Re-land Fix broken HTML inlining of non UTF-8 decodable binary data from Flight payload #65664 vercel/next.js#65988This one means we need to update both our CacheHandler to support that kind (should be done) and our build time handling of prerendered content (not fully done yet - missing part is correct condition to use current or new one cache kind - right now I'm relying on our test env var to at least test that blob shape is correct)
PrerenderManifest
when doing staleness calculations. Instead they now useSharedRevalidateTimings
for that ( Shared Revalidate Timings vercel/next.js#64370 ) and madePrerenderManifest
frozen ( Freeze loaded manifests vercel/next.js#64313 ) which means we can't mutate it and so c91e257 is causing actually more problems there (I'm also trying to add some graceful error handling with addition of try/catches so in case the hacks that we have stop working it's not completely borked)Documentation
Tests
You can test this change yourself like so:
Relevant links (GitHub issues, etc.) or a picture of cute animal