Today I Learned

hashrocket A Hashrocket project

Casting Associations in Phoenix

If you want to cast changes on a struct's associations, you can use the changeset function cast_assoc/3. This allows you to make changes to a parent struct and its associations at the same time.

Example

Lets say you have a struct called Artist and an associated schema called Album. The schema for the Album looks something like this:

def module MyApp.Music.Album do
 use Ecto.Schema
 alias MyApp.Music.Artist

  schema "albums" do
    field :title, :string
    
    belongs_to :artist, Artist
  end

  def changeset(artist, params \\ %{}) do
    artist
    |> cast(params, [:title, :artist_id])
    |> validate_required([:title])
  end
end

and the schema for artist looks like this:

def module MyApp.Music.Artist do
 use Ecto.Schema
 alias MyApp.Music.Album

  schema "albums" do
    field :name, :string
    
    has_many :albums, Album
  end
end

Now, if you wanted to build a changeset for the Artist where you can change the artist's name and the title field on an associated album:

def changeset(artist, params \\ %{}) do
    artist
    |> cast(params, [:name])
    |> cast_assoc(:albums, with: &MyApp.Album.changeset/2)
    |> validate_required([:name])
end
See More #elixir TILs
Looking for help? At Hashrocket, we 💜 Elixir! From our many Elixir client projects, to sponsoring the Chicago Elixir Meetup, to the source code for this application, we are invested in this community. Contact us today to talk about your Elixir project.