defmodule MicrowavepropWeb.ContactMapControllerTest do
  use MicrowavepropWeb.ConnCase, async: false

  alias Microwaveprop.Cache

  setup do
    # The controller caches a gzipped payload under a module-level key —
    # clear it between tests so gzip vs identity requests don't reuse
    # each other's output.
    Cache.invalidate({MicrowavepropWeb.ContactMapController, :gzipped_payload})
    :ok
  end

  describe "GET /api/contacts/map" do
    test "serves plain JSON when the client does not accept gzip", %{conn: conn} do
      conn = get(conn, ~p"/api/contacts/map")

      assert conn.status == 200
      assert get_resp_header(conn, "content-type") == ["application/json; charset=utf-8"]
      assert get_resp_header(conn, "content-encoding") == []
      assert [cache_control] = get_resp_header(conn, "cache-control")
      assert cache_control =~ "max-age=60"

      # Body must be parseable JSON; on an empty dev/test DB that's a
      # list (possibly empty) of contact tuples.
      assert {:ok, parsed} = Jason.decode(conn.resp_body)
      assert is_list(parsed)
    end

    test "emits gzip-encoded body when the client advertises gzip support", %{conn: conn} do
      conn =
        conn
        |> put_req_header("accept-encoding", "gzip, deflate")
        |> get(~p"/api/contacts/map")

      assert conn.status == 200
      assert get_resp_header(conn, "content-encoding") == ["gzip"]

      # The gzipped body decompresses to valid JSON.
      decompressed = :zlib.gunzip(conn.resp_body)
      assert {:ok, _} = Jason.decode(decompressed)
    end

    test "caches the gzipped payload across requests", %{conn: conn} do
      conn1 =
        conn
        |> put_req_header("accept-encoding", "gzip")
        |> get(~p"/api/contacts/map")

      conn2 =
        build_conn()
        |> put_req_header("accept-encoding", "gzip")
        |> get(~p"/api/contacts/map")

      # Byte-identical bodies prove the second hit came from the cache,
      # not a fresh Radio.contact_map_payload/0 + gzip round-trip.
      assert conn1.resp_body == conn2.resp_body
    end
  end
end
