Generate warning whenever someone exits a live view form without saving

I have a simple phoenix live view form with a save button. I want to generate a warning whenever someone tries to exit a form without saving the form. If they click on any type of link that takes them to a different page I want the warning to be generated(Without the use JS). Would really appreciate the community’s help thanks.

Independently from LiveView, this kind of functionality is normally implemented by means of the beforeunload DOM event, as explained here. It does require a little JavaScript though.

2 Likes

This blog post shows an example of how to use beforeunload with Phoenix hooks.

1 Like

Thanks a lot. That really helped. The only issue I am facing is that if you are navigating away from the form but are still in the same live view then the warning doesn’t come up. Any workaround ?

Perhaps you could do it all in LiveView with a special assign when you open the form and a conditionally rendered data-confirm attribute.

def render(assigns) do
  ~H"""
  <button data-confirm={@data_confirm} phx-click="close_form">Close form</button>
  """
end

def mount(_, _, socket) do
  {:ok, assign(socket, :data_confirm, false)}
end

def handle_event("fill_in_form", _, socket) do
  {:noreply, assign(socket, :data_confirm, "You have unsaved changes.")}
end

def handle_event("close_form", _, socket) do
  {:noreply, assign(socket, :data_confirm, false)}
end

The phx-click event will not be triggered if the user cancels the action.

You’d have to apply this attribute to each clickable element that closes the form, or transform it with assigns_to_attributes

def render(assigns) do
  extras = assigns_to_attributes(assigns)
  assign(assigns, :extras, extras)
  ~H"""
  <button phx-click="close_form" {@extras}>Close form</button>
  """
end

Obviously this won’t do anything if the user closes the browser tab, so maybe you can combine it with JS hooks to cover all bases.