defmodule Ash.Resource.Transformers.DefaultPrimaryKey do @moduledoc """ Creates the default primary key if one applies. Currently, the only resources that get a default primary key are embedded resources. The reason for this is that resources must have a primary key, and embedded resources actually make sense without one. But this is simulated with a private uuid primary key. """ use Ash.Dsl.Transformer alias Ash.Dsl.Transformer alias Ash.Error.Dsl.DslError @extension Module.concat(["Ash", Resource, Dsl]) def transform(resource, dsl_state) do if Ash.Resource.Info.embedded?(resource) do has_pkey? = resource |> Ash.Resource.Info.attributes() |> Enum.any?(& &1.primary_key?) if has_pkey? do {:ok, dsl_state} else case Transformer.build_entity(@extension, [:attributes], :uuid_primary_key, name: :autogenerated_id, private?: true ) do {:ok, attribute} -> {:ok, Transformer.add_entity(dsl_state, [:attributes], attribute)} {:error, error} -> {:error, DslError.exception( module: __MODULE__, message: "Could not create default primary key for embedded resource: #{inspect(error)}", path: [:attributes, :autogenerated_id] )} end end else {:ok, dsl_state} end end def after?(Ash.Resource.Transformers.BelongsToSourceField), do: true def after?(_), do: false end