ash_double_entry/lib/balance/transformers/add_structure.ex

80 lines
2.3 KiB
Elixir
Raw Normal View History

defmodule AshDoubleEntry.Balance.Transformers.AddStructure do
2023-09-27 02:46:07 +13:00
# Adds all the structure required for the resource. See the getting started guide for more.
@moduledoc false
use Spark.Dsl.Transformer
import Spark.Dsl.Builder
def before?(Ash.Resource.Transformers.CachePrimaryKey), do: true
def before?(Ash.Resource.Transformers.BelongsToAttribute), do: true
def before?(_), do: false
def transform(dsl) do
2023-12-06 13:49:23 +13:00
storage_type =
if AshDoubleEntry.Balance.Info.balance_money_composite_type?(dsl) do
:money_with_currency
else
:map
end
dsl
2024-04-02 10:21:49 +13:00
|> Ash.Resource.Builder.add_new_attribute(:id, :uuid,
primary_key?: true,
writable?: false,
generated?: true,
allow_nil?: false,
default: &Ash.UUID.generate/0
)
2024-04-02 10:21:49 +13:00
|> Ash.Resource.Builder.add_new_attribute(:balance, AshMoney.Types.Money,
2023-12-06 13:49:23 +13:00
allow_nil?: false,
constraints: [
storage_type: storage_type
]
)
2024-04-02 10:21:49 +13:00
|> Ash.Resource.Builder.add_new_relationship(
:belongs_to,
:transfer,
AshDoubleEntry.Balance.Info.balance_transfer_resource!(dsl),
attribute_type: AshDoubleEntry.ULID,
allow_nil?: false,
attribute_writable?: true
)
2024-04-02 10:21:49 +13:00
|> Ash.Resource.Builder.add_new_relationship(
:belongs_to,
:account,
AshDoubleEntry.Balance.Info.balance_account_resource!(dsl),
allow_nil?: false,
attribute_writable?: true
)
|> add_primary_read_action()
|> Ash.Resource.Builder.add_action(:create, :upsert_balance,
accept: [:balance, :account_id, :transfer_id],
upsert?: true,
upsert_identity: :unique_references
)
|> Ash.Resource.Builder.add_identity(:unique_references, [:account_id, :transfer_id],
pre_check_with: pre_check_with(dsl)
)
end
defbuilder add_primary_read_action(dsl) do
if Ash.Resource.Info.primary_action(dsl, :read) do
{:ok, dsl}
else
Ash.Resource.Builder.add_action(dsl, :read, :_autogenerated_primary_read,
primary?: true,
pagination: Ash.Resource.Builder.build_pagination(keyset?: true)
)
end
end
defp pre_check_with(dsl) do
case AshDoubleEntry.Balance.Info.balance_pre_check_identities_with(dsl) do
:error ->
nil
{:ok, value} ->
value
end
end
end