Skip to content

Record and cancel pending prefetch requests#1490

Open
m-vo wants to merge 3 commits intohotwired:mainfrom
m-vo:bugfix/cancel-prefetch
Open

Record and cancel pending prefetch requests#1490
m-vo wants to merge 3 commits intohotwired:mainfrom
m-vo:bugfix/cancel-prefetch

Conversation

@m-vo
Copy link
Copy Markdown
Contributor

@m-vo m-vo commented Jan 24, 2026

Fixes #1244, #1372, #1479

Inspired by #1244 (comment) by @SHPmax

What's this?

Turbo can speed up page loads by prefetching requests. If the connection is slow or the server takes some time to respond, this currently has two side-effects, though:

  1. Requesting a resource (that takes longer to load than the prefetch delay) multiple times - e.g. by quickly hovering back and forth over a link - will result in multiple requests to this same resource, that are running in parallel.

    fetches-piling-up.mp4
  2. If you request a resource that loads slow, then one that loads fast, the promise of the fast one will fulfill first (displaying a page for instance), then the slow one - that is still running - kicks in and overwrites the result.

    2025-12-13.15-03-52.mp4

    (taken from Prefetch causes wrong pages to be rendered #1479)

Solution

This PR makes the link_prefetch_observer record the last fetch request and cancel the previous one to the same URL. On top of that, during turbo:visit, all currently recorded requests but the one for the current URL are cancelled as well. This way, there now can only be one active prefetch request per URL and never a pending one of a different URL a visit happens.

I added test cases to outline the issue. You can see this PR in effect by commenting out the two added fetchRequest.cancel() statements in the link_prefetch_observer.

/cc @fritzmg, @ilyadh

@m-vo
Copy link
Copy Markdown
Contributor Author

m-vo commented Jan 24, 2026

I found a way of further improving this. I will update the PR accordingly.

@m-vo m-vo marked this pull request as draft January 24, 2026 17:49
@m-vo m-vo marked this pull request as ready for review January 25, 2026 11:49
@m-vo m-vo force-pushed the bugfix/cancel-prefetch branch from f22f7b3 to 44a5764 Compare January 25, 2026 13:48
@m-vo
Copy link
Copy Markdown
Contributor Author

m-vo commented Jan 25, 2026

Just to illustrate the difference. This is the behavior with this PR:

optimized-prefetch.mp4
  • In the first part of the video, I hovered over "Page 1" (which issues a prefetch request), clicked on it, then made a visit to "Page 2" which canceled the prefetch to the slow loading resource.

  • In the second part [0:10], I hovered over both links back and forth to trigger multiple prefetch requests. For each resource only one is now running at a time.

Copy link
Copy Markdown

@fritzmg fritzmg left a comment

Choose a reason for hiding this comment

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

The built resources are also deployed on https://www.inspiredminds.at/turbo.php - and I can confirm that this fixes #1479 and I could not find any other issues 👍

Copy link
Copy Markdown

@Toflar Toflar left a comment

Choose a reason for hiding this comment

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

We also had to disable prefetch because of the too many requests and "page result swapping" issues. This PR will allow us to re-enable it! Thank you @m-vo ❤️

@m-vo
Copy link
Copy Markdown
Contributor Author

m-vo commented Feb 1, 2026

Is there anything I could do to move this forward?

/cc @packagethief maybe?

@t1ll
Copy link
Copy Markdown

t1ll commented Feb 6, 2026

Thank you @m-vo for the fix; can't wait for it to be merged

@zoglo
Copy link
Copy Markdown

zoglo commented Feb 17, 2026

I've had the same issue happen to me on GitHub quite a bunch of times when my network was slow.
I guess it's negligible that the URL and/or the content were different when not knowing what causes the issue.

It's just more obvious when knowing that it's a possible bug in the Turbo library and does not happen on faster connections / good optimized pages as often.

@leofeyer
Copy link
Copy Markdown

@packagethief @jorgemanrubia would you be open to merging this PR? Or should this stay an opt-in solution that users implement themselves when needed, as outlined in #1244 (comment)?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Development

Successfully merging this pull request may close these issues.

Turbo does not cancel pending requests that were prefetched on consecutive link clicks

6 participants