Nested LiveView, clarification about assign_new

Hello guys,

I’ve used LiveViews for some time but now it’s the first time I’m using nested LV. I’m using a child LV for a custom select widget with lookup on the db and selection in a modal dialog. I thought I needed a child LV instead of a child component to better handle communication with the lookup table (with filter features) and the dialog that are componentized already. The form is managed by the root and master LV.

Anyway… I stumbled upon the issue of sending the details for the lookup to the child LV. Having previously used only root LVs I was accustomed to having the parameters, but for a non-root LV only the session seems available on the invocation of live_render, but seemed the wrong way.

Then I saw here the mention of assign_new and I read its documentation. From what I read I understand that I can use it to get the parent assigns from the child, LV, am I wrong? I’ve done a small manual test on my code and I’m unable to get that behaviour.

Am I missing something? Do you have a code example that doesn’t involves the usage of the session map? (only string keys? seems silly) (also I would like to use it for real session global data)

More generally how do you managed to have some kind of complex form widgets that designed to let the user perform some kind of task related to data associations?

Were you able to solve this?

Can you give us a gist or a test app we can take a look to help you further?

Unless you need handle_info you don’t need a nested LV, you can do just fine with components. You can feed your filter component with data it will need from the parent when you render it and send messages to the parent LV whenever you need so the parent will set the correct association the user chose in the component.

no, not yet. I’m currently try to understand what @josevalim (to the bug I’ve opened, see next paragraph) answer means and if I’m correct understanding that it’s a bug in the JS code and if it’s possible to code a test case that then can be run with git bisect to find the commit that introduced the bug.

of course, a test application that shows the problem is linked to the issue that I have opened on LV’s repo.

My use case is essentially to lookup an association item of a foreign key. The user chooses the associated item ( how is not important) and when the form is submitted the foreign key value is saved.

Ideally, I would like to pass the details of the association in the live_component/live_render call, and having the component/subview send an info/event to the parent LV with the choosed FK.

For reuse and encapsulation, the less they know of each other, the better.

Following this preference then the choice of the right “tool” to use for the “widget” depends it’s complexity and the constraints of the framework and in my case, the UI uses a modal dialog live_component (that I’ve already developed) that uses send_update and handle_info under the hood to show up and then communicate the exit status of the interaction with the user. Now as it seems to me if reusability/encapsulation is a goal and I don’t want to rewrite the dialog, the sub-LV is the best tool for the job. The only drawback is the additional process created.

It’s also possible that I’m unable to see a simpler solution that is in fron of my eyes (you must know that I’m a relatively new Elixir/Phoenix developer), hence my call for help here :slight_smile:.

I’ll read your issue with more time as soon as I can.

I noticed you highlighted you want to use a modal in multiple places so I’m assuming this is one of the pieces you want to reuse. Have you seen the live_modal/3 the Chirp demo app uses? Maybe you can get some insights from it.

You can see it here: https://github.com/dersnek/chirp

I mentioned this because it looks like you have your app that is rendering the form (with or without a LV), then you developed a “modal component” and you have the actual “modal content that filters the association”. From what I understood your modal is doing more than it should if it is bridging the communication between what it shows and the parent LV.

I will read the issue and check your app. Will try to get back with some results.

thanks

Interesting, thanks. I didn’t knew it
You’re right, one of the components I want to reuse is a dialog. I could also show the filter not in a modal dialog and that’s what I’ll do until the bug is fixed or I find a work around it.

From what I see Chirp’s dialog is a simplified version of mine. Unfortunately I cannot show the code of the entire because it contains some details of my client, but you can see my dialog code here: dialog.ex · GitHub .

As you can see, my dialog is a bit more flexible but also needs more support from the calling context.

The main difference between the two is that in Chirp’s dialog the closing is detected with a patch to the location address (which may be not a tecnique I would like to use as it means a call to handle_params to the root LV) and in mine it’s an event generated by JS, handled by the component but then proxied to the LV.

So no, I have a modal dialog component that takes some other code/component that does the actual filtering and has the selection state, the dialog only has the shown/hidden state.

I can agree with you that it’s not always the preferred approach, but I tend to create units of behaviour that tries to do one thing well in a way that fulfills a broader need instead of having more components of different complexity that do more or less the same thing just to cover different needs.

Thanks for your time and effort but please bear in mind that the demo application linked to the issue only shows the “problem” with assign_new, and nothing more.

Thanks again

1 Like