Hotwire Discussion

Flash messages with Turbo

A simple controller that redirects to a path with a flash message works in a traditional rails app because usually there is a part in the app layout that renders flash messages.

However, when used with Turbo frames, flash messages are not shown during a frame controlled redirect as they are not part of the returning frame.

To fix this, I’ve wrapped my flash render view in a turbo frame called :notifications and in the action I use a turbo_stream.erb to send 2 streams down the client: one for the actions main response and a second one just to replace the :notifications frame, so the flash messages are shown.

Using this approach shows the flash message at the right time, but also repeats them on the next full refresh.

I was wondering if there is a “correct” way to deal with flash messages in Hotwire which I am completely missing out.

2 Likes

Are you looking for Flash#now?

BTW, you may be interested in this post by Bram Jetten.

Flash messages with Hotwire and Turbo Streams

kBfdG2Tt6A0QRLFf

Thanks for sharing that. This is what I ended up doing, however I’m trying to find an elegant solution when the action needs to stream a partial to the client itself too. In cases like that, the format.turbo_stream can only send one turbo stream down from the action. To send more than one (the main one and the flash one) together, we need to move the payload to a turbo_stream.erb file and include the flash stream there every time.

I’m not quite following.

However, when used with Turbo frames, flash messages are not shown during a frame controlled redirect as they are not part of the returning frame.

With a “frame controlled redirect”, are you saying the frame is redirected to additional content, but only display in the frame or it redirects the entire page?

So let’s say you want to redirect to a page after a certain operation is done in your action. In a normal Rails setup, you’d do that with a redirect_to. In such scenario, if you want to show a flash message, you then add a flash in the action too.

The suggested approach can either do the redirect OR the flash, not both. For flash to work with a stream, it would need to render a turbo_stream and a redirect would be considered double rendering.

To clarify, you want to be able to have a Rails controller respond with a turbo-stream (instead of a full-page redirect)? And in this scenario, you are getting the flash rendered within the turbo stream, and then on the next full page request. Is this correct?

If yes, does Flash#now solve the problem?