Nextjs GET route being cached irrespective of query params

Hello!

Since Friday we’ve been seeing an intermittent caching issue with one of our nextjs 15 GET routes.

If a search is made from this page: Search | WW1 Volunteers | British Red Cross it brings back a cached copy of unrelated search results from a search someone else has run previously.

example request: https://vad.redcross.org.uk/api/search?$count=true&$top=500&searchTerm=sandra&filter=Name

If, instead, a search is made on https://brc-web-vad.netlify.app/search which sends requests to the same deployment, the search is handled correctly.

example request: https://brc-web-vad.netlify.app/api/search?$count=true&$top=500&searchTerm=sandra&filter=Name

The exact path (for getting search results) that seems to be cached is /api/search.

The only difference we can think of between the two domains is that the vad.redcross one sends requests through Imperva. We’ve disabled Imperva caching and you can see in the response headers from Netlify that it’s often a “Netlify Edge: hit” or “Netlify Durable: hit” for requests made to the vad.redcross domain so it seems Netlify related.

Also worth noting that if we redeploy the site, the search requests work as expect for around half an hour before reverting to the caching behaviour. Also that the GET route we’ve got doesn’t export ‘force-static’ or any nextjs cache instruction so we’d expect it to never be cached.

Any help with this issue would be much appreciated!

Best regards,

Dan

1 Like

I work with @danomrc and have a couple extra notes:

  1. We’ve added a log so that some info about requests to /api/search are logged in the Function Next.js Server Handler log, and when the search stops working - when we get unexpected cache hits - we also stop seeing new requests in the log. We should see every request received and accepted individually, recorded in the log.
  2. We’re on the Standard network, not the High-Powered/enterprise one.
1 Like

Just wanted to note that we’ve tried modifying one of the response headers from the route to be: “Netlify Vary: query” but the issue persists :man_shrugging:

I’m not seeing the vary header on your site. I’m only seeing the default vary which is: query=__nextDataReq

Hey @hrishikesh, that may be because earlier today I rolled the site back to an older deploy, one where the search worked, to avoid disappointing our users. I’ll regroup with our team tomorrow and get back to you!

We found a workaround to fix the GET route caching:

By using export const dynamic = 'force-dynamic' in the GET route we got a fresh response on every request.

This shouldn’t be required as GET routes aren’t supposed to be cached at all by default. Prior to nextjs 15 we didn’t see this behaviour.

It only occurred for us when the requests went through Imperva which added an ‘if-modified-since’ header to the request which is our best guess for why we saw the Netlify cache get used. We’re working on a a minimum reproduction of this issue.

1 Like

Just adding that we think both the export const dynamic = 'force-dynamic' and the response.headers.set("Netlify-Vary", "query") are required for this workaround to work, one isn’t enough without the other