defmodule BerrypodWeb.CartControllerTest do use BerrypodWeb.ConnCase, async: false import Berrypod.AccountsFixtures alias Berrypod.ProductsFixtures setup do user_fixture() {:ok, _} = Berrypod.Settings.set_site_live(true) :ok end defp create_variant(_context) do product = ProductsFixtures.complete_product_fixture(%{title: "Test Print"}) variant = List.first(product.variants) %{product: product, variant: variant} end defp conn_with_cart(conn, variant_id, qty) do Phoenix.ConnTest.init_test_session(conn, %{"cart" => [{variant_id, qty}]}) end describe "POST /cart/add" do setup [:create_variant] test "adds item to session cart and redirects to /cart", %{conn: conn, variant: variant} do conn = post(conn, ~p"/cart/add", %{"variant_id" => variant.id, "quantity" => "1"}) assert redirected_to(conn) == "/cart" assert Phoenix.Flash.get(conn.assigns.flash, :info) == "Added to basket" cart = get_session(conn, "cart") assert [{variant_id, 1}] = cart assert variant_id == variant.id end test "increments quantity if item already in cart", %{conn: conn, variant: variant} do conn = conn |> conn_with_cart(variant.id, 2) |> post(~p"/cart/add", %{"variant_id" => variant.id, "quantity" => "3"}) cart = get_session(conn, "cart") assert [{_, 5}] = cart end test "defaults quantity to 1 for invalid values", %{conn: conn, variant: variant} do conn = post(conn, ~p"/cart/add", %{"variant_id" => variant.id, "quantity" => "abc"}) cart = get_session(conn, "cart") assert [{_, 1}] = cart end test "handles missing params gracefully", %{conn: conn} do conn = post(conn, ~p"/cart/add", %{}) assert redirected_to(conn) == "/cart" assert Phoenix.Flash.get(conn.assigns.flash, :error) == "Could not add item to basket" end end describe "POST /cart/remove" do setup [:create_variant] test "removes item from session cart", %{conn: conn, variant: variant} do conn = conn |> conn_with_cart(variant.id, 2) |> post(~p"/cart/remove", %{"variant_id" => variant.id}) assert redirected_to(conn) == "/cart" assert Phoenix.Flash.get(conn.assigns.flash, :info) == "Removed from basket" cart = get_session(conn, "cart") assert cart == [] end test "handles removing non-existent item", %{conn: conn} do conn = post(conn, ~p"/cart/remove", %{"variant_id" => Ecto.UUID.generate()}) assert redirected_to(conn) == "/cart" end end describe "POST /cart/update" do setup [:create_variant] test "updates quantity in session cart", %{conn: conn, variant: variant} do conn = conn |> conn_with_cart(variant.id, 1) |> post(~p"/cart/update", %{"variant_id" => variant.id, "quantity" => "5"}) assert redirected_to(conn) == "/cart" cart = get_session(conn, "cart") assert [{_, 5}] = cart end test "removes item when quantity is 0 or less", %{conn: conn, variant: variant} do conn = conn |> conn_with_cart(variant.id, 3) |> post(~p"/cart/update", %{"variant_id" => variant.id, "quantity" => "0"}) cart = get_session(conn, "cart") assert cart == [] end end describe "POST /cart/country" do test "saves country to session and redirects to /cart", %{conn: conn} do conn = post(conn, ~p"/cart/country", %{"country" => "DE"}) assert redirected_to(conn) == "/cart" assert get_session(conn, "country_code") == "DE" end test "handles missing country param", %{conn: conn} do conn = post(conn, ~p"/cart/country", %{}) assert redirected_to(conn) == "/cart" end end end