Nested forms questions

I'm building a nested form with a single resource that can be nested as many times as the user wants. I cannot use manage_relationship/4 in my case so I'm using after_action hooks that don't seem to work with auto?: true. 1. Is there a way to get a behaviour similar to auto?: true? I'm currently specifying the forms option using a function that just generates recursive options for n levels deep and results in
forms: [
direct_child_listings: [
type: :list,
resource: App.Listings.Listing,
create_action: :create,
forms: [
direct_child_listings: [
# ...
forms: [
direct_child_listings: [
type: :list,
resource: App.Listings.Listing,
create_action: :create
]
forms: [
direct_child_listings: [
type: :list,
resource: App.Listings.Listing,
create_action: :create,
forms: [
direct_child_listings: [
# ...
forms: [
direct_child_listings: [
type: :list,
resource: App.Listings.Listing,
create_action: :create
]
2. Using Form.add_form, is there a way to get the path of a newly created form? In this case I could update the form to solve question 1. 3. It looks like all form levels track the params of their nested forms. When updating a form I cannot see the change on my page unless I run something like add_form again – this seems to update all params. Is there a way to refresh the params manually?
Form.update_form(socket.assigns.form, path, fn form ->
Form.validate(form, %{"type" => "type", "subtype" => subtype})
end)
Form.update_form(socket.assigns.form, path, fn form ->
Form.validate(form, %{"type" => "type", "subtype" => subtype})
end)
5 Replies
ZachDaniel
ZachDaniel2y ago
There is an option called updater that can be placed in your forms that allows for lazy computing of child options
defp direct_child_listings() do
[
type: :list,
resource: App.Listings.Listing,
create_action: :create,
forms: [],
updater: fn opts ->
Keyword.update!(opts, :forms, &Keyword.put(&1, :direct_child_listings, direct_child_lists())
end
]
end
defp direct_child_listings() do
[
type: :list,
resource: App.Listings.Listing,
create_action: :create,
forms: [],
updater: fn opts ->
Keyword.update!(opts, :forms, &Keyword.put(&1, :direct_child_listings, direct_child_lists())
end
]
end
So then you'd specify your stuff like forms: [direct_child_listings: direct_child_listings()] This allows for lazily evaluated arbitrary nesting
zimt28
zimt28OP2y ago
Nice, problem 1 solved 🙂 Any ideas about 2 and 3? I can solve no 2 by just following the path, so that's not super important Using my new helper I can just add and remove a new child to "refresh" the form, it works for now but I'd like to see it there's a better solution to both questions
ZachDaniel
ZachDaniel2y ago
sorry, got distracted 🙂 I think what you need to do is something like form = update_form(...) and then validate(form, AshPhoenix.Form.params(form)) Looking into making add_form return the added form so you can do that more easily, and TBH its a PITA. It can be done, just some code I don't have time to write
zimt28
zimt28OP2y ago
All right, I'll open an issue Using the updater, is there a way to get the parent form so that I can build the forms dynamically?
ZachDaniel
ZachDaniel2y ago
Nope. Youll need to capture the parent form in your updater Like form = parent; updater = fn opts -> form .. end;

Did you find this page helpful?