defmodule MvWeb.UserLive.FormMemberSearchTest do
  @moduledoc """
  UI tests for fuzzy search functionality in member linking.
  Tests PostgreSQL trigram-based fuzzy search behavior.
  Related to Issue #168.
  """

  use MvWeb.ConnCase, async: true

  import Phoenix.LiveViewTest

  alias Mv.Membership

  # Helper to setup authenticated connection for admin
  defp setup_admin_conn(conn) do
    conn_with_oidc_user(conn, %{email: "admin@example.com"})
  end

  describe "fuzzy search" do
    test "finds member with exact name", %{conn: conn} do
      system_actor = Mv.Helpers.SystemActor.get_system_actor()
      conn = setup_admin_conn(conn)

      {:ok, _member} =
        Membership.create_member(
          %{
            first_name: "Jonathan",
            last_name: "Smith",
            email: "jonathan.smith@example.com"
          },
          actor: system_actor
        )

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

      # Type exact name
      view
      |> element("#member-search-input")
      |> render_change(%{"member_search" => "Jonathan"})

      html = render(view)

      assert html =~ "Jonathan"
      assert html =~ "Smith"
    end

    test "finds member with typo (Jon finds Jonathan)", %{conn: conn} do
      system_actor = Mv.Helpers.SystemActor.get_system_actor()
      conn = setup_admin_conn(conn)

      {:ok, _member} =
        Membership.create_member(
          %{
            first_name: "Jonathan",
            last_name: "Smith",
            email: "jonathan.smith@example.com"
          },
          actor: system_actor
        )

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

      # Type with typo
      view
      |> element("#member-search-input")
      |> render_change(%{"member_search" => "Jon"})

      html = render(view)

      # Fuzzy search should find Jonathan
      assert html =~ "Jonathan"
      assert html =~ "Smith"
    end

    test "finds member with partial substring", %{conn: conn} do
      system_actor = Mv.Helpers.SystemActor.get_system_actor()
      conn = setup_admin_conn(conn)

      {:ok, _member} =
        Membership.create_member(
          %{
            first_name: "Alexander",
            last_name: "Williams",
            email: "alex@example.com"
          },
          actor: system_actor
        )

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

      # Type partial
      view
      |> element("#member-search-input")
      |> render_change(%{"member_search" => "lex"})

      html = render(view)

      assert html =~ "Alexander"
    end

    test "shows partial match with similar names", %{conn: conn} do
      system_actor = Mv.Helpers.SystemActor.get_system_actor()
      conn = setup_admin_conn(conn)

      {:ok, _member} =
        Membership.create_member(
          %{
            first_name: "Johnny",
            last_name: "Doeson",
            email: "johnny@example.com"
          },
          actor: system_actor
        )

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

      # Type partial match
      view
      |> element("#member-search-input")
      |> render_change(%{"member_search" => "John"})

      html = render(view)

      # Should find member with similar name
      assert html =~ "Johnny"
    end
  end
end
