user settings updated to lv and lv tests created. all tests working
This commit is contained in:
parent
24502e2667
commit
ef7b8e0bb8
26 changed files with 389 additions and 288 deletions
|
@ -172,10 +172,10 @@ defmodule Bones73k.Accounts do
|
||||||
{:error, %Ecto.Changeset{}}
|
{:error, %Ecto.Changeset{}}
|
||||||
|
|
||||||
"""
|
"""
|
||||||
def apply_user_email(user, password, attrs) do
|
def apply_user_email(user, %{"current_password" => curr_pw} = attrs) do
|
||||||
user
|
user
|
||||||
|> User.email_changeset(attrs)
|
|> User.email_changeset(attrs)
|
||||||
|> User.validate_current_password(password)
|
|> User.validate_current_password(curr_pw)
|
||||||
|> Ecto.Changeset.apply_action(:update)
|
|> Ecto.Changeset.apply_action(:update)
|
||||||
end
|
end
|
||||||
|
|
||||||
|
@ -247,11 +247,11 @@ defmodule Bones73k.Accounts do
|
||||||
{:error, %Ecto.Changeset{}}
|
{:error, %Ecto.Changeset{}}
|
||||||
|
|
||||||
"""
|
"""
|
||||||
def update_user_password(user, password, attrs) do
|
def update_user_password(user, %{"current_password" => curr_pw} = attrs) do
|
||||||
changeset =
|
changeset =
|
||||||
user
|
user
|
||||||
|> User.password_changeset(attrs)
|
|> User.password_changeset(attrs)
|
||||||
|> User.validate_current_password(password)
|
|> User.validate_current_password(curr_pw)
|
||||||
|
|
||||||
Ecto.Multi.new()
|
Ecto.Multi.new()
|
||||||
|> Ecto.Multi.update(:user, changeset)
|
|> Ecto.Multi.update(:user, changeset)
|
||||||
|
|
|
@ -35,10 +35,6 @@ defmodule Bones73kWeb.UserAuth do
|
||||||
|> put_session(:user_token, token)
|
|> put_session(:user_token, token)
|
||||||
|> put_session(:live_socket_id, "users_sessions:#{Base.url_encode64(token)}")
|
|> put_session(:live_socket_id, "users_sessions:#{Base.url_encode64(token)}")
|
||||||
|> maybe_write_remember_me_cookie(token, params)
|
|> maybe_write_remember_me_cookie(token, params)
|
||||||
|> put_flash(
|
|
||||||
:info,
|
|
||||||
raw("Welcome back, #{user.email} — you were logged in successfuly.")
|
|
||||||
)
|
|
||||||
|> redirect(to: get_session(conn, :user_return_to) || signed_in_path(conn))
|
|> redirect(to: get_session(conn, :user_return_to) || signed_in_path(conn))
|
||||||
end
|
end
|
||||||
|
|
||||||
|
|
|
@ -1,6 +1,7 @@
|
||||||
defmodule Bones73kWeb.UserSessionController do
|
defmodule Bones73kWeb.UserSessionController do
|
||||||
use Bones73kWeb, :controller
|
use Bones73kWeb, :controller
|
||||||
|
|
||||||
|
alias Phoenix.HTML
|
||||||
alias Bones73k.Accounts
|
alias Bones73k.Accounts
|
||||||
alias Bones73k.Accounts.User
|
alias Bones73k.Accounts.User
|
||||||
alias Bones73kWeb.UserAuth
|
alias Bones73kWeb.UserAuth
|
||||||
|
@ -11,7 +12,12 @@ defmodule Bones73kWeb.UserSessionController do
|
||||||
|
|
||||||
def create(conn, %{"user" => %{"email" => email, "password" => password} = user_params}) do
|
def create(conn, %{"user" => %{"email" => email, "password" => password} = user_params}) do
|
||||||
if user = Accounts.get_user_by_email_and_password(email, password) do
|
if user = Accounts.get_user_by_email_and_password(email, password) do
|
||||||
UserAuth.log_in_user(conn, user, user_params)
|
conn
|
||||||
|
|> put_flash(
|
||||||
|
:info,
|
||||||
|
HTML.raw("Welcome back, #{user.email} — you were logged in successfuly.")
|
||||||
|
)
|
||||||
|
|> UserAuth.log_in_user(user, user_params)
|
||||||
else
|
else
|
||||||
render(conn, "new.html", error_message: "Invalid email or password")
|
render(conn, "new.html", error_message: "Invalid email or password")
|
||||||
end
|
end
|
||||||
|
|
|
@ -2,36 +2,6 @@ defmodule Bones73kWeb.UserSettingsController do
|
||||||
use Bones73kWeb, :controller
|
use Bones73kWeb, :controller
|
||||||
|
|
||||||
alias Bones73k.Accounts
|
alias Bones73k.Accounts
|
||||||
alias Bones73kWeb.UserAuth
|
|
||||||
|
|
||||||
plug(:assign_email_and_password_changesets)
|
|
||||||
|
|
||||||
def edit(conn, _params) do
|
|
||||||
render(conn, "edit.html")
|
|
||||||
end
|
|
||||||
|
|
||||||
def update_email(conn, %{"current_password" => password, "user" => user_params}) do
|
|
||||||
user = conn.assigns.current_user
|
|
||||||
|
|
||||||
case Accounts.apply_user_email(user, password, user_params) do
|
|
||||||
{:ok, applied_user} ->
|
|
||||||
Accounts.deliver_update_email_instructions(
|
|
||||||
applied_user,
|
|
||||||
user.email,
|
|
||||||
&Routes.user_settings_url(conn, :confirm_email, &1)
|
|
||||||
)
|
|
||||||
|
|
||||||
conn
|
|
||||||
|> put_flash(
|
|
||||||
:info,
|
|
||||||
"A link to confirm your email change has been sent to the new address."
|
|
||||||
)
|
|
||||||
|> redirect(to: Routes.user_settings_path(conn, :edit))
|
|
||||||
|
|
||||||
{:error, changeset} ->
|
|
||||||
render(conn, "edit.html", email_changeset: changeset)
|
|
||||||
end
|
|
||||||
end
|
|
||||||
|
|
||||||
def confirm_email(conn, %{"token" => token}) do
|
def confirm_email(conn, %{"token" => token}) do
|
||||||
case Accounts.update_user_email(conn.assigns.current_user, token) do
|
case Accounts.update_user_email(conn.assigns.current_user, token) do
|
||||||
|
@ -46,27 +16,4 @@ defmodule Bones73kWeb.UserSettingsController do
|
||||||
|> redirect(to: Routes.user_settings_path(conn, :edit))
|
|> redirect(to: Routes.user_settings_path(conn, :edit))
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
def update_password(conn, %{"current_password" => password, "user" => user_params}) do
|
|
||||||
user = conn.assigns.current_user
|
|
||||||
|
|
||||||
case Accounts.update_user_password(user, password, user_params) do
|
|
||||||
{:ok, user} ->
|
|
||||||
conn
|
|
||||||
|> put_flash(:info, "Password updated successfully.")
|
|
||||||
|> put_session(:user_return_to, Routes.user_settings_path(conn, :edit))
|
|
||||||
|> UserAuth.log_in_user(user)
|
|
||||||
|
|
||||||
{:error, changeset} ->
|
|
||||||
render(conn, "edit.html", password_changeset: changeset)
|
|
||||||
end
|
|
||||||
end
|
|
||||||
|
|
||||||
defp assign_email_and_password_changesets(conn, _opts) do
|
|
||||||
user = conn.assigns.current_user
|
|
||||||
|
|
||||||
conn
|
|
||||||
|> assign(:email_changeset, Accounts.change_user_email(user))
|
|
||||||
|> assign(:password_changeset, Accounts.change_user_password(user))
|
|
||||||
end
|
|
||||||
end
|
end
|
||||||
|
|
|
@ -4,12 +4,6 @@ defmodule Bones73kWeb.UserLive.Registration do
|
||||||
alias Bones73k.Accounts
|
alias Bones73k.Accounts
|
||||||
alias Bones73k.Accounts.User
|
alias Bones73k.Accounts.User
|
||||||
|
|
||||||
@messages [
|
|
||||||
success: "Welcome! New accout created.",
|
|
||||||
info:
|
|
||||||
"Some features may be unavailable until you confirm your email. Check your inbox for instructions."
|
|
||||||
]
|
|
||||||
|
|
||||||
@impl true
|
@impl true
|
||||||
def mount(_params, session, socket) do
|
def mount(_params, session, socket) do
|
||||||
socket
|
socket
|
||||||
|
@ -25,7 +19,11 @@ defmodule Bones73kWeb.UserLive.Registration do
|
||||||
%{
|
%{
|
||||||
user_id: nil,
|
user_id: nil,
|
||||||
user_return_to: Map.get(session, "user_return_to", "/"),
|
user_return_to: Map.get(session, "user_return_to", "/"),
|
||||||
messages: @messages
|
messages: [
|
||||||
|
success: "Welcome! Your new account has been created, and you've been logged in.",
|
||||||
|
info:
|
||||||
|
"Some features may be unavailable until you confirm your email address. Check your inbox for instructions."
|
||||||
|
]
|
||||||
}
|
}
|
||||||
end
|
end
|
||||||
|
|
||||||
|
|
|
@ -27,7 +27,7 @@ defmodule Bones73kWeb.UserLive.ResetPassword do
|
||||||
{:ok, _} ->
|
{:ok, _} ->
|
||||||
{:noreply,
|
{:noreply,
|
||||||
socket
|
socket
|
||||||
|> put_flash(:success, "Password reset successfully.")
|
|> put_flash(:info, "Password reset successfully.")
|
||||||
|> redirect(to: Routes.user_session_path(socket, :new))}
|
|> redirect(to: Routes.user_session_path(socket, :new))}
|
||||||
|
|
||||||
{:error, changeset} ->
|
{:error, changeset} ->
|
||||||
|
|
39
lib/bones73k_web/live/user/settings.ex
Normal file
39
lib/bones73k_web/live/user/settings.ex
Normal file
|
@ -0,0 +1,39 @@
|
||||||
|
defmodule Bones73kWeb.UserLive.Settings do
|
||||||
|
use Bones73kWeb, :live_view
|
||||||
|
|
||||||
|
alias Bones73k.Accounts.User
|
||||||
|
|
||||||
|
@impl true
|
||||||
|
def mount(_params, session, socket) do
|
||||||
|
socket
|
||||||
|
|> assign_defaults(session)
|
||||||
|
|> alert_email_verified?()
|
||||||
|
|> live_okreply()
|
||||||
|
end
|
||||||
|
|
||||||
|
defp alert_email_verified?(socket) do
|
||||||
|
case socket.assigns.current_user do
|
||||||
|
%{confirmed_at: nil} ->
|
||||||
|
put_flash(socket, :warning, [
|
||||||
|
"Your email hasn't been confirmed, some areas may be restricted. Shall we ",
|
||||||
|
link("resend the verification email?",
|
||||||
|
to: Routes.user_confirmation_path(socket, :new),
|
||||||
|
class: "alert-link"
|
||||||
|
)
|
||||||
|
])
|
||||||
|
|
||||||
|
_ ->
|
||||||
|
socket
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
@impl true
|
||||||
|
def handle_info({:put_flash_message, {flash_type, msg}}, socket) do
|
||||||
|
socket |> put_flash(flash_type, msg) |> live_noreply()
|
||||||
|
end
|
||||||
|
|
||||||
|
@impl true
|
||||||
|
def handle_info({:clear_flash_message, flash_type}, socket) do
|
||||||
|
socket |> clear_flash(flash_type) |> live_noreply()
|
||||||
|
end
|
||||||
|
end
|
9
lib/bones73k_web/live/user/settings.html.leex
Normal file
9
lib/bones73k_web/live/user/settings.html.leex
Normal file
|
@ -0,0 +1,9 @@
|
||||||
|
<h3 class="mb-3">
|
||||||
|
<%= icon_div @socket, "bi-sliders", [class: "icon baseline"] %>
|
||||||
|
User Settings
|
||||||
|
</h3>
|
||||||
|
|
||||||
|
<div class="row">
|
||||||
|
<%= live_component @socket, Bones73kWeb.UserLive.Settings.Email, id: "email-#{@current_user.id}", current_user: @current_user %>
|
||||||
|
<%= live_component @socket, Bones73kWeb.UserLive.Settings.Password, id: "password-#{@current_user.id}", current_user: @current_user %>
|
||||||
|
</div>
|
62
lib/bones73k_web/live/user/settings/email.ex
Normal file
62
lib/bones73k_web/live/user/settings/email.ex
Normal file
|
@ -0,0 +1,62 @@
|
||||||
|
defmodule Bones73kWeb.UserLive.Settings.Email do
|
||||||
|
use Bones73kWeb, :live_component
|
||||||
|
|
||||||
|
alias Bones73k.Accounts
|
||||||
|
alias Bones73k.Accounts.User
|
||||||
|
|
||||||
|
@impl true
|
||||||
|
def update(%{current_user: user} = assigns, socket) do
|
||||||
|
socket
|
||||||
|
|> assign(id: assigns.id)
|
||||||
|
|> assign(current_user: user)
|
||||||
|
|> assign(changeset: get_changeset(user))
|
||||||
|
|> live_okreply()
|
||||||
|
end
|
||||||
|
|
||||||
|
defp get_changeset(user, user_params \\ %{}) do
|
||||||
|
Accounts.change_user_email(user, user_params)
|
||||||
|
end
|
||||||
|
|
||||||
|
@impl true
|
||||||
|
def handle_event("validate", %{"user" => user_params}, socket) do
|
||||||
|
cs = get_changeset(socket.assigns.current_user, user_params)
|
||||||
|
{:noreply, assign(socket, changeset: %{cs | action: :update})}
|
||||||
|
end
|
||||||
|
|
||||||
|
# user_settings_path GET /users/settings/confirm_email/:token Bones73kWeb.UserSettingsController :confirm_email
|
||||||
|
|
||||||
|
@impl true
|
||||||
|
def handle_event("save", %{"user" => user_params}, socket) do
|
||||||
|
case Accounts.apply_user_email(socket.assigns.current_user, user_params) do
|
||||||
|
{:ok, applied_user} ->
|
||||||
|
Accounts.deliver_update_email_instructions(
|
||||||
|
applied_user,
|
||||||
|
socket.assigns.current_user.email,
|
||||||
|
&Routes.user_settings_url(socket, :confirm_email, &1)
|
||||||
|
)
|
||||||
|
|
||||||
|
send(self(), {:clear_flash_message, :error})
|
||||||
|
|
||||||
|
send(
|
||||||
|
self(),
|
||||||
|
{:put_flash_message,
|
||||||
|
{:info, "A link to confirm your e-mail change has been sent to the new address."}}
|
||||||
|
)
|
||||||
|
|
||||||
|
socket
|
||||||
|
|> assign(changeset: get_changeset(socket.assigns.current_user))
|
||||||
|
|> live_noreply()
|
||||||
|
|
||||||
|
{:error, cs} ->
|
||||||
|
cu = socket.assigns.current_user
|
||||||
|
cpw = user_params["current_password"]
|
||||||
|
valid_password? = User.valid_password?(cu, cpw)
|
||||||
|
msg = (valid_password? && "Could not reset email.") || "Invalid current password."
|
||||||
|
send(self(), {:put_flash_message, {:error, msg}})
|
||||||
|
|
||||||
|
socket
|
||||||
|
|> assign(changeset: cs)
|
||||||
|
|> live_noreply()
|
||||||
|
end
|
||||||
|
end
|
||||||
|
end
|
51
lib/bones73k_web/live/user/settings/email.html.leex
Normal file
51
lib/bones73k_web/live/user/settings/email.html.leex
Normal file
|
@ -0,0 +1,51 @@
|
||||||
|
<div id="<%= @id %>" class="col-sm-9 col-md-7 col-lg-5 col-xl-4 mt-1">
|
||||||
|
|
||||||
|
<h4>Change email</h4>
|
||||||
|
|
||||||
|
<%= form_for @changeset, "#", [phx_change: :validate, phx_submit: :save, phx_target: @myself], fn f -> %>
|
||||||
|
|
||||||
|
<div class="mb-3" phx-feedback-for="<%= input_id(f, :email) %>">
|
||||||
|
<%= label f, :email, class: "form-label" %>
|
||||||
|
<div class="input-group has-validation">
|
||||||
|
<span class="input-group-text">
|
||||||
|
<%= icon_div @socket, "bi-at", [class: "icon fs-5"] %>
|
||||||
|
</span>
|
||||||
|
<%= email_input f, :email,
|
||||||
|
value: input_value(f, :email),
|
||||||
|
class: input_class(f, :email, "form-control"),
|
||||||
|
placeholder: "e.g., babka@73k.us",
|
||||||
|
maxlength: User.max_email,
|
||||||
|
phx_debounce: "600",
|
||||||
|
aria_describedby: error_id(f, :email)
|
||||||
|
%>
|
||||||
|
<%= error_tag f, :email %>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
|
||||||
|
<div class="mb-3" phx-feedback-for="<%= input_id(f, :current_password) %>">
|
||||||
|
<%= label f, :current_password, class: "form-label" %>
|
||||||
|
<div class="input-group">
|
||||||
|
<span class="input-group-text">
|
||||||
|
<%= icon_div @socket, "bi-lock", [class: "icon fs-5"] %>
|
||||||
|
</span>
|
||||||
|
<%= password_input f, :current_password,
|
||||||
|
class: "form-control",
|
||||||
|
required: true,
|
||||||
|
aria_describedby: error_id(f, :current_password)
|
||||||
|
%>
|
||||||
|
<%= error_tag f, :current_password %>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="mb-3">
|
||||||
|
<%= submit "Change email",
|
||||||
|
disabled: !@changeset.valid? || input_value(f, :current_password) == "",
|
||||||
|
class: "btn btn-primary",
|
||||||
|
phx_disable_with: "Saving..."
|
||||||
|
%>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<% end %>
|
||||||
|
|
||||||
|
</div>
|
57
lib/bones73k_web/live/user/settings/password.ex
Normal file
57
lib/bones73k_web/live/user/settings/password.ex
Normal file
|
@ -0,0 +1,57 @@
|
||||||
|
defmodule Bones73kWeb.UserLive.Settings.Password do
|
||||||
|
use Bones73kWeb, :live_component
|
||||||
|
|
||||||
|
alias Bones73k.Accounts
|
||||||
|
alias Bones73k.Accounts.User
|
||||||
|
|
||||||
|
@impl true
|
||||||
|
def update(%{current_user: user} = assigns, socket) do
|
||||||
|
socket
|
||||||
|
|> assign(id: assigns.id)
|
||||||
|
|> assign(current_user: user)
|
||||||
|
|> assign(changeset: get_changeset(user))
|
||||||
|
|> assign(login_params: init_login_params(socket))
|
||||||
|
|> assign(trigger_submit: false)
|
||||||
|
|> live_okreply()
|
||||||
|
end
|
||||||
|
|
||||||
|
defp get_changeset(user, user_params \\ %{}) do
|
||||||
|
Accounts.change_user_password(user, user_params)
|
||||||
|
end
|
||||||
|
|
||||||
|
defp init_login_params(socket) do
|
||||||
|
%{
|
||||||
|
user_id: nil,
|
||||||
|
user_return_to: Routes.user_settings_path(socket, :edit),
|
||||||
|
messages: [info: "Password updated successfully."]
|
||||||
|
}
|
||||||
|
end
|
||||||
|
|
||||||
|
@impl true
|
||||||
|
def handle_event("validate", %{"user" => user_params}, socket) do
|
||||||
|
cs = get_changeset(socket.assigns.current_user, user_params)
|
||||||
|
{:noreply, assign(socket, changeset: %{cs | action: :update})}
|
||||||
|
end
|
||||||
|
|
||||||
|
@impl true
|
||||||
|
def handle_event("save", %{"user" => user_params}, socket) do
|
||||||
|
case Accounts.update_user_password(socket.assigns.current_user, user_params) do
|
||||||
|
{:ok, user} ->
|
||||||
|
socket
|
||||||
|
|> assign(login_params: %{socket.assigns.login_params | user_id: user.id})
|
||||||
|
|> assign(trigger_submit: true)
|
||||||
|
|> live_noreply()
|
||||||
|
|
||||||
|
{:error, cs} ->
|
||||||
|
cu = socket.assigns.current_user
|
||||||
|
cpw = user_params["current_password"]
|
||||||
|
valid_password? = User.valid_password?(cu, cpw)
|
||||||
|
msg = (valid_password? && "Could not change password.") || "Invalid current password."
|
||||||
|
send(self(), {:put_flash_message, {:error, msg}})
|
||||||
|
|
||||||
|
socket
|
||||||
|
|> assign(changeset: cs)
|
||||||
|
|> live_noreply()
|
||||||
|
end
|
||||||
|
end
|
||||||
|
end
|
76
lib/bones73k_web/live/user/settings/password.html.leex
Normal file
76
lib/bones73k_web/live/user/settings/password.html.leex
Normal file
|
@ -0,0 +1,76 @@
|
||||||
|
<div id="<%= @id %>" class="col-sm-9 col-md-7 col-lg-5 col-xl-4 mt-1">
|
||||||
|
|
||||||
|
<h4>Change password</h4>
|
||||||
|
|
||||||
|
<%= form_for @changeset, "#", [phx_change: :validate, phx_submit: :save, phx_target: @myself], fn f -> %>
|
||||||
|
|
||||||
|
<div class="mb-3" phx-feedback-for="<%= input_id(f, :password) %>">
|
||||||
|
<%= label f, :password, "New password", class: "form-label" %>
|
||||||
|
<div class="input-group has-validation">
|
||||||
|
<span class="input-group-text">
|
||||||
|
<%= icon_div @socket, "bi-key", [class: "icon fs-5"] %>
|
||||||
|
</span>
|
||||||
|
<%= password_input f, :password,
|
||||||
|
value: input_value(f, :password),
|
||||||
|
class: input_class(f, :password, "form-control"),
|
||||||
|
maxlength: User.max_password,
|
||||||
|
phx_debounce: "600",
|
||||||
|
aria_describedby: error_id(f, :password)
|
||||||
|
%>
|
||||||
|
<%= error_tag f, :password %>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="mb-3" phx-feedback-for="<%= input_id(f, :password_confirmation) %>">
|
||||||
|
<%= label f, :password_confirmation, "Confirm new password", class: "form-label" %>
|
||||||
|
<div class="input-group has-validation">
|
||||||
|
<span class="input-group-text">
|
||||||
|
<%= icon_div @socket, "bi-key-fill", [class: "icon fs-5"] %>
|
||||||
|
</span>
|
||||||
|
<%= password_input f, :password_confirmation,
|
||||||
|
value: input_value(f, :password_confirmation),
|
||||||
|
class: input_class(f, :password_confirmation, "form-control"),
|
||||||
|
maxlength: User.max_password,
|
||||||
|
aria_describedby: error_id(f, :password_confirmation)
|
||||||
|
%>
|
||||||
|
<%= error_tag f, :password_confirmation %>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="mb-3" phx-feedback-for="<%= input_id(f, :current_password) %>">
|
||||||
|
<%= label f, :current_password, class: "form-label" %>
|
||||||
|
<div class="input-group">
|
||||||
|
<span class="input-group-text">
|
||||||
|
<%= icon_div @socket, "bi-lock", [class: "icon fs-5"] %>
|
||||||
|
</span>
|
||||||
|
<%= password_input f, :current_password,
|
||||||
|
class: "form-control",
|
||||||
|
required: true,
|
||||||
|
aria_describedby: error_id(f, :current_password)
|
||||||
|
%>
|
||||||
|
<%= error_tag f, :current_password %>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="mb-3">
|
||||||
|
<%= submit "Change password",
|
||||||
|
disabled: !@changeset.valid? || input_value(f, :current_password) == "",
|
||||||
|
class: "btn btn-primary",
|
||||||
|
phx_disable_with: "Saving..."
|
||||||
|
%>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<% end %>
|
||||||
|
|
||||||
|
<%# hidden form for initial login after registration %>
|
||||||
|
<%= form_for :user, Routes.user_session_path(@socket, :create), [phx_trigger_action: @trigger_submit, id: "settings_pw_change_trigger"], fn f -> %>
|
||||||
|
<%= hidden_input f, :params_token, value: Phoenix.Token.encrypt(Bones73kWeb.Endpoint, "login_params", @login_params) %>
|
||||||
|
<% end %>
|
||||||
|
|
||||||
|
<%# hidden form to submit user for relogin after password change %>
|
||||||
|
<%#= form_for :user_login, Routes.user_session_path(@socket, :create), [phx_trigger_action: @trigger_submit], fn f -> %>
|
||||||
|
<%#= hidden_input f, :login_params_token, value: Phoenix.Token.encrypt(Bones73kWeb.Endpoint, "login_params", @login_params) %>
|
||||||
|
<%#= hidden_input f, :remember_me, value: false %>
|
||||||
|
<%# end %>
|
||||||
|
|
||||||
|
</div>
|
|
@ -72,13 +72,9 @@ defmodule Bones73kWeb.Router do
|
||||||
pipe_through([:browser, :require_authenticated_user])
|
pipe_through([:browser, :require_authenticated_user])
|
||||||
|
|
||||||
# # liveview user settings
|
# # liveview user settings
|
||||||
# live "/users/settings", UserLive.Settings, :edit
|
live "/users/settings", UserLive.Settings, :edit
|
||||||
|
|
||||||
# original user routes from phx.gen.auth
|
# original user routes from phx.gen.auth
|
||||||
# TODO:
|
|
||||||
get("/users/settings", UserSettingsController, :edit)
|
|
||||||
put("/users/settings/update_password", UserSettingsController, :update_password)
|
|
||||||
put("/users/settings/update_email", UserSettingsController, :update_email)
|
|
||||||
get("/users/settings/confirm_email/:token", UserSettingsController, :confirm_email)
|
get("/users/settings/confirm_email/:token", UserSettingsController, :confirm_email)
|
||||||
end
|
end
|
||||||
|
|
||||||
|
@ -86,7 +82,6 @@ defmodule Bones73kWeb.Router do
|
||||||
pipe_through([:browser])
|
pipe_through([:browser])
|
||||||
|
|
||||||
delete("/users/log_out", UserSessionController, :delete)
|
delete("/users/log_out", UserSessionController, :delete)
|
||||||
# TODO: understanding/testing force_logout?
|
|
||||||
get("/users/force_logout", UserSessionController, :force_logout)
|
get("/users/force_logout", UserSessionController, :force_logout)
|
||||||
get("/users/confirm", UserConfirmationController, :new)
|
get("/users/confirm", UserConfirmationController, :new)
|
||||||
post("/users/confirm", UserConfirmationController, :create)
|
post("/users/confirm", UserConfirmationController, :create)
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
|
|
||||||
<%# phoenix flash alerts: %>
|
<%# phoenix flash alerts: %>
|
||||||
<div class="row justify-content-center">
|
<div class="row justify-content-center">
|
||||||
<div class="col-md-11 col-lg-9 col-xl-8 ">
|
<div class="col-md-12 col-lg-10 col-xl-9 ">
|
||||||
<%= for {kind, color} <- alert_kinds() do %>
|
<%= for {kind, color} <- alert_kinds() do %>
|
||||||
<%= if flash_content = get_flash(@conn, kind) do %>
|
<%= if flash_content = get_flash(@conn, kind) do %>
|
||||||
<div class="alert alert-<%= color %> alert-dismissible fade show" role="alert">
|
<div class="alert alert-<%= color %> alert-dismissible fade show" role="alert">
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
|
|
||||||
<%# liveview flash alerts: %>
|
<%# liveview flash alerts: %>
|
||||||
<div class="row justify-content-center">
|
<div class="row justify-content-center">
|
||||||
<div class="col-md-11 col-lg-9 col-xl-8 ">
|
<div class="col-md-12 col-lg-10 col-xl-9 ">
|
||||||
<%= for {kind, color} <- alert_kinds() do %>
|
<%= for {kind, color} <- alert_kinds() do %>
|
||||||
<%= if flash_content = live_flash(@flash, kind) do %>
|
<%= if flash_content = live_flash(@flash, kind) do %>
|
||||||
<div class="alert alert-<%= color %> alert-dismissible fade show" role="alert" id="lv-alert-<%= kind %>" phx-hook="AlertRemover" data-key="<%= kind %>">
|
<div class="alert alert-<%= color %> alert-dismissible fade show" role="alert" id="lv-alert-<%= kind %>" phx-hook="AlertRemover" data-key="<%= kind %>">
|
||||||
|
|
|
@ -1,49 +0,0 @@
|
||||||
<h1>Settings</h1>
|
|
||||||
|
|
||||||
<h3>Change email</h3>
|
|
||||||
|
|
||||||
<%= form_for @email_changeset, Routes.user_settings_path(@conn, :update_email), fn f -> %>
|
|
||||||
<%= if @email_changeset.action do %>
|
|
||||||
<div class="alert alert-danger">
|
|
||||||
<p>Oops, something went wrong! Please check the errors below.</p>
|
|
||||||
</div>
|
|
||||||
<% end %>
|
|
||||||
|
|
||||||
<%= label f, :email %>
|
|
||||||
<%= email_input f, :email, required: true %>
|
|
||||||
<%= error_tag f, :email %>
|
|
||||||
|
|
||||||
<%= label f, :current_password, for: "current_password_for_email" %>
|
|
||||||
<%= password_input f, :current_password, required: true, name: "current_password", id: "current_password_for_email" %>
|
|
||||||
<%= error_tag f, :current_password %>
|
|
||||||
|
|
||||||
<div>
|
|
||||||
<%= submit "Change email" %>
|
|
||||||
</div>
|
|
||||||
<% end %>
|
|
||||||
|
|
||||||
<h3>Change password</h3>
|
|
||||||
|
|
||||||
<%= form_for @password_changeset, Routes.user_settings_path(@conn, :update_password), fn f -> %>
|
|
||||||
<%= if @password_changeset.action do %>
|
|
||||||
<div class="alert alert-danger">
|
|
||||||
<p>Oops, something went wrong! Please check the errors below.</p>
|
|
||||||
</div>
|
|
||||||
<% end %>
|
|
||||||
|
|
||||||
<%= label f, :password, "New password" %>
|
|
||||||
<%= password_input f, :password, required: true %>
|
|
||||||
<%= error_tag f, :password %>
|
|
||||||
|
|
||||||
<%= label f, :password_confirmation, "Confirm new password" %>
|
|
||||||
<%= password_input f, :password_confirmation, required: true %>
|
|
||||||
<%= error_tag f, :password_confirmation %>
|
|
||||||
|
|
||||||
<%= label f, :current_password, for: "current_password_for_password" %>
|
|
||||||
<%= password_input f, :current_password, required: true, name: "current_password", id: "current_password_for_password" %>
|
|
||||||
<%= error_tag f, :current_password %>
|
|
||||||
|
|
||||||
<div>
|
|
||||||
<%= submit "Change password" %>
|
|
||||||
</div>
|
|
||||||
<% end %>
|
|
|
@ -1,3 +0,0 @@
|
||||||
defmodule Bones73kWeb.UserSettingsView do
|
|
||||||
use Bones73kWeb, :view
|
|
||||||
end
|
|
|
@ -58,19 +58,19 @@ defmodule Bones73k.AccountsTest do
|
||||||
end
|
end
|
||||||
|
|
||||||
test "validates email and password when given" do
|
test "validates email and password when given" do
|
||||||
{:error, changeset} = Accounts.register_user(%{email: "not valid", password: "not valid"})
|
{:error, changeset} = Accounts.register_user(%{email: "not valid", password: "2shrt"})
|
||||||
|
pw_err = "should be at least #{User.min_password()} character(s)"
|
||||||
assert %{
|
assert "must be a valid email address" in errors_on(changeset).email
|
||||||
email: ["must have the @ sign and no spaces"],
|
assert pw_err in errors_on(changeset).password
|
||||||
password: ["should be at least 12 character(s)"]
|
|
||||||
} = errors_on(changeset)
|
|
||||||
end
|
end
|
||||||
|
|
||||||
test "validates maximum values for email and password for security" do
|
test "validates maximum values for email and password for security" do
|
||||||
too_long = String.duplicate("db", 100)
|
too_long = "#{String.duplicate("db", 300)}@example.com"
|
||||||
{:error, changeset} = Accounts.register_user(%{email: too_long, password: too_long})
|
{:error, changeset} = Accounts.register_user(%{email: too_long, password: too_long})
|
||||||
assert "should be at most 160 character(s)" in errors_on(changeset).email
|
em_err = "should be at most #{User.max_email()} character(s)"
|
||||||
assert "should be at most 80 character(s)" in errors_on(changeset).password
|
pw_err = "should be at most #{User.max_password()} character(s)"
|
||||||
|
assert em_err in errors_on(changeset).email
|
||||||
|
assert pw_err in errors_on(changeset).password
|
||||||
end
|
end
|
||||||
|
|
||||||
test "validates email uniqueness" do
|
test "validates email uniqueness" do
|
||||||
|
@ -92,16 +92,22 @@ defmodule Bones73k.AccountsTest do
|
||||||
assert is_nil(user.password)
|
assert is_nil(user.password)
|
||||||
assert user.role == :user
|
assert user.role == :user
|
||||||
end
|
end
|
||||||
end
|
|
||||||
|
|
||||||
describe "register_admin/1" do
|
test "registers different role :manager and sets role to :manager" do
|
||||||
test "registers users with a hashed password and sets role to :admin" do
|
|
||||||
email = unique_user_email()
|
email = unique_user_email()
|
||||||
{:ok, user} = Accounts.register_admin(%{email: email, password: valid_user_password()})
|
attrs = %{email: email, role: :manager, password: valid_user_password()}
|
||||||
|
{:ok, user} = Accounts.register_user(attrs)
|
||||||
assert user.email == email
|
assert user.email == email
|
||||||
assert is_binary(user.hashed_password)
|
assert is_binary(user.hashed_password)
|
||||||
assert is_nil(user.confirmed_at)
|
assert is_nil(user.confirmed_at)
|
||||||
assert is_nil(user.password)
|
assert is_nil(user.password)
|
||||||
|
assert user.role == :manager
|
||||||
|
end
|
||||||
|
|
||||||
|
test "registers different role :admin and sets role to :admin" do
|
||||||
|
email = unique_user_email()
|
||||||
|
attrs = %{email: email, role: :admin, password: valid_user_password()}
|
||||||
|
{:ok, user} = Accounts.register_user(attrs)
|
||||||
assert user.role == :admin
|
assert user.role == :admin
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
@ -109,7 +115,7 @@ defmodule Bones73k.AccountsTest do
|
||||||
describe "change_user_registration/2" do
|
describe "change_user_registration/2" do
|
||||||
test "returns a changeset" do
|
test "returns a changeset" do
|
||||||
assert %Ecto.Changeset{} = changeset = Accounts.change_user_registration(%User{})
|
assert %Ecto.Changeset{} = changeset = Accounts.change_user_registration(%User{})
|
||||||
assert changeset.required == [:password, :email]
|
assert changeset.required == [:password, :email, :role]
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
@ -126,45 +132,42 @@ defmodule Bones73k.AccountsTest do
|
||||||
end
|
end
|
||||||
|
|
||||||
test "requires email to change", %{user: user} do
|
test "requires email to change", %{user: user} do
|
||||||
{:error, changeset} = Accounts.apply_user_email(user, valid_user_password(), %{})
|
attrs = %{"current_password" => valid_user_password()}
|
||||||
|
{:error, changeset} = Accounts.apply_user_email(user, attrs)
|
||||||
assert %{email: ["did not change"]} = errors_on(changeset)
|
assert %{email: ["did not change"]} = errors_on(changeset)
|
||||||
end
|
end
|
||||||
|
|
||||||
test "validates email", %{user: user} do
|
test "validates email", %{user: user} do
|
||||||
{:error, changeset} =
|
attrs = %{"current_password" => valid_user_password(), "email" => "not valid"}
|
||||||
Accounts.apply_user_email(user, valid_user_password(), %{email: "not valid"})
|
{:error, changeset} = Accounts.apply_user_email(user, attrs)
|
||||||
|
assert %{email: ["must be a valid email address"]} = errors_on(changeset)
|
||||||
assert %{email: ["must have the @ sign and no spaces"]} = errors_on(changeset)
|
|
||||||
end
|
end
|
||||||
|
|
||||||
test "validates maximum value for email for security", %{user: user} do
|
test "validates maximum value for email for security", %{user: user} do
|
||||||
too_long = String.duplicate("db", 100)
|
too_long = "#{String.duplicate("db", 300)}@example.com"
|
||||||
|
attrs = %{"current_password" => valid_user_password(), "email" => too_long}
|
||||||
{:error, changeset} =
|
{:error, changeset} = Accounts.apply_user_email(user, attrs)
|
||||||
Accounts.apply_user_email(user, valid_user_password(), %{email: too_long})
|
em_err = "should be at most #{User.max_email()} character(s)"
|
||||||
|
assert em_err in errors_on(changeset).email
|
||||||
assert "should be at most 160 character(s)" in errors_on(changeset).email
|
|
||||||
end
|
end
|
||||||
|
|
||||||
test "validates email uniqueness", %{user: user} do
|
test "validates email uniqueness", %{user: user} do
|
||||||
%{email: email} = user_fixture()
|
%{email: email} = user_fixture()
|
||||||
|
attrs = %{"current_password" => valid_user_password(), "email" => email}
|
||||||
{:error, changeset} =
|
{:error, changeset} = Accounts.apply_user_email(user, attrs)
|
||||||
Accounts.apply_user_email(user, valid_user_password(), %{email: email})
|
|
||||||
|
|
||||||
assert "has already been taken" in errors_on(changeset).email
|
assert "has already been taken" in errors_on(changeset).email
|
||||||
end
|
end
|
||||||
|
|
||||||
test "validates current password", %{user: user} do
|
test "validates current password", %{user: user} do
|
||||||
{:error, changeset} =
|
attrs = %{"current_password" => "invalid", "email" => unique_user_email()}
|
||||||
Accounts.apply_user_email(user, "invalid", %{email: unique_user_email()})
|
{:error, changeset} = Accounts.apply_user_email(user, attrs)
|
||||||
|
|
||||||
assert %{current_password: ["is not valid"]} = errors_on(changeset)
|
assert %{current_password: ["is not valid"]} = errors_on(changeset)
|
||||||
end
|
end
|
||||||
|
|
||||||
test "applies the email without persisting it", %{user: user} do
|
test "applies the email without persisting it", %{user: user} do
|
||||||
email = unique_user_email()
|
email = unique_user_email()
|
||||||
{:ok, user} = Accounts.apply_user_email(user, valid_user_password(), %{email: email})
|
attrs = %{"current_password" => valid_user_password(), "email" => email}
|
||||||
|
{:ok, user} = Accounts.apply_user_email(user, attrs)
|
||||||
assert user.email == email
|
assert user.email == email
|
||||||
assert Accounts.get_user!(user.id).email != email
|
assert Accounts.get_user!(user.id).email != email
|
||||||
end
|
end
|
||||||
|
@ -245,52 +248,47 @@ defmodule Bones73k.AccountsTest do
|
||||||
end
|
end
|
||||||
|
|
||||||
test "validates password", %{user: user} do
|
test "validates password", %{user: user} do
|
||||||
{:error, changeset} =
|
attrs = %{
|
||||||
Accounts.update_user_password(user, valid_user_password(), %{
|
"current_password" => valid_user_password(),
|
||||||
password: "not valid",
|
"password" => "2shrt",
|
||||||
password_confirmation: "another"
|
"password_confirmation" => "another"
|
||||||
})
|
}
|
||||||
|
|
||||||
assert %{
|
{:error, changeset} = Accounts.update_user_password(user, attrs)
|
||||||
password: ["should be at least 12 character(s)"],
|
pw_err = "should be at least #{User.min_password()} character(s)"
|
||||||
password_confirmation: ["does not match password"]
|
conf_err = "does not match password"
|
||||||
} = errors_on(changeset)
|
assert pw_err in errors_on(changeset).password
|
||||||
|
assert conf_err in errors_on(changeset).password_confirmation
|
||||||
end
|
end
|
||||||
|
|
||||||
test "validates maximum values for password for security", %{user: user} do
|
test "validates maximum values for password for security", %{user: user} do
|
||||||
too_long = String.duplicate("db", 100)
|
attrs = %{
|
||||||
|
"current_password" => valid_user_password(),
|
||||||
|
"password" => String.duplicate("db", 100)
|
||||||
|
}
|
||||||
|
|
||||||
{:error, changeset} =
|
{:error, changeset} = Accounts.update_user_password(user, attrs)
|
||||||
Accounts.update_user_password(user, valid_user_password(), %{password: too_long})
|
pw_err = "should be at most #{User.max_password()} character(s)"
|
||||||
|
assert pw_err in errors_on(changeset).password
|
||||||
assert "should be at most 80 character(s)" in errors_on(changeset).password
|
|
||||||
end
|
end
|
||||||
|
|
||||||
test "validates current password", %{user: user} do
|
test "validates current password", %{user: user} do
|
||||||
{:error, changeset} =
|
attrs = %{"current_password" => "invalid", "password" => valid_user_password()}
|
||||||
Accounts.update_user_password(user, "invalid", %{password: valid_user_password()})
|
{:error, changeset} = Accounts.update_user_password(user, attrs)
|
||||||
|
|
||||||
assert %{current_password: ["is not valid"]} = errors_on(changeset)
|
assert %{current_password: ["is not valid"]} = errors_on(changeset)
|
||||||
end
|
end
|
||||||
|
|
||||||
test "updates the password", %{user: user} do
|
test "updates the password", %{user: user} do
|
||||||
{:ok, user} =
|
attrs = %{"current_password" => valid_user_password(), "password" => "new valid password"}
|
||||||
Accounts.update_user_password(user, valid_user_password(), %{
|
{:ok, user} = Accounts.update_user_password(user, attrs)
|
||||||
password: "new valid password"
|
|
||||||
})
|
|
||||||
|
|
||||||
assert is_nil(user.password)
|
assert is_nil(user.password)
|
||||||
assert Accounts.get_user_by_email_and_password(user.email, "new valid password")
|
assert Accounts.get_user_by_email_and_password(user.email, "new valid password")
|
||||||
end
|
end
|
||||||
|
|
||||||
test "deletes all tokens for the given user", %{user: user} do
|
test "deletes all tokens for the given user", %{user: user} do
|
||||||
_ = Accounts.generate_user_session_token(user)
|
_ = Accounts.generate_user_session_token(user)
|
||||||
|
attrs = %{"current_password" => valid_user_password(), "password" => "new valid password"}
|
||||||
{:ok, _} =
|
{:ok, _} = Accounts.update_user_password(user, attrs)
|
||||||
Accounts.update_user_password(user, valid_user_password(), %{
|
|
||||||
password: "new valid password"
|
|
||||||
})
|
|
||||||
|
|
||||||
refute Repo.get_by(UserToken, user_id: user.id)
|
refute Repo.get_by(UserToken, user_id: user.id)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
@ -456,14 +454,13 @@ defmodule Bones73k.AccountsTest do
|
||||||
test "validates password", %{user: user} do
|
test "validates password", %{user: user} do
|
||||||
{:error, changeset} =
|
{:error, changeset} =
|
||||||
Accounts.reset_user_password(user, %{
|
Accounts.reset_user_password(user, %{
|
||||||
password: "not valid",
|
password: "2shrt",
|
||||||
password_confirmation: "another"
|
password_confirmation: "another"
|
||||||
})
|
})
|
||||||
|
|
||||||
assert %{
|
pw_err = "should be at least #{User.min_password()} character(s)"
|
||||||
password: ["should be at least 12 character(s)"],
|
assert pw_err in errors_on(changeset).password
|
||||||
password_confirmation: ["does not match password"]
|
assert "does not match password" in errors_on(changeset).password_confirmation
|
||||||
} = errors_on(changeset)
|
|
||||||
end
|
end
|
||||||
|
|
||||||
test "validates maximum values for password for security", %{user: user} do
|
test "validates maximum values for password for security", %{user: user} do
|
||||||
|
|
|
@ -13,7 +13,8 @@ defmodule Bones73kWeb.UserRegistrationControllerTest do
|
||||||
end
|
end
|
||||||
|
|
||||||
test "redirects if already logged in", %{conn: conn} do
|
test "redirects if already logged in", %{conn: conn} do
|
||||||
conn = conn |> log_in_user(user_fixture()) |> get(Routes.user_registration_path(conn, :new))
|
to = Routes.user_registration_path(conn, :new)
|
||||||
|
conn = conn |> log_in_user(user_fixture()) |> get(to)
|
||||||
assert redirected_to(conn) == "/"
|
assert redirected_to(conn) == "/"
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
|
@ -15,6 +15,12 @@ defmodule Bones73kWeb.UserResetPasswordControllerTest do
|
||||||
response = html_response(conn, 200)
|
response = html_response(conn, 200)
|
||||||
assert response =~ "Forgot your password?\n </h3>"
|
assert response =~ "Forgot your password?\n </h3>"
|
||||||
end
|
end
|
||||||
|
|
||||||
|
test "redirects if already logged in", %{conn: conn} do
|
||||||
|
to = Routes.user_reset_password_path(conn, :new)
|
||||||
|
conn = conn |> log_in_user(user_fixture()) |> get(to)
|
||||||
|
assert redirected_to(conn) == "/"
|
||||||
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
describe "POST /users/reset_password" do
|
describe "POST /users/reset_password" do
|
||||||
|
|
|
@ -10,7 +10,7 @@ defmodule Bones73kWeb.UserSettingsControllerTest do
|
||||||
test "renders settings page", %{conn: conn} do
|
test "renders settings page", %{conn: conn} do
|
||||||
conn = get(conn, Routes.user_settings_path(conn, :edit))
|
conn = get(conn, Routes.user_settings_path(conn, :edit))
|
||||||
response = html_response(conn, 200)
|
response = html_response(conn, 200)
|
||||||
assert response =~ "<h1>Settings</h1>"
|
assert response =~ "User Settings\n</h3>"
|
||||||
end
|
end
|
||||||
|
|
||||||
test "redirects if user is not logged in" do
|
test "redirects if user is not logged in" do
|
||||||
|
@ -20,71 +20,6 @@ defmodule Bones73kWeb.UserSettingsControllerTest do
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
describe "PUT /users/settings/update_password" do
|
|
||||||
test "updates the user password and resets tokens", %{conn: conn, user: user} do
|
|
||||||
new_password_conn =
|
|
||||||
put(conn, Routes.user_settings_path(conn, :update_password), %{
|
|
||||||
"current_password" => valid_user_password(),
|
|
||||||
"user" => %{
|
|
||||||
"password" => "new valid password",
|
|
||||||
"password_confirmation" => "new valid password"
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
assert redirected_to(new_password_conn) == Routes.user_settings_path(conn, :edit)
|
|
||||||
assert get_session(new_password_conn, :user_token) != get_session(conn, :user_token)
|
|
||||||
assert get_flash(new_password_conn, :info) =~ "Password updated successfully"
|
|
||||||
assert Accounts.get_user_by_email_and_password(user.email, "new valid password")
|
|
||||||
end
|
|
||||||
|
|
||||||
test "does not update password on invalid data", %{conn: conn} do
|
|
||||||
old_password_conn =
|
|
||||||
put(conn, Routes.user_settings_path(conn, :update_password), %{
|
|
||||||
"current_password" => "invalid",
|
|
||||||
"user" => %{
|
|
||||||
"password" => "too short",
|
|
||||||
"password_confirmation" => "does not match"
|
|
||||||
}
|
|
||||||
})
|
|
||||||
|
|
||||||
response = html_response(old_password_conn, 200)
|
|
||||||
assert response =~ "<h1>Settings</h1>"
|
|
||||||
assert response =~ "should be at least 12 character(s)"
|
|
||||||
assert response =~ "does not match password"
|
|
||||||
assert response =~ "is not valid"
|
|
||||||
|
|
||||||
assert get_session(old_password_conn, :user_token) == get_session(conn, :user_token)
|
|
||||||
end
|
|
||||||
end
|
|
||||||
|
|
||||||
describe "PUT /users/settings/update_email" do
|
|
||||||
@tag :capture_log
|
|
||||||
test "updates the user email", %{conn: conn, user: user} do
|
|
||||||
conn =
|
|
||||||
put(conn, Routes.user_settings_path(conn, :update_email), %{
|
|
||||||
"current_password" => valid_user_password(),
|
|
||||||
"user" => %{"email" => unique_user_email()}
|
|
||||||
})
|
|
||||||
|
|
||||||
assert redirected_to(conn) == Routes.user_settings_path(conn, :edit)
|
|
||||||
assert get_flash(conn, :info) =~ "A link to confirm your email"
|
|
||||||
assert Accounts.get_user_by_email(user.email)
|
|
||||||
end
|
|
||||||
|
|
||||||
test "does not update email on invalid data", %{conn: conn} do
|
|
||||||
conn =
|
|
||||||
put(conn, Routes.user_settings_path(conn, :update_email), %{
|
|
||||||
"current_password" => "invalid",
|
|
||||||
"user" => %{"email" => "with spaces"}
|
|
||||||
})
|
|
||||||
|
|
||||||
response = html_response(conn, 200)
|
|
||||||
assert response =~ "<h1>Settings</h1>"
|
|
||||||
assert response =~ "must have the @ sign and no spaces"
|
|
||||||
assert response =~ "is not valid"
|
|
||||||
end
|
|
||||||
end
|
|
||||||
|
|
||||||
describe "GET /users/settings/confirm_email/:token" do
|
describe "GET /users/settings/confirm_email/:token" do
|
||||||
setup %{user: user} do
|
setup %{user: user} do
|
||||||
email = unique_user_email()
|
email = unique_user_email()
|
||||||
|
|
|
@ -52,9 +52,6 @@ defmodule Bones73kWeb.AdminDashboardLiveTest do
|
||||||
assert "/" = redir_path = redirected_to(conn, 302)
|
assert "/" = redir_path = redirected_to(conn, 302)
|
||||||
conn = get(recycle(conn), redir_path)
|
conn = get(recycle(conn), redir_path)
|
||||||
|
|
||||||
assert "/users/log_in" = redir_path = redirected_to(conn, 302)
|
|
||||||
conn = get(recycle(conn), redir_path)
|
|
||||||
|
|
||||||
assert html_response(conn, 200) =~
|
assert html_response(conn, 200) =~
|
||||||
"You were logged out. Please login again to continue using our application."
|
"You were logged out. Please login again to continue using our application."
|
||||||
end
|
end
|
||||||
|
|
|
@ -4,12 +4,6 @@ defmodule Bones73kWeb.PageLiveTest do
|
||||||
import Phoenix.LiveViewTest
|
import Phoenix.LiveViewTest
|
||||||
import Bones73k.AccountsFixtures
|
import Bones73k.AccountsFixtures
|
||||||
|
|
||||||
test "disconnected and connected render without authentication should redirect to login page",
|
|
||||||
%{conn: conn} do
|
|
||||||
# If we don't previously log in we will be redirected to the login page
|
|
||||||
assert {:error, {:redirect, %{to: "/users/log_in"}}} = live(conn, "/")
|
|
||||||
end
|
|
||||||
|
|
||||||
test "disconnected and connected render with authentication should redirect to index page", %{
|
test "disconnected and connected render with authentication should redirect to index page", %{
|
||||||
conn: conn
|
conn: conn
|
||||||
} do
|
} do
|
||||||
|
@ -44,9 +38,6 @@ defmodule Bones73kWeb.PageLiveTest do
|
||||||
assert "/" = redir_path = redirected_to(conn, 302)
|
assert "/" = redir_path = redirected_to(conn, 302)
|
||||||
conn = get(recycle(conn), redir_path)
|
conn = get(recycle(conn), redir_path)
|
||||||
|
|
||||||
assert "/users/log_in" = redir_path = redirected_to(conn, 302)
|
|
||||||
conn = get(recycle(conn), redir_path)
|
|
||||||
|
|
||||||
assert html_response(conn, 200) =~
|
assert html_response(conn, 200) =~
|
||||||
"You were logged out. Please login again to continue using our application."
|
"You were logged out. Please login again to continue using our application."
|
||||||
end
|
end
|
||||||
|
|
|
@ -188,16 +188,13 @@ defmodule Bones73kWeb.PropertyLiveTest do
|
||||||
assert_receive {:DOWN, ^ref, _, _, _}
|
assert_receive {:DOWN, ^ref, _, _, _}
|
||||||
refute Process.alive?(index_live.pid)
|
refute Process.alive?(index_live.pid)
|
||||||
|
|
||||||
# Assert our liveview was redirected, following first to /users/force_logout, then to "/", and then to "/users/log_in"
|
# Assert our liveview was redirected, following first to /users/force_logout, then to "/"
|
||||||
assert_redirect(index_live, "/users/force_logout")
|
assert_redirect(index_live, "/users/force_logout")
|
||||||
|
|
||||||
conn = get(conn, "/users/force_logout")
|
conn = get(conn, "/users/force_logout")
|
||||||
assert "/" = redir_path = redirected_to(conn, 302)
|
assert "/" = redir_path = redirected_to(conn, 302)
|
||||||
conn = get(recycle(conn), redir_path)
|
conn = get(recycle(conn), redir_path)
|
||||||
|
|
||||||
assert "/users/log_in" = redir_path = redirected_to(conn, 302)
|
|
||||||
conn = get(recycle(conn), redir_path)
|
|
||||||
|
|
||||||
assert html_response(conn, 200) =~
|
assert html_response(conn, 200) =~
|
||||||
"You were logged out. Please login again to continue using our application."
|
"You were logged out. Please login again to continue using our application."
|
||||||
end
|
end
|
||||||
|
@ -338,9 +335,6 @@ defmodule Bones73kWeb.PropertyLiveTest do
|
||||||
assert "/" = redir_path = redirected_to(conn, 302)
|
assert "/" = redir_path = redirected_to(conn, 302)
|
||||||
conn = get(recycle(conn), redir_path)
|
conn = get(recycle(conn), redir_path)
|
||||||
|
|
||||||
assert "/users/log_in" = redir_path = redirected_to(conn, 302)
|
|
||||||
conn = get(recycle(conn), redir_path)
|
|
||||||
|
|
||||||
assert html_response(conn, 200) =~
|
assert html_response(conn, 200) =~
|
||||||
"You were logged out. Please login again to continue using our application."
|
"You were logged out. Please login again to continue using our application."
|
||||||
end
|
end
|
||||||
|
|
|
@ -6,8 +6,7 @@ defmodule Bones73kWeb.UserLive.ResetPasswordTest do
|
||||||
|
|
||||||
alias Bones73k.Repo
|
alias Bones73k.Repo
|
||||||
alias Bones73k.Accounts
|
alias Bones73k.Accounts
|
||||||
alias Bones73k.Accounts.User
|
alias Bones73k.Accounts.{User, UserToken}
|
||||||
alias Bones73k.Accounts.UserToken
|
|
||||||
|
|
||||||
setup %{conn: conn} do
|
setup %{conn: conn} do
|
||||||
user = user_fixture()
|
user = user_fixture()
|
||||||
|
@ -46,7 +45,7 @@ defmodule Bones73kWeb.UserLive.ResetPasswordTest do
|
||||||
|
|
||||||
# Confirm redirected
|
# Confirm redirected
|
||||||
flash = assert_redirected(view, Routes.user_session_path(conn, :new))
|
flash = assert_redirected(view, Routes.user_session_path(conn, :new))
|
||||||
assert flash["success"] == "Password reset successfully."
|
assert flash["info"] == "Password reset successfully."
|
||||||
|
|
||||||
# Confirm password was updated
|
# Confirm password was updated
|
||||||
assert Accounts.get_user_by_email_and_password(user.email, new_pw)
|
assert Accounts.get_user_by_email_and_password(user.email, new_pw)
|
||||||
|
|
|
@ -54,9 +54,6 @@ defmodule Bones73kWeb.UserDashboardLiveTest do
|
||||||
assert "/" = redir_path = redirected_to(conn, 302)
|
assert "/" = redir_path = redirected_to(conn, 302)
|
||||||
conn = get(recycle(conn), redir_path)
|
conn = get(recycle(conn), redir_path)
|
||||||
|
|
||||||
assert "/users/log_in" = redir_path = redirected_to(conn, 302)
|
|
||||||
conn = get(recycle(conn), redir_path)
|
|
||||||
|
|
||||||
assert html_response(conn, 200) =~
|
assert html_response(conn, 200) =~
|
||||||
"You were logged out. Please login again to continue using our application."
|
"You were logged out. Please login again to continue using our application."
|
||||||
end
|
end
|
||||||
|
|
Loading…
Reference in a new issue