question-mark
Stuck on an issue?

Lightrun Answers was designed to reduce the constant googling that comes with debugging 3rd party libraries. It collects links to all the places you might be looking at while hunting down a tough bug.

And, if you’re still stuck at the end, we’re happy to hop on a call to see how we can help out.

`turbo:frame-missing` event not dispatched when code is not 200

See original GitHub issue
<turbo-frame id="my-frame">
    <a href="/non-existing-url">Link to 404 from inside frame</a>
</turbo-frame>

If in the code above you click in the link, turbo:frame-missing is not dispatched.

From my understanding, we are inside of a frame expecting a frame in the response, so the event should be dispatched.

Is this expected from the new turbo:frame-missing event, or am I wrong?

Issue Analytics

  • State:closed
  • Created a year ago
  • Comments:18 (9 by maintainers)

github_iconTop GitHub Comments

2reactions
dhhcommented, Aug 9, 2022

I think the problem is that if you don’t directly setup a turbo:frame-missing handler to deal with the 404, and the frame hits one, you’re leaving the UI in a broken state with no explanation. Maybe the brokenness is contained to the frame, but that hardly makes it better? The user took an action, but got no feedback that it failed.

I think letting all error codes, and therefore all pages without the matching turbo frame, target top is the right default. Better to have the 404 take over the whole page than to fail silently. And then, if you’re a developer who wants to explicitly let 404s be contained, you can catch the event and do your custom work.

1reaction
jon-sullycommented, Aug 22, 2022

EDIT: I’ve since realized the change I describe below has already been made in https://github.com/hotwired/turbo/pull/672 (🎉) and just isn’t released into beta.3 yet! Sweet 😁. Leaving most of the rest of this comment for others who want to run beta.2 but need the event handler code below to avoid a second request.


One additional note I wanted to make after playing with this yesterday is that the behavior of “no matching frame was found, just render the response that was given as a whole page navigation” isn’t quite true currently (beta.2). In https://github.com/hotwired/turbo/pull/445/commits/1043f0def44b182e7e34bb8d631ea38fc7c3277a (one of the latter commits of https://github.com/hotwired/turbo/pull/445) the behavior was changed slightly from “render the exact content that was given” (don’t make another request to the same path) to “request the same path again but as a full visit”. I’d suggest that we may want to revert that change. (EDIT: This happened in https://github.com/hotwired/turbo/pull/672 🎉 )

I can understand that re-requesting the same path would be valuable in the case where potentially only a partial was returned from the initial response, but I’ll wager that that’s very, very unlikely. If no matching frame was found I believe it likely that the response was already a full page of markup. E.g. if we’re protecting against the case where the back-end only served just a frame and we don’t want to render a layout-less page (therefore re-request the whole page as a full navigation), I think that problem is already guarded against by the notion that there is no matching frame. The odds that the back-end served back a response with no matching frame… but is still only a frame, just not the right one, seems… unlikely.

The downside of re-requesting the same path, as noted in several other threads over the last year, is that we lose any flash message/content that would’ve been present in the first response. I think that’s a notable cost.

In the meantime (and for others), the frame-missing event is obviously exposed and we have control to do this ourselves, so here’s the JS snippet I’m using to use the initial request’s HTML rather than re-request the same path again. This is essentially a clone of the ‘before’ from https://github.com/hotwired/turbo/pull/445/commits/1043f0def44b182e7e34bb8d631ea38fc7c3277a. I’ll dump this once beta.3 is out and we hop on it! 👍

document.addEventListener("turbo:frame-missing", async (event) => {
   event.preventDefault()

   const responseHTML = await event.detail.fetchResponse.responseHTML
   const { location, redirected, statusCode } = event.detail.fetchResponse

   Turbo.visit(location, { response: { redirected, statusCode, responseHTML } })
 })
Read more comments on GitHub >

github_iconTop Results From Across the Web

turbo:frame-missing event not dispatched when code ... - GitHub
If I navigate from a page within a frame, to another page without frames, the event is not being fired if the response...
Read more >
Turbostream not replacing the DOM - Hotwire Discussion
I'd like to replace a modal's content dynamically, by rendering an empty modal and then use Turbo stream to replace it.
Read more >
Rails view not displaying partial - "response has no matching ...
The solution was to wrap the results in a turbo frame with an id of "events" like so:- <turbo-frame id="events"> <% if @events.any?...
Read more >
Using TurboStream with the Fetch API - Fly.io
Stimulus enables you to attach JavaScript controllers and actions to your HTML via data- attributes. Turbo Frames encourages you to split out ...
Read more >
How to use Devise with Hotwire & Turbo.js (Example) - GoRails
I tried adding the turbo navigational format to devise and unfortunately that did not fix the problem on user destroy for me. What...
Read more >

github_iconTop Related Medium Post

No results found

github_iconTop Related StackOverflow Question

No results found

github_iconTroubleshoot Live Code

Lightrun enables developers to add logs, metrics and snapshots to live code - no restarts or redeploys required.
Start Free

github_iconTop Related Reddit Thread

No results found

github_iconTop Related Hackernoon Post

No results found

github_iconTop Related Tweet

No results found

github_iconTop Related Dev.to Post

No results found

github_iconTop Related Hashnode Post

No results found