fix: ignore?: true still accumulates changes

fix: properly require_attributes before setting defaults
This commit is contained in:
Zach Daniel 2021-05-18 01:44:10 -04:00
parent e43ca47ec4
commit 013b49c2b2
4 changed files with 29 additions and 31 deletions

View file

@ -47,6 +47,7 @@ defmodule Ash.Actions.ManagedRelationships do
end) end)
|> Enum.flat_map(fn {relationship, inputs} -> |> Enum.flat_map(fn {relationship, inputs} ->
inputs inputs
|> Enum.reject(fn {_, opts} -> opts[:ignore?] end)
|> Enum.with_index() |> Enum.with_index()
|> Enum.map(fn {{input, opts}, index} -> |> Enum.map(fn {{input, opts}, index} ->
{{relationship, {input, opts}}, index} {{relationship, {input, opts}}, index}
@ -321,6 +322,7 @@ defmodule Ash.Actions.ManagedRelationships do
end) end)
|> Enum.flat_map(fn {key, batches} -> |> Enum.flat_map(fn {key, batches} ->
batches batches
|> Enum.reject(fn {_, opts} -> opts[:ignore?] end)
|> Enum.with_index() |> Enum.with_index()
|> Enum.map(fn {{batch, opts}, index} -> |> Enum.map(fn {{batch, opts}, index} ->
opts = Keyword.put(opts, :authorize?, engine_opts[:authorize?] && opts[:authorize?]) opts = Keyword.put(opts, :authorize?, engine_opts[:authorize?] && opts[:authorize?])

View file

@ -455,9 +455,9 @@ defmodule Ash.Changeset do
|> Map.put(:__validated_for_action__, action.name) |> Map.put(:__validated_for_action__, action.name)
|> cast_params(action, params || %{}, opts) |> cast_params(action, params || %{}, opts)
|> validate_attributes_accepted(action) |> validate_attributes_accepted(action)
|> set_defaults(changeset.action_type, false)
|> run_action_changes(action, opts[:actor])
|> require_values(action.type, false, action.require_attributes) |> require_values(action.type, false, action.require_attributes)
|> run_action_changes(action, opts[:actor])
|> set_defaults(changeset.action_type, false)
|> add_validations() |> add_validations()
|> mark_validated(action.name) |> mark_validated(action.name)
|> require_arguments(action) |> require_arguments(action)
@ -1076,10 +1076,6 @@ defmodule Ash.Changeset do
end end
@manage_opts [ @manage_opts [
ignore?: [
type: :any,
hide: true
],
type: [ type: [
type: {:one_of, @manage_types}, type: {:one_of, @manage_types},
doc: """ doc: """
@ -1227,6 +1223,14 @@ defmodule Ash.Changeset do
type: :any, type: :any,
doc: doc:
"Freeform data that will be retained along with the options, which can be used to track/manage the changes that are added to the `relationships` key." "Freeform data that will be retained along with the options, which can be used to track/manage the changes that are added to the `relationships` key."
],
ignore?: [
type: :any,
default: false,
doc: """
This tells Ash to ignore the provided inputs when actually running the action. This can be useful for
building up a set of instructions that you intend to handle manually
"""
] ]
] ]

View file

@ -34,10 +34,6 @@ defmodule Ash.Resource.Change.Builtins do
```elixir ```elixir
change manage_relationship(:add_comments, :comments, on_missing: :ignore, on_match: :no_match, on_no_match: {:create, :add_comment_to_post} change manage_relationship(:add_comments, :comments, on_missing: :ignore, on_match: :no_match, on_no_match: {:create, :add_comment_to_post}
``` ```
A special `:ignore?` option can be passed to tell the change not to actually happen.
This is useful specifically if you have tooling that looks for `manage_relationship` changes,
like `ash_admin`, but you want to actually handle the input yourself.
""" """
def manage_relationship(argument, relationship_name \\ nil, opts) do def manage_relationship(argument, relationship_name \\ nil, opts) do
relationship_name = relationship_name || argument relationship_name = relationship_name || argument

View file

@ -8,9 +8,6 @@ defmodule Ash.Resource.Change.ManageRelationship do
end end
def change(changeset, opts, _) do def change(changeset, opts, _) do
if opts[:ignore?] do
changeset
else
case Changeset.fetch_argument(changeset, opts[:argument]) do case Changeset.fetch_argument(changeset, opts[:argument]) do
{:ok, argument_value} -> {:ok, argument_value} ->
destination = Ash.Resource.Info.related(changeset.resource, opts[:relationship]) destination = Ash.Resource.Info.related(changeset.resource, opts[:relationship])
@ -33,7 +30,6 @@ defmodule Ash.Resource.Change.ManageRelationship do
changeset changeset
end end
end end
end
defp from_structs(argument_value, destination) when is_list(argument_value) do defp from_structs(argument_value, destination) when is_list(argument_value) do
Enum.map(argument_value, &from_structs(&1, destination)) Enum.map(argument_value, &from_structs(&1, destination))