Skip to content

Commit

Permalink
fix: backport fix to changing_attributes and atomic validations (#1098
Browse files Browse the repository at this point in the history
)
  • Loading branch information
vonagam authored May 2, 2024
1 parent 61a537d commit 3bc2b9c
Show file tree
Hide file tree
Showing 4 changed files with 15 additions and 19 deletions.
13 changes: 6 additions & 7 deletions lib/ash/policy/check/changing_attributes.ex
Original file line number Diff line number Diff line change
Expand Up @@ -41,27 +41,26 @@ defmodule Ash.Policy.Check.ChangingAttributes do

{{:ok, from}, {:ok, to}} ->
if expr == true do
{:cont,
Ash.Expr.expr(not (^ref(attribute) == ^from and ^atomic_ref(attribute) == ^to))}
{:cont, Ash.Expr.expr(^ref(attribute) == ^from and ^atomic_ref(attribute) == ^to)}
else
{:cont,
Ash.Expr.expr(
^expr and not (^ref(attribute) == ^from and ^atomic_ref(attribute) == ^to)
^expr and ^ref(attribute) == ^from and ^atomic_ref(attribute) == ^to
)}
end

{{:ok, from}, :error} ->
if expr == true do
{:cont, Ash.Expr.expr(^ref(attribute) != ^from)}
{:cont, Ash.Expr.expr(^ref(attribute) == ^from)}
else
{:cont, Ash.Expr.expr(^expr and ref(attribute) != ^from)}
{:cont, Ash.Expr.expr(^expr and ref(attribute) == ^from)}
end

{:error, {:ok, to}} ->
if expr == true do
{:cont, Ash.Expr.expr(^atomic_ref(attribute) != ^to)}
{:cont, Ash.Expr.expr(^atomic_ref(attribute) == ^to)}
else
{:cont, Ash.Expr.expr(^expr and ^atomic_ref(attribute) != ^to)}
{:cont, Ash.Expr.expr(^expr and ^atomic_ref(attribute) == ^to)}
end
end
else
Expand Down
3 changes: 2 additions & 1 deletion lib/ash/resource/validation/attribute_in.ex
Original file line number Diff line number Diff line change
Expand Up @@ -46,7 +46,8 @@ defmodule Ash.Resource.Validation.AttributeIn do

@impl true
def atomic(_changeset, opts, context) do
{:atomic, [opts[:attribute]], Ash.Expr.expr(^atomic_ref(opts[:attribute]) in ^opts[:list]),
{:atomic, [opts[:attribute]],
Ash.Expr.expr(^atomic_ref(opts[:attribute]) not in ^opts[:list]),
Ash.Expr.expr(
error(^InvalidAttribute, %{
field: ^opts[:attribute],
Expand Down
2 changes: 1 addition & 1 deletion lib/ash/resource/validation/changing.ex
Original file line number Diff line number Diff line change
Expand Up @@ -56,7 +56,7 @@ defmodule Ash.Resource.Validation.Changing do
@impl true
def atomic(_changeset, opts, context) do
{:atomic, [opts[:field]],
Ash.Expr.expr(^atomic_ref(opts[:attribute]) != ^ref(opts[:attribute])),
Ash.Expr.expr(^atomic_ref(opts[:attribute]) == ^ref(opts[:attribute])),
Ash.Expr.expr(
error(^InvalidAttribute, %{
field: ^opts[:field],
Expand Down
16 changes: 6 additions & 10 deletions lib/ash/resource/validation/present.ex
Original file line number Diff line number Diff line change
Expand Up @@ -94,14 +94,13 @@ defmodule Ash.Resource.Validation.Present do
end

def atomic_for_values(opts, context, values) do
attribute_count = length(opts[:attributes])
nil_count = expr(count_nils(^values))

opts
|> Keyword.delete(:attributes)
|> Enum.map(fn
{:exactly, exactly} ->
attribute_count = length(opts[:attributes])

message =
cond do
context[:message] ->
Expand Down Expand Up @@ -137,7 +136,7 @@ defmodule Ash.Resource.Validation.Present do
})
)}
else
exactly_nil = Enum.count(opts[:attributes]) - exactly
exactly_nil = attribute_count - exactly

{:atomic, opts[:attributes], expr(^nil_count != ^exactly_nil),
expr(
Expand All @@ -151,11 +150,9 @@ defmodule Ash.Resource.Validation.Present do
end

{:at_least, at_least} ->
attributes = Enum.map(opts[:attributes], fn attr -> expr(^atomic_ref(attr)) end)

at_most_nil = Enum.count(opts[:attributes]) - at_least
at_most_nil = attribute_count - at_least

{:atomic, opts[:attributes], expr(count_nils(^attributes) > ^at_most_nil),
{:atomic, opts[:attributes], expr(^nil_count > ^at_most_nil),
expr(
error(^InvalidAttribute, %{
field: ^Enum.at(opts[:attributes], 0),
Expand All @@ -166,10 +163,9 @@ defmodule Ash.Resource.Validation.Present do
)}

{:at_most, at_most} ->
attributes = Enum.map(opts[:attributes], fn attr -> expr(^atomic_ref(attr)) end)
at_least_nil = Enum.count(opts[:attributes]) - at_most
at_least_nil = attribute_count - at_most

{:atomic, opts[:attributes], expr(count_nils(^attributes) < ^at_least_nil),
{:atomic, opts[:attributes], expr(^nil_count < ^at_least_nil),
expr(
error(^InvalidAttribute, %{
field: ^Enum.at(opts[:attributes], 0),
Expand Down

0 comments on commit 3bc2b9c

Please sign in to comment.