defmodule Microwaveprop.Commercial.PollWorkerTest do
  use Microwaveprop.DataCase, async: false

  alias Microwaveprop.Commercial
  alias Microwaveprop.Commercial.PollWorker
  alias Microwaveprop.Commercial.Sample

  @link_attrs %{
    label: "test-poll-link",
    host: "10.0.0.1",
    community: "public",
    radio_type: "af11x",
    weather_station: "KTKI",
    enabled: true
  }

  describe "poll_and_record/2" do
    test "creates samples for enabled links when SNMP succeeds" do
      {:ok, link} = Commercial.create_link(@link_attrs)

      snmp_result = %{
        rx_power_0: -55,
        tx_power: 20,
        link_state: 1,
        link_uptime: 86_400
      }

      PollWorker.poll_and_record([link], fn _host, _community, _type -> {:ok, snmp_result} end)

      samples = Repo.all(Sample)
      assert length(samples) == 1
      assert hd(samples).rx_power_0 == -55.0
      assert hd(samples).link_id == link.id
    end

    test "skips links when SNMP fails" do
      {:ok, link} = Commercial.create_link(@link_attrs)

      PollWorker.poll_and_record(
        [link],
        fn _host, _community, _type -> {:error, :snmp_failed} end
      )

      assert Repo.all(Sample) == []
    end

    test "continues polling remaining links after one failure" do
      {:ok, link1} = Commercial.create_link(@link_attrs)
      {:ok, link2} = Commercial.create_link(%{@link_attrs | label: "test-poll-link-2", host: "10.0.0.2"})

      call_count = :counters.new(1, [:atomics])

      poll_fn = fn _host, _community, _type ->
        n = :counters.get(call_count, 1)
        :counters.add(call_count, 1, 1)

        if n == 0 do
          {:error, :snmp_failed}
        else
          {:ok, %{rx_power_0: -60, link_state: 1}}
        end
      end

      PollWorker.poll_and_record([link1, link2], poll_fn)

      assert length(Repo.all(Sample)) == 1
    end
  end
end
