Hi, all.
I have read several elixir books and the only Ecto book, and still confused on Typespecs. I googled a few articles on typespecs including official Typespect document of Elixir site and questions in elixir forum here, but not clear at all.
For example,
defmodule Friends.Person do
use Ecto.Schema
schema "people" do
field(:first_name, :string)
field(:last_name, :string)
field(:age, :integer)
end
@spec changeset(
{map, map} | %{:__struct__ => atom | %{__changeset__: map}, optional(atom) => any},
:invalid | %{optional(:__struct__) => none, optional(atom | binary) => any}
) :: Ecto.Changeset.t()
def changeset(person, params \\ %{}) do
person
|> Ecto.Changeset.cast(params, [:first_name, :last_name, :age])
|> Ecto.Changeset.validate_required([:first_name, :last_name])
end
end
I hope someone explain the typespec of the changeset function above.
I guess,
- The paremeters of the changeset function can be one of the three:
(1) {map, map},
(2) %{:__struct__ => atom | %{__changeset__: map}, optional(atom) => any}, :invalid ,
(3) %{optional(:__struct__) => none, optional(atom | binary) => any}
- In the first case(1) of {map, map}, The type of the first parameter person is a struct, and that of the second is a map. What is the meaning of {map, map} tuple? That is to say, why {} is necessary here?
- In the second case(2), the changeset function needs only two parameters, then why the third parameter, :invalid atom, is there? What is the meaning of
__strunct__in:__struct__ => atom? What is the meaning of__changeset__in%{__changeset__: map}? What is the meaning of `optional(atom) => any’ here? - What is the meaning of the third case(3)?
%{optional(:__struct__) => none, optional(atom | binary) => any}
It’s quite a verbose question, but it surely will help many novices in the future who visit this forum or googling similar questions.
Always thank you all.






















