defmodule BerrypodWeb.Admin.SettingsTest do
  use BerrypodWeb.ConnCase, async: false

  import Phoenix.LiveViewTest
  import Berrypod.AccountsFixtures
  import Berrypod.ProductsFixtures

  alias Berrypod.Settings

  setup do
    user = user_fixture()
    %{user: user}
  end

  describe "shop status toggle" do
    setup %{conn: conn, user: user} do
      conn = log_in_user(conn, user)
      %{conn: conn}
    end

    test "shows offline status by default", %{conn: conn} do
      {:ok, _view, html} = live(conn, ~p"/admin/settings")

      assert html =~ "Offline"
      assert html =~ "coming soon"
      assert html =~ "Go live"
    end

    test "can go live", %{conn: conn} do
      {:ok, view, _html} = live(conn, ~p"/admin/settings")

      html = render_click(view, "toggle_site_live")

      assert html =~ "Shop is now live"
      assert html =~ "Live"
      assert html =~ "Take offline"
      assert Settings.site_live?()
    end

    test "can take offline after going live", %{conn: conn} do
      {:ok, _} = Settings.set_site_live(true)
      {:ok, view, _html} = live(conn, ~p"/admin/settings")

      html = render_click(view, "toggle_site_live")

      assert html =~ "Shop taken offline"
      assert html =~ "Offline"
      assert html =~ "Go live"
      refute Settings.site_live?()
    end
  end

  describe "unauthenticated" do
    test "redirects to login", %{conn: conn} do
      {:error, redirect} = live(conn, ~p"/admin/settings")
      assert {:redirect, %{to: path}} = redirect
      assert path == ~p"/users/log-in"
    end
  end

  describe "authenticated - not configured" do
    setup %{conn: conn, user: user} do
      conn = log_in_user(conn, user)
      %{conn: conn}
    end

    test "renders setup form when Stripe is not configured", %{conn: conn} do
      {:ok, _view, html} = live(conn, ~p"/admin/settings")

      assert html =~ "Settings"
      assert html =~ "Not connected"
      assert html =~ "Connect Stripe"
      assert html =~ "Stripe dashboard"
    end

    test "shows error for empty API key", %{conn: conn} do
      {:ok, view, _html} = live(conn, ~p"/admin/settings")

      html =
        view
        |> form(~s(form[phx-submit="connect_stripe"]), %{stripe: %{api_key: ""}})
        |> render_submit()

      assert html =~ "Please enter your Stripe secret key"
    end
  end

  describe "authenticated - connected (localhost)" do
    setup %{conn: conn, user: user} do
      # Pre-configure a Stripe API key
      Settings.put_secret("stripe_api_key", "sk_test_simulated_key_12345")
      conn = log_in_user(conn, user)
      %{conn: conn}
    end

    test "renders dev mode view with CLI instructions", %{conn: conn} do
      {:ok, _view, html} = live(conn, ~p"/admin/settings")

      assert html =~ "Dev mode"
      assert html =~ "sk_test_•••345"
      assert html =~ "stripe listen"
      assert html =~ "Webhook signing secret"
    end

    test "saves manual signing secret", %{conn: conn} do
      {:ok, view, _html} = live(conn, ~p"/admin/settings")

      html =
        view
        |> form(~s(form[phx-submit="save_signing_secret"]), %{
          webhook: %{signing_secret: "whsec_test_manual_456"}
        })
        |> render_submit()

      assert has_element?(view, ".admin-inline-feedback-saved")
      assert html =~ "whsec_te•••456"
    end

    test "shows error for empty signing secret", %{conn: conn} do
      {:ok, view, _html} = live(conn, ~p"/admin/settings")

      html =
        view
        |> form(~s(form[phx-submit="save_signing_secret"]), %{webhook: %{signing_secret: ""}})
        |> render_submit()

      assert html =~ "Please enter a signing secret"
    end

    test "disconnect clears configuration", %{conn: conn} do
      {:ok, view, _html} = live(conn, ~p"/admin/settings")

      html = render_click(view, "disconnect_stripe")

      assert html =~ "Stripe disconnected"
      assert html =~ "Not connected"
      assert html =~ "Connect Stripe"
      refute Settings.has_secret?("stripe_api_key")
    end
  end

  describe "products section" do
    setup %{conn: conn, user: user} do
      conn = log_in_user(conn, user)
      %{conn: conn}
    end

    test "shows connect button when no provider connected", %{conn: conn} do
      {:ok, view, html} = live(conn, ~p"/admin/settings")

      assert html =~ "Products"
      assert html =~ "Not connected"
      assert has_element?(view, ~s(a[href="/admin/providers"]), "Connect a provider")
    end

    test "shows connection info when provider connected", %{conn: conn} do
      conn_record = provider_connection_fixture(%{name: "Test Shop"})
      product_fixture(%{provider_connection: conn_record})

      {:ok, _view, html} = live(conn, ~p"/admin/settings")

      assert html =~ "Connected"
      assert html =~ "Test Shop"
      assert html =~ "Sync products"
    end
  end

  describe "from address" do
    setup %{conn: conn, user: user} do
      conn = log_in_user(conn, user)
      %{conn: conn}
    end

    test "shows from address section", %{conn: conn} do
      {:ok, _view, html} = live(conn, ~p"/admin/settings")

      assert html =~ "From address"
      assert html =~ "sender address"
    end

    test "saves from address", %{conn: conn} do
      {:ok, view, _html} = live(conn, ~p"/admin/settings")

      view
      |> form("form[phx-submit=\"save_from_address\"]", %{from_address: "shop@example.com"})
      |> render_submit()

      assert has_element?(view, ".admin-inline-feedback-saved")
      assert Settings.get_setting("email_from_address") == "shop@example.com"
    end
  end
end
