Push_event followed by push_redirect does not call the JavaScript hook?


I have a LiveComponent (the :new :edit modal that came with a mix phx.gen.live for instance).

In the save handle_event I’m doing this:

def handle_event("save", params, socket) do
     |> put_flash(:info, "Template updated successfully")
     |> push_event("save", params)
     |> push_redirect(to: socket.assigns.return_to)}

In the app.js I have the following JavaScript hook:

let hooks = {}
hooks.template = {
	mounted() {
		this.handleEvent("save", (template) => {
			console.log("save", template);
			localStorage.setItem(template.name, template.content);

I’m just trying to save to local storage the form in the live component.

When I remove the push_redirect the hook gets called. When the push_redirect is executed the hook does not get called.

I’m not sure why first, and is there a better way to do this? How can I call a JS hook with the push_redirect after?


I will add a note to the docs but the short answer is no: events are not called because all event handlers are invoked after patches/redirects/etc are applied.

The simplest approach in your case is to only emit the events and, once you handle them, you use pushEvent on the client to ask the server to redirect. This has benefit of guaranteeing, regardless of the LV implementation, that the redirect only happens after it was written to the storage.

1 Like

Thanks, using the pushEvent in my hook I was expecting the handle_event to be called in the “caller” (the LiveComponent) and not in the parent LiveView, for instance I have this:

MyApp.PageLive.Index which uses the live_modal to load the MyApp.PageLive.FormComponent.

The push_event is in the FormComponent, I was expecting the callback to be call there from the JavaScript hook.

I moved the callback handlers to MyApp.PageLive.Index.

See pushEventTo, it will allow you to send it to a component. What you need to do is to include a phx-target=<%= @myself %> in the same element you add the phx-hook and then read the value of phx-target, giving it to pushEventTo.