defmodule BerrypodWeb.Admin.NewsletterTest do use BerrypodWeb.ConnCase, async: true import Phoenix.LiveViewTest import Berrypod.AccountsFixtures import Berrypod.NewsletterFixtures alias Berrypod.Newsletter setup %{conn: conn} do user = user_fixture() conn = log_in_user(conn, user) %{conn: conn, user: user} end describe "overview tab" do test "shows newsletter toggle", %{conn: conn} do {:ok, view, _html} = live(conn, ~p"/admin/newsletter") assert has_element?(view, "[role=switch]") end test "toggles newsletter enabled", %{conn: conn} do {:ok, view, _html} = live(conn, ~p"/admin/newsletter") refute Newsletter.newsletter_enabled?() view |> element("[role=switch]") |> render_click() assert Newsletter.newsletter_enabled?() end test "shows subscriber counts", %{conn: conn} do confirmed_subscriber_fixture(email: "a@example.com") confirmed_subscriber_fixture(email: "b@example.com") {:ok, _view, html} = live(conn, ~p"/admin/newsletter") assert html =~ "2" assert html =~ "Confirmed" end end describe "subscribers tab" do test "lists subscribers", %{conn: conn} do confirmed_subscriber_fixture(email: "listed@example.com") {:ok, view, _html} = live(conn, ~p"/admin/newsletter?tab=subscribers") assert has_element?(view, "#subscribers") assert render(view) =~ "listed@example.com" end test "filters by status", %{conn: conn} do confirmed_subscriber_fixture(email: "confirmed@example.com") {:ok, view, _html} = live(conn, ~p"/admin/newsletter?tab=subscribers") # Filter to confirmed only view |> element("button", "Confirmed") |> render_click() assert render(view) =~ "confirmed@example.com" end test "searches subscribers", %{conn: conn} do confirmed_subscriber_fixture(email: "findme@example.com") confirmed_subscriber_fixture(email: "other@example.com") {:ok, view, _html} = live(conn, ~p"/admin/newsletter?tab=subscribers") view |> element("form") |> render_change(%{search: "findme"}) html = render(view) assert html =~ "findme@example.com" refute html =~ "other@example.com" end test "deletes subscriber", %{conn: conn} do confirmed_subscriber_fixture(email: "deleteme@example.com") {:ok, view, _html} = live(conn, ~p"/admin/newsletter?tab=subscribers") assert render(view) =~ "deleteme@example.com" view |> element("button", "Delete") |> render_click() refute render(view) =~ "deleteme@example.com" end end describe "campaigns tab" do test "lists campaigns", %{conn: conn} do campaign_fixture(subject: "Test campaign") {:ok, view, _html} = live(conn, ~p"/admin/newsletter?tab=campaigns") assert render(view) =~ "Test campaign" end test "deletes draft campaign", %{conn: conn} do campaign_fixture(subject: "Delete me") {:ok, view, _html} = live(conn, ~p"/admin/newsletter?tab=campaigns") assert render(view) =~ "Delete me" view |> element("button", "Delete") |> render_click() refute render(view) =~ "Delete me" end test "links to new campaign form", %{conn: conn} do {:ok, view, _html} = live(conn, ~p"/admin/newsletter?tab=campaigns") assert has_element?(view, "a[href='/admin/newsletter/campaigns/new']") end end describe "GET /admin/newsletter/export" do test "downloads CSV of subscribers", %{conn: conn} do confirmed_subscriber_fixture(email: "export@example.com") conn = get(conn, ~p"/admin/newsletter/export") assert response_content_type(conn, :csv) =~ "text/csv" assert get_resp_header(conn, "content-disposition") |> hd() =~ "attachment" assert conn.resp_body =~ "export@example.com" assert conn.resp_body =~ "email,status" end end end