Postgres reference with non-"id" primary keys

Hey, I have these two resources:
defmodule Moneybadger.Ledger.Expense do
use Ash.Resource,
data_layer: AshPostgres.DataLayer

alias Moneybadger.Ledger.Currency

attributes do
uuid_primary_key :id

attribute :name, :string do
allow_nil? false
end

attribute :amount, :decimal do
allow_nil? false
end

attribute :date, :date

timestamps()
end

relationships do
belongs_to :currency, Currency do
allow_nil? false
attribute_type :string
destination_attribute :code
end
end

actions do
defaults [:create, :read]
end

code_interface do
...
end

postgres do
table "expenses"
repo Moneybadger.Repo

references do
reference :currency, on_delete: :delete, on_update: :update
end
end
end
defmodule Moneybadger.Ledger.Expense do
use Ash.Resource,
data_layer: AshPostgres.DataLayer

alias Moneybadger.Ledger.Currency

attributes do
uuid_primary_key :id

attribute :name, :string do
allow_nil? false
end

attribute :amount, :decimal do
allow_nil? false
end

attribute :date, :date

timestamps()
end

relationships do
belongs_to :currency, Currency do
allow_nil? false
attribute_type :string
destination_attribute :code
end
end

actions do
defaults [:create, :read]
end

code_interface do
...
end

postgres do
table "expenses"
repo Moneybadger.Repo

references do
reference :currency, on_delete: :delete, on_update: :update
end
end
end
defmodule Moneybadger.Ledger.Currency do
use Ash.Resource,
data_layer: AshPostgres.DataLayer

alias Moneybadger.Ledger.Expense

attributes do
attribute :code, :string do
primary_key? true
allow_nil? false
end
end

relationships do
has_many :expenses, Expense
end

actions do
defaults [:create]
end

code_interface do
...
end

postgres do
table "currencies"
repo Moneybadger.Repo
end
end
defmodule Moneybadger.Ledger.Currency do
use Ash.Resource,
data_layer: AshPostgres.DataLayer

alias Moneybadger.Ledger.Expense

attributes do
attribute :code, :string do
primary_key? true
allow_nil? false
end
end

relationships do
has_many :expenses, Expense
end

actions do
defaults [:create]
end

code_interface do
...
end

postgres do
table "currencies"
repo Moneybadger.Repo
end
end
And I'm getting this compile error:
== Compilation error in file lib/moneybadger/ledger/resources/currency.ex ==
** (ArgumentError) schema does not have the field :id used by association :expenses, please set the :references option accordingly
(ecto 3.10.3) lib/ecto/association.ex:696: Ecto.Association.Has.struct/3
(ecto 3.10.3) lib/ecto/schema.ex:1891: Ecto.Schema.association/5
(ecto 3.10.3) lib/ecto/schema.ex:2032: Ecto.Schema.__has_many__/4
== Compilation error in file lib/moneybadger/ledger/resources/currency.ex ==
** (ArgumentError) schema does not have the field :id used by association :expenses, please set the :references option accordingly
(ecto 3.10.3) lib/ecto/association.ex:696: Ecto.Association.Has.struct/3
(ecto 3.10.3) lib/ecto/schema.ex:1891: Ecto.Schema.association/5
(ecto 3.10.3) lib/ecto/schema.ex:2032: Ecto.Schema.__has_many__/4
I would appreciate any help on or pointers to how to fix this and tell Ash that my primary reference is indeed not :id but :code. Thanks, Michal
3 Replies
ZachDaniel
ZachDaniel2y ago
Add source_attribute :code to the expenses relationship. We could likely improve that default behavior there.
michaljanocko
michaljanockoOP2y ago
Great, thanks! This is my second time trying out Ash and I'm really loving it so far!
ZachDaniel
ZachDaniel2y ago
LMK if you have any other questions!

Did you find this page helpful?