Skip to content

Instantly share code, notes, and snippets.

@alanpeabody
Last active January 3, 2024 03:29
Show Gist options
  • Star 4 You must be signed in to star a gist
  • Fork 1 You must be signed in to fork a gist
  • Save alanpeabody/7eab2d4b8bedf4172130 to your computer and use it in GitHub Desktop.
Save alanpeabody/7eab2d4b8bedf4172130 to your computer and use it in GitHub Desktop.
Ecto change password w/ confirmation.
defmodule User do
use Ecto.Model
schema "users" do
field :email, :string
field :hashed_password, :string
field :password, :string, virtual: true
field :password_confirmation, virtual: true
timestamps
end
before_save :hash_password
@required [:email, :password, :password_confirmation]
@optional []
def changeset(user, params) do
params
|> cast(user, @required, @optional)
|> validate_format(:email, ~r/@/)
|> validate_password_confirmation
end
defp validate_password_confirmation(%{changes: changes} = changeset) do
case changes[:password_confirmation] do
changes[:password] -> changeset
_ -> add_error(changeset, :password_confirmation, "must match password")
end
end
defp hash_password(changeset) do
#hash things
end
end
defmodule API.User do
import Plug.Conn
post "/" do
change = User.changeset(%User{}, params(conn))
if change.valid? do
send_resp(conn, 200, JSON.Encode(Repo.update(change)))
else
send_resp(conn, 422, JSON.Encode(change.errors))
end
end
end
@mmyoji
Copy link

mmyoji commented Jun 26, 2016

thank you for this gist!

but the code itself doesn't work, and following does!

my env is like this:

  • elixir v1.3.0
  • phoenix v1.2.0
  defp validate_password_confirmation(%{changes: changes} = changeset) do
    pwd = changes[:password]
    case changes[:password_confirmation] do
      ^pwd -> changeset
      _    -> add_error(changeset, :password_confirmation, "must match password")
    end
  end

or just use validate_confirmation

@progsmile
Copy link

Interesting part comes when before_save event is used... Sometimes we need:

  • to update profile not changing password
  • import user from somewhere with already encoded password
  • . . .
    Events are evil. And why we should validate it inside model? Are there any forms or requests that are really responsible for validation?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment