Hi alchemists,
I know that there are topics with exact same title but they don’t really address my question.
Setup:
- two schemas:
Round
has manyMatches
-
Match
haveresult
field - a form to set round results which write
results
to allMatches
in aRound
Round:
schema "rounds" do
many_to_many :matches, Match, join_through: "round_matches"
end
Match:
schema "matches" do
field :result
end
Form:
h1 Finalize Round
= form_for @changeset, Routes.round_result_path(@conn, :result, @changeset.data), fn f ->
= for match_fields <- inputs_for(f, :matches) do
div
= hidden_input match_fields, :id, value: match_fields.data.id
= label match_fields, :result
= select(match_fields, :result, ["Home Team": "home_team", "Draw": "draw", "Away Team": "away"])
div
= submit "Submit"
When submitted this form output that I split in matches
and round_id
in controller
matches = %{
"0" => %{"id" => "7277d8e5-f239-4474-ada4-09b347e100aa", "result" => "home_team"},
"1" => %{"id" => "ef63696e-dced-46b8-9f2c-edb52d17a93f", "result" => "home_team"},
"10" => %{"id" => "6a3656d3-b756-4f45-9057-68a6d35bb5a3", "result" => "home_team"},
"11" => %{"id" => "db1601f9-0609-45cf-81b4-220f99cd4df8", "result" => "home_team"},
"12" => %{"id" => "0dbc35f0-a3a6-46f8-9391-9e80194f6303", "result" => "home_team"},
"2" => %{"id" => "6cdb7765-60e3-4056-b33e-06e3512973c6", "result" => "home_team"},
"3" => %{"id" => "8c53843c-ba35-44ca-a478-74459bac1c32", "result" => "home_team"},
"4" => %{"id" => "c097502f-6e38-487e-9226-6220f89c13d7", "result" => "home_team"},
"5" => %{"id" => "13b325a7-1723-4b24-a677-f9e2d0a16e5c", "result" => "home_team"},
"6" => %{"id" => "3dfa9ea4-25e7-4381-9f0b-44ae58a757b8", "result" => "home_team"},
"7" => %{"id" => "3b9833b9-baf3-4bd7-95fc-f670e4eb15fb", "result" => "home_team"},
"8" => %{"id" => "1d00d1ff-e6c0-4372-acf0-287d56c67c84", "result" => "home_team"},
"9" => %{"id" => "32fb6c1c-fff6-4dc7-836a-4dfc0aba17a3", "result" => "home_team"}
}
"round_id" = "917789de-56a2-4650-839c-17ff7d63fb3c"
Since I want to update all round matches I decided to go wtih put_assoc
bit it raises an error errors: [matches: {"is invalid", [type: {:array, :map}]}]
when fed a matches
map.
def result_changeset(round, matches_changes) do
round
|> cast(%{}, [])
|> put_assoc(:matches, matches_changes)`
In contrast when I convert that map to a least of maps, each of which contains an id
field and convert string keys to atom keys then everything seems to work fine
matches_changes =
matches_changes
|> Map.values()
|> Enum.map(& Map.new(&1, fn {k, v} -> {String.to_atom(k), v} end))
round
|> cast(%{}, [])
|> put_assoc(:matches, matches_changes)
Am I doing something wrong? I’d expect put_assoc
to be able to work with output produced by inputs_for
without additional rituals.