The following was generated automatically by ecto in the User
module:
@doc false
def changeset(user, attrs) do
user
|> cast(attrs, [:uid_nf])
|> validate_required([:uid_nf])
|> unique_constraint(:uid_nf)
end
What is the point of having two separate parameters (user and attrs) and then casting those to user? Most examples I see online just end up calling changeset
with an empty User
struct, like this: Mvsg.Interaction.changeset(%Interaction{}, %{uid_nf: 1})
.
Also, I can put the data on the first parameter instead of the second, and insertion into the database still works:
iex(14)> cs1 = User.changeset(%Mvsg.User{uid_nf: 37}, %{})
#Ecto.Changeset<action: nil, changes: %{}, errors: [], data: #Mvsg.User<>,
valid?: true>
iex(15)> cs2 = User.changeset(%Mvsg.User{}, %{uid_nf: 38})
#Ecto.Changeset<
action: nil,
changes: %{uid_nf: 38},
errors: [],
data: #Mvsg.User<>,
valid?: true
>
iex(16)> Repo.insert(cs1)
[debug] QUERY OK db=11.3ms
INSERT INTO `users` (`uid_nf`,`inserted_at`,`updated_at`) VALUES (?,?,?) [37, ~N[2019-08-06 16:58:42], ~N[2019-08-06 16:58:42]]
{:ok,
%Mvsg.User{
__meta__: #Ecto.Schema.Metadata<:loaded, "users">,
id: 7,
inserted_at: ~N[2019-08-06 16:58:42],
uid_nf: 37,
updated_at: ~N[2019-08-06 16:58:42]
}}
iex(17)> Repo.insert(cs2)
[debug] QUERY OK db=11.6ms
INSERT INTO `users` (`uid_nf`,`inserted_at`,`updated_at`) VALUES (?,?,?) [38, ~N[2019-08-06 16:58:44], ~N[2019-08-06 16:58:44]]
{:ok,
%Mvsg.User{
__meta__: #Ecto.Schema.Metadata<:loaded, "users">,
id: 8,
inserted_at: ~N[2019-08-06 16:58:44],
uid_nf: 38,
updated_at: ~N[2019-08-06 16:58:44]
}}
Looking at the changests, it seems the only difference is that cs1
stores the new data in cs1.data
while cs2
stores it in cs2.changes
.