How to set optional keys?

I have only two required keys, others are optional, I tried this:

def changeset(student, params \\ %{}) do
    student
    |> cast(params, [:name, :school_id], [:father_id , :mother_id , :section, :gender, :comment, :city, :pick_up_address, :pick_up_lat, :pick_up_lng, :drop_off_address, :drop_off_lat, :drop_off_lng, :created_at])
    |> check_constraint(:gender)
  end

considering that 4th arg is the optional keys, as here: https://hexdocs.pm/ecto/Ecto.Changeset.html#cast/4

but, cast/4 is depreciated, and I could not follow documentation, currently I get this error:

** (exit) an exception was raised:
    ** (KeyError) key :drop_off_lat not found in: %{created_at: #Ecto.DateTime<2017-05-08 13:07:24>, father_id: nil, gender: "Male", mother_id: nil, name: "Ethel Waters", school_id: 1}
        (trackware) web/controllers/csvs_controller.ex:288: anonymous fn/2 in Trackware.CsvsController.write_ecto_rows_schools/4
        (trackware) web/controllers/csvs_controller.ex:224: Trackware.CsvsController.write_ecto_rows_schools/4
        (elixir) lib/task/supervised.ex:85: Task.Supervised.do_apply/2
        (elixir) lib/task/supervised.ex:36: Task.Supervised.reply/5
        (stdlib) proc_lib.erl:247: :proc_lib.init_p_do_apply/3

This error has nothing to do with this function that you’re showing. The error happens on web/controllers/csvs_controller.ex:288.

Ops! sorry for that, but anyway, how to set optional keys?

I’m not entirely sure what you mean by set, but the correct modern way to do the changeset function you have is

    student
    |> cast(params,[:name, :school_id, :father_id , :mother_id , :section, :gender, :comment, :city, :pick_up_address, :pick_up_lat, :pick_up_lng, :drop_off_address, :drop_off_lat, :drop_off_lng, :created_at])
    |> validate_required([:name, :school_id])
    |> check_constraint(:gender)
1 Like

Ah, so all keys are optional, unless I use validate_required to make them required?

That’s correct.

1 Like