fix: don't use :same return type for most operators

fix: don't use returns as basis type unless explicitly allowed
This commit is contained in:
Zach Daniel 2024-07-14 11:22:20 -04:00
parent a665a17c59
commit c5b118a37c
4 changed files with 34 additions and 10 deletions

View file

@ -835,14 +835,9 @@ defmodule Ash.Expr do
{type, constraints}
end
def determine_types(mod, values, returns) do
def determine_types(mod, values, known_result) do
Code.ensure_compiled(mod)
basis =
if returns && returns != [:any, :same, {:array, :any}, {:array, :same}] do
returns
end
name =
cond do
function_exported?(mod, :operator, 0) ->
@ -893,6 +888,27 @@ defmodule Ash.Expr do
length(typeset) == length(values)
end)
|> Enum.find_value({Enum.map(values, fn _ -> nil end), nil}, fn {typeset, returns} ->
basis =
cond do
!returns ->
nil
returns == :same ->
known_result
returns == {:array, :same} ->
case known_result do
{:array, type} ->
type
_ ->
nil
end
true ->
nil
end
types_and_values =
if typeset == :same do
Enum.map(values, &{:same, &1})

View file

@ -20,7 +20,8 @@ defmodule Ash.Query.Operator.Basic do
div: [
symbol: :/,
no_nils: true,
evaluate_types: :numbers
evaluate_types: :numbers,
returns: [:float]
],
concat: [
symbol: :<>,

View file

@ -11,8 +11,7 @@ defmodule Ash.Query.Operator.Eq do
operator: :==,
name: :eq,
predicate?: true,
types: [:any, :same],
returns: [:boolean]
types: [:any, :same]
def new(left, right) do
{:ok, struct(__MODULE__, left: left, right: right)}

View file

@ -399,7 +399,15 @@ defmodule Ash.Query.Operator do
def predicate?, do: unquote(opts[:predicate?] || false)
@impl Ash.Query.Operator
def returns, do: unquote(opts[:returns] || [:same])
if unquote(opts[:predicate?]) do
def returns do
Enum.map(List.wrap(unquote(opts[:types])), fn _ -> :boolean end)
end
else
def returns do
unquote(opts[:returns] || :unknown)
end
end
@impl Ash.Query.Operator
def types do