defmodule MvWeb.UserLiveAuthorizationTest do
  @moduledoc """
  Tests for UI authorization on User LiveViews (Index and Show).
  """
  use MvWeb.ConnCase, async: false

  import Phoenix.LiveViewTest

  alias Mv.Fixtures

  describe "User Index - Admin" do
    @tag role: :admin
    test "sees New User, Edit and Delete buttons", %{conn: conn} do
      user = Fixtures.user_with_role_fixture("admin")

      {:ok, view, _html} = live(conn, "/users")

      assert has_element?(view, "[data-testid=user-new]")
      assert has_element?(view, "#row-#{user.id} [data-testid=user-edit]")
      assert has_element?(view, "#row-#{user.id} [data-testid=user-delete]")
    end
  end

  describe "User Index - Non-Admin is redirected" do
    @tag role: :read_only
    test "read_only is redirected when accessing /users", %{conn: conn, current_user: user} do
      assert {:error, {:redirect, %{to: to}}} = live(conn, "/users")
      assert to == "/users/#{user.id}"
    end

    @tag role: :member
    test "member is redirected when accessing /users", %{conn: conn, current_user: user} do
      assert {:error, {:redirect, %{to: to}}} = live(conn, "/users")
      assert to == "/users/#{user.id}"
    end

    @tag role: :normal_user
    test "normal_user is redirected when accessing /users", %{conn: conn, current_user: user} do
      assert {:error, {:redirect, %{to: to}}} = live(conn, "/users")
      assert to == "/users/#{user.id}"
    end
  end

  describe "User Show - own profile" do
    @tag role: :member
    test "member sees Edit button on own profile", %{conn: conn, current_user: user} do
      {:ok, view, _html} = live(conn, "/users/#{user.id}")

      assert has_element?(view, "[data-testid=user-edit]")
    end

    @tag role: :read_only
    test "read_only sees Edit button on own profile", %{conn: conn, current_user: user} do
      {:ok, view, _html} = live(conn, "/users/#{user.id}")

      assert has_element?(view, "[data-testid=user-edit]")
    end

    @tag role: :admin
    test "admin sees Edit button on user show", %{conn: conn} do
      user = Fixtures.user_with_role_fixture("read_only")

      {:ok, view, _html} = live(conn, "/users/#{user.id}")

      assert has_element?(view, "[data-testid=user-edit]")
    end
  end

  describe "User Show - other user (non-admin redirected)" do
    @tag role: :member
    test "member is redirected when accessing other user's profile", %{
      conn: conn,
      current_user: current_user
    } do
      other_user = Fixtures.user_with_role_fixture("admin")

      assert {:error, {:redirect, %{to: to}}} = live(conn, "/users/#{other_user.id}")
      assert to == "/users/#{current_user.id}"
    end
  end
end
