diff --git a/lib/aprsme/accounts/user.ex b/lib/aprsme/accounts/user.ex index f4cfb3b..747716f 100644 --- a/lib/aprsme/accounts/user.ex +++ b/lib/aprsme/accounts/user.ex @@ -84,19 +84,22 @@ defmodule Aprsme.Accounts.User do end defp do_hash_password(changeset, true, password) when is_binary(password) do - if changeset.valid? do - changeset - # If using Bcrypt, then further validate it is at most 72 bytes long - |> validate_length(:password, max: 72, count: :bytes) - |> put_change(:hashed_password, Bcrypt.hash_pwd_salt(password)) - |> delete_change(:password) - else - changeset - end + apply_hash(changeset.valid?, changeset, password) end defp do_hash_password(changeset, _, _), do: changeset + # Bcrypt has a 72-byte key cap, so we enforce that before hashing and + # drop the plaintext from the changeset so it can't accidentally leak. + defp apply_hash(true, changeset, password) do + changeset + |> validate_length(:password, max: 72, count: :bytes) + |> put_change(:hashed_password, Bcrypt.hash_pwd_salt(password)) + |> delete_change(:password) + end + + defp apply_hash(false, changeset, _password), do: changeset + defp maybe_validate_unique_email(changeset, opts) do validate_email? = Keyword.get(opts, :validate_email, true) do_validate_unique_email(changeset, validate_email?) @@ -200,10 +203,9 @@ defmodule Aprsme.Accounts.User do Validates the current password otherwise adds an error to the changeset. """ def validate_current_password(changeset, password) do - if valid_password?(changeset.data, password) do - changeset - else - add_error(changeset, :current_password, "is not valid") - end + check_current_password(valid_password?(changeset.data, password), changeset) end + + defp check_current_password(true, changeset), do: changeset + defp check_current_password(false, changeset), do: add_error(changeset, :current_password, "is not valid") end