defmodule ToweropsWeb.Org.PreseemInsightsLiveTest do
  use ToweropsWeb.ConnCase, async: true

  import Phoenix.LiveViewTest
  import Towerops.AccountsFixtures
  import Towerops.DevicesFixtures
  import Towerops.OrganizationsFixtures

  alias Towerops.Preseem.AccessPoint
  alias Towerops.Preseem.Insight
  alias Towerops.Repo

  setup do
    user = user_fixture()
    org = organization_fixture(user.id)
    %{user: user, organization: org}
  end

  defp insert_access_point!(org, attrs \\ %{}) do
    default = %{
      organization_id: org.id,
      preseem_id: "ap-#{System.unique_integer([:positive])}",
      name: "Test AP"
    }

    {:ok, ap} =
      %AccessPoint{}
      |> AccessPoint.changeset(Map.merge(default, attrs))
      |> Repo.insert()

    ap
  end

  defp insert_insight!(org, ap, attrs) do
    default = %{
      organization_id: org.id,
      preseem_access_point_id: ap.id,
      type: "qoe_degradation",
      urgency: "warning",
      channel: "proactive",
      title: "Test insight",
      description: "Test description"
    }

    {:ok, insight} =
      %Insight{}
      |> Insight.changeset(Map.merge(default, attrs))
      |> Repo.insert()

    insight
  end

  describe "index" do
    test "renders empty state when no insights exist", %{
      conn: conn,
      user: user,
      organization: org
    } do
      {:ok, view, html} =
        conn
        |> log_in_user(user)
        |> live(~p"/orgs/#{org.slug}/settings/integrations/preseem/insights")

      assert html =~ "Network Insights"
      assert has_element?(view, "#empty-state")
    end

    test "shows insights in list", %{conn: conn, user: user, organization: org} do
      ap = insert_access_point!(org, %{name: "Tower 1"})
      insert_insight!(org, ap, %{title: "QoE dropping on Tower 1"})

      {:ok, _view, html} =
        conn
        |> log_in_user(user)
        |> live(~p"/orgs/#{org.slug}/settings/integrations/preseem/insights")

      assert html =~ "QoE dropping on Tower 1"
    end

    test "shows urgency badges", %{conn: conn, user: user, organization: org} do
      ap = insert_access_point!(org)

      insert_insight!(org, ap, %{
        title: "Critical Issue",
        urgency: "critical"
      })

      {:ok, view, _html} =
        conn
        |> log_in_user(user)
        |> live(~p"/orgs/#{org.slug}/settings/integrations/preseem/insights")

      assert has_element?(view, "#insights-list")
      assert render(view) =~ "Critical Issue"
      assert render(view) =~ "critical"
    end

    test "shows related access point name", %{conn: conn, user: user, organization: org} do
      ap = insert_access_point!(org, %{name: "Main Tower AP"})
      insert_insight!(org, ap, %{title: "Some insight"})

      {:ok, _view, html} =
        conn
        |> log_in_user(user)
        |> live(~p"/orgs/#{org.slug}/settings/integrations/preseem/insights")

      assert html =~ "Main Tower AP"
    end

    test "links to device page when device_id exists", %{
      conn: conn,
      user: user,
      organization: org
    } do
      ap = insert_access_point!(org)
      device = device_fixture(%{organization_id: org.id, name: "My Router"})

      insert_insight!(org, ap, %{
        title: "Device issue",
        device_id: device.id
      })

      {:ok, view, _html} =
        conn
        |> log_in_user(user)
        |> live(~p"/orgs/#{org.slug}/settings/integrations/preseem/insights")

      assert has_element?(view, "a[href='/devices/#{device.id}']")
    end
  end

  describe "filtering" do
    setup %{organization: org} do
      ap = insert_access_point!(org)

      critical =
        insert_insight!(org, ap, %{
          title: "Critical Issue",
          urgency: "critical"
        })

      info =
        insert_insight!(org, ap, %{
          title: "Info Note",
          urgency: "info"
        })

      %{ap: ap, critical: critical, info: info}
    end

    test "filters by urgency via URL params", %{conn: conn, user: user, organization: org} do
      {:ok, _view, html} =
        conn
        |> log_in_user(user)
        |> live(~p"/orgs/#{org.slug}/settings/integrations/preseem/insights?urgency=critical")

      assert html =~ "Critical Issue"
      refute html =~ "Info Note"
    end

    test "filters by status", %{conn: conn, user: user, organization: org, ap: ap} do
      insert_insight!(org, ap, %{
        title: "Dismissed One",
        status: "dismissed",
        dismissed_at: DateTime.truncate(DateTime.utc_now(), :second)
      })

      {:ok, _view, html} =
        conn
        |> log_in_user(user)
        |> live(~p"/orgs/#{org.slug}/settings/integrations/preseem/insights?status=dismissed")

      assert html =~ "Dismissed One"
      refute html =~ "Critical Issue"
    end
  end

  describe "dismiss" do
    test "dismisses a single insight", %{conn: conn, user: user, organization: org} do
      ap = insert_access_point!(org)
      insight = insert_insight!(org, ap, %{title: "Dismissable"})

      {:ok, view, _html} =
        conn
        |> log_in_user(user)
        |> live(~p"/orgs/#{org.slug}/settings/integrations/preseem/insights")

      assert render(view) =~ "Dismissable"

      view
      |> element("button[phx-click=dismiss][phx-value-id='#{insight.id}']")
      |> render_click()

      html = render(view)
      assert html =~ "Insight dismissed"
      refute html =~ "Dismissable"
    end
  end

  describe "bulk actions" do
    test "select all and bulk dismiss", %{conn: conn, user: user, organization: org} do
      ap = insert_access_point!(org)
      insert_insight!(org, ap, %{title: "Bulk 1"})
      insert_insight!(org, ap, %{title: "Bulk 2"})

      {:ok, view, _html} =
        conn
        |> log_in_user(user)
        |> live(~p"/orgs/#{org.slug}/settings/integrations/preseem/insights")

      assert render(view) =~ "Bulk 1"
      assert render(view) =~ "Bulk 2"

      # Select all
      view |> element("#select-all-btn") |> render_click()

      # Bulk dismiss
      view |> element("#bulk-dismiss-btn") |> render_click()

      html = render(view)
      assert html =~ "dismissed"
      refute html =~ "Bulk 1"
      refute html =~ "Bulk 2"
    end
  end
end
