I have a sticky liveview, for a stateful navigation tree, which is shared across multiple pages. I navigate between the pages using link_patch() and would like the sticky liveview to get the params. Unfortunately, the handle_params() callback is not supported by child liveviews (sticky or not).
Currently, my convoluted solution is to generate a unique ‘tree_id’ in the handle_params() callback of the parent page (if it does not already exist in the URL) and pass it to the sticky liveview in the session. The navigation tree subscribes to that tree_id topic and appends the tree_id to every link_patch() URL.
On navigating, the handle_params() of the new parent page is called and I publish a message to the tree_id topic to inform the tree liveview of the params change.
I then use PubSub to send a message to the tree liveview to let it know the params have changed.
This works but seems needlessly convoluted. Is there an alternative I am missing?
I have to use a liveview for the tree as it receives handle_info() callbacks. It has to be shared between multiple pages (I initially used a single page for all possible routes but this became a behemoth).
The challenge appears to be that sticky liveviews are, by necessity, divorced from their parents so that they can persist between page changes.
I tried this method once too and did not have any luck with it. You can ditch the sticky liveview, put a function component in your layout and add on_mount hooks to add the necessary functionality to all the pages.
I’m not sure I can go that way. I need a child liveview because I need the handle_info() callback. Also, I think on_mount() does allow me to inject state for many pages using a live_session() but I need to store that state somewhere outside of the component. I’ll keep reading as it’s more than likely I have misunderstood some nuances in the livebeats app.
I was hoping I had missed the really straightforward send(parent_id…) approach
My understanding (after much IO.inspect()) is that
attaching hooks to the live session is a shorthand means of attaching hooks to every route within the session.
on navigating to a route, the hooks will run again.
The socket.assigns is reset prior to running the hooks so no information persists between navigations.
You were correct in suggesting attach_hook() to inject common handle_info() and handle_event() callbacks. That worked well.
Unfortunately, I am managing the folder tree using an in-memory digraph which is initialized once on mounting the sticky liveview. I need to persist the digraph between route changes (hence the desire to use a sticky liveview). The on_mount() hook regenerates the digraph each time so I lose the open/close state.
Honestly, I didn’t expect a shared stateful layout to be this challenging. I’m probably going to go back to a single liveview, a non-sticky liveview tree child and live actions to render the correct content.