From 1bbe7c34dbeebe73dff1d1664f4392d264f451cf Mon Sep 17 00:00:00 2001 From: Zach Daniel Date: Tue, 16 Aug 2022 22:16:47 -0400 Subject: [PATCH] fix: mark forms updated with `update_form/4` as touched by default --- lib/ash_phoenix/form/form.ex | 40 ++++++++++++++++++++++++++++++++---- test/form_test.exs | 20 ++++++++++++++++++ 2 files changed, 56 insertions(+), 4 deletions(-) diff --git a/lib/ash_phoenix/form/form.ex b/lib/ash_phoenix/form/form.ex index a32caa1..ddff0b2 100644 --- a/lib/ash_phoenix/form/form.ex +++ b/lib/ash_phoenix/form/form.ex @@ -1370,8 +1370,18 @@ defmodule AshPhoenix.Form do end end + @update_form_opts [ + mark_as_touched?: [ + type: :boolean, + default: true, + doc: "Whether or not to mark the path to the updating form as touched" + ] + ] + @spec update_form(t(), list(atom | integer) | String.t(), (t() -> t())) :: t() - def update_form(form, path, func) do + def update_form(form, path, func, opts \\ []) do + opts = Ash.OptionsHelpers.validate!(opts, @update_form_opts) + path = case path do [] -> @@ -1395,14 +1405,36 @@ defmodule AshPhoenix.Form do List.update_at(nested_forms, integer, &update_form(&1, rest, func)) end) - %{form | forms: new_forms} + if opts[:mark_as_touched?] do + %{ + form + | forms: new_forms, + touched_forms: MapSet.put(form.touched_forms, to_string(atom)) + } + else + %{ + form + | forms: new_forms + } + end [atom | rest] -> new_forms = form.forms - |> Map.update!(atom, &update_form(&1, rest, func)) + |> Map.update!(atom, &update_form(&1, rest, func, opts)) - %{form | forms: new_forms} + if opts[:mark_as_touched?] do + %{ + form + | forms: new_forms, + touched_forms: MapSet.put(form.touched_forms, to_string(atom)) + } + else + %{ + form + | forms: new_forms + } + end end end diff --git a/test/form_test.exs b/test/form_test.exs index 756be7a..1c6b641 100644 --- a/test/form_test.exs +++ b/test/form_test.exs @@ -51,6 +51,26 @@ defmodule AshPhoenix.FormTest do "Unhandled error in form submission for AshPhoenix.Test.Comment.create_with_unknown_error" end + test "update_form marks touched by default" do + form = + Post + |> Form.for_create(:create, + api: Api, + params: %{"text" => "bar"}, + forms: [ + comments: [ + type: :list, + resource: Comment, + create_action: :create_with_unknown_error + ] + ] + ) + |> Form.add_form([:comments], params: %{"text" => "foo"}) + |> Form.update_form([:comments, 0], & &1) + + assert MapSet.member?(form.touched_forms, "comments") + end + test "errors are not set on the parent and single child form" do form = Comment