DEV Community

Cover image for Getting Started on Elixir and Ecto Part 3
Kenzy Limon
Kenzy Limon

Posted on

3

Getting Started on Elixir and Ecto Part 3

Schema, Changeset and Data types

At this point, you might start to wonder why you are doing essentially the same thing twice when dealing with Schema and Changeset.

While migrations are liable for giving us the database tables, schemas are liable for how Ecto interacts with those tables.

A schema is an Elixir declaration of data from our database. Besides working as data mappers, embedded_schema/1 and schema/2 can also be used together to decouple how the data is represented in your applications from the database.

schema/2 is typically used to map data from a persisted source, usually a database table, into Elixir structs and vice-versa.

embedded_schema/1 is used for defining schemas that are embedded in other schemas or only exist in memory without ever persisting elsewhere.

Changesets define a pipeline of transformations our data needs to undergo before it will be ready for our application to use. These transformations might include type-casting, user input validation, and filtering out any extraneous parameters.

NOTE: You can actually use an embedded schema to depict your UI, mapping and validating its inputs, and then you convert such embedded schema to other schemas that can persist data to the database.

defmodule Task do
use Ecto.Schema
schema "tasks" do
field :user_id, :integer
field :title, :string
field :description, :string
field :status, :boolean, default: true
field :estimated_time, :float, default: 1.0
field :rate, :float, default: 1.0
field :start_date, :utc_datetime
field :end_date, :utc_datetime
field :plan_start_date, :utc_datetime
field :plan_end_date, :utc_datetime
field :comments, :string
field :cover_image, :string
field :created_by, :integer
field :updated_by, :integer
field :created_at, :utc_datetime
field :updated_at, :utc_datetime
end
embedded_schema do
field :id, :integer
field :title, :string
field :description, :string
end
end

NOTE: The naming convention in Ecto for schemas is a singularized name.

ECTO TYPE  -> ELIXIR TYPE  -> LITERAL SYNTAX IN QUERY

:id -> integer  { 1, 2, ...}
:binary_id -> binary  { <<int, int, ...>> }
:integer -> integer  { 1, 2, ...}
:float -> float  { 1.0, 2.0, ... }
:boolean -> boolean  { true, false }
:string -> UTF-8 encoded string  { "hello" }
:binary -> binary { int, int, ... }
{:array, inner_type} -> list { [value, value, ...] }
:map -> map
{:map, inner_type} -> map
:decimal -> Decimal
:date -> Date
:time -> Time
:time_usec -> Time
:naive_datetime -> NaiveDateTime
:naive_datetime_usec -> NaiveDateTime
:utc_datetime -> DateTime
:utc_datetime_usec -> DateTime
Enter fullscreen mode Exit fullscreen mode

You can easily play around with schema by simply starting an IEx iex -S mix

task = %Taskers.Task{}

We can set values on these fields by generating a new struct:
task = %Taskers.Task{estimated_time: 28}
task = %{task | estimated_time: 3.0}

And retrieve values using this syntax:
task.estimated_time # => 3.0
Enter fullscreen mode Exit fullscreen mode

Sentry blog image

How I fixed 20 seconds of lag for every user in just 20 minutes.

Our AI agent was running 10-20 seconds slower than it should, impacting both our own developers and our early adopters. See how I used Sentry Profiling to fix it in record time.

Read more

Top comments (0)

Billboard image

Try REST API Generation for Snowflake

DevOps for Private APIs. Automate the building, securing, and documenting of internal/private REST APIs with built-in enterprise security on bare-metal, VMs, or containers.

  • Auto-generated live APIs mapped from Snowflake database schema
  • Interactive Swagger API documentation
  • Scripting engine to customize your API
  • Built-in role-based access control

Learn more

👋 Kindness is contagious

Please leave a ❤️ or a friendly comment on this post if you found it helpful!

Okay