270 lines
8.1 KiB
Elixir
270 lines
8.1 KiB
Elixir
defmodule AprsmeWeb.MapLive.DisplayManagerTest do
|
|
use Aprsme.DataCase, async: true
|
|
|
|
alias AprsmeWeb.MapLive.DisplayManager
|
|
|
|
setup do
|
|
# Create a basic socket mock for testing
|
|
socket = %Phoenix.LiveView.Socket{
|
|
assigns: %{
|
|
visible_packets: %{},
|
|
tracked_callsign: nil,
|
|
packet_age_threshold: nil,
|
|
map_bounds: nil,
|
|
map_zoom: 10,
|
|
historical_packets: %{}
|
|
},
|
|
private: %{live_temp: %{}}
|
|
}
|
|
|
|
{:ok, socket: socket}
|
|
end
|
|
|
|
# Helper function to assert push events
|
|
defp assert_push_event(socket, event_name, expected_data) do
|
|
push_events = get_in(socket.private, [:live_temp, :push_events]) || []
|
|
|
|
matching_event = Enum.find(push_events, fn [name, _data] -> name == event_name end)
|
|
|
|
assert matching_event != nil, "Expected to find event '#{event_name}' in push_events"
|
|
|
|
[_name, data] = matching_event
|
|
|
|
# For partial matching, check if all expected keys are present
|
|
Enum.each(expected_data, fn {key, value} ->
|
|
assert Map.get(data, key) == value,
|
|
"Expected #{key} to be #{inspect(value)}, got #{inspect(Map.get(data, key))}"
|
|
end)
|
|
|
|
socket
|
|
end
|
|
|
|
describe "handle_zoom_threshold_crossing/2" do
|
|
test "shows trail line for tracked callsign at low zoom", %{socket: socket} do
|
|
packet1 = %{
|
|
id: "1",
|
|
sender: "W5ISP-9",
|
|
lat: 30.123,
|
|
lon: -97.456,
|
|
received_at: ~U[2024-01-01 10:00:00Z]
|
|
}
|
|
|
|
visible_packets = %{"W5ISP-9:1" => packet1}
|
|
|
|
socket =
|
|
Map.put(socket, :assigns, %{
|
|
socket.assigns
|
|
| visible_packets: visible_packets,
|
|
tracked_callsign: "W5ISP-9",
|
|
packet_age_threshold: ~U[2024-01-01 09:00:00Z],
|
|
map_zoom: 8
|
|
})
|
|
|
|
# Zoom from 9 to 8 (crossing threshold) - socket already has new zoom
|
|
result_socket = DisplayManager.handle_zoom_threshold_crossing(socket, 8)
|
|
|
|
# Should clear markers and show trail line
|
|
assert_push_event(result_socket, "clear_all_markers", %{})
|
|
assert_push_event(result_socket, "show_trail_line", %{callsign: "W5ISP-9"})
|
|
end
|
|
|
|
test "shows heat map when no tracked callsign at low zoom", %{socket: socket} do
|
|
socket =
|
|
Map.put(socket, :assigns, %{
|
|
socket.assigns
|
|
| visible_packets: %{},
|
|
tracked_callsign: "",
|
|
historical_packets: %{},
|
|
map_bounds: %{north: 90, south: -90, east: 180, west: -180},
|
|
map_zoom: 8
|
|
})
|
|
|
|
# Zoom from 9 to 8 (crossing threshold) - socket already has new zoom
|
|
result_socket = DisplayManager.handle_zoom_threshold_crossing(socket, 8)
|
|
|
|
# Should clear markers and show heat map
|
|
assert_push_event(result_socket, "clear_all_markers", %{})
|
|
assert_push_event(result_socket, "show_heat_map", %{heat_points: []})
|
|
end
|
|
|
|
test "shows markers for tracked callsign at high zoom", %{socket: socket} do
|
|
packet1 = %{
|
|
id: "1",
|
|
sender: "W5ISP-9",
|
|
lat: 30.123,
|
|
lon: -97.456,
|
|
received_at: ~U[2024-01-01 10:00:00Z]
|
|
}
|
|
|
|
visible_packets = %{"W5ISP-9:1" => packet1}
|
|
|
|
socket =
|
|
Map.put(socket, :assigns, %{
|
|
socket.assigns
|
|
| visible_packets: visible_packets,
|
|
tracked_callsign: "W5ISP-9",
|
|
packet_age_threshold: ~U[2024-01-01 09:00:00Z],
|
|
map_zoom: 9
|
|
})
|
|
|
|
# Zoom from 8 to 9 (crossing threshold) - socket already has new zoom
|
|
result_socket = DisplayManager.handle_zoom_threshold_crossing(socket, 9)
|
|
|
|
# Should show markers
|
|
assert_push_event(result_socket, "show_markers", %{})
|
|
end
|
|
end
|
|
|
|
describe "send_trail_line_for_tracked_callsign/1" do
|
|
test "pushes trail line event with sorted points", %{socket: socket} do
|
|
packet1 = %{
|
|
id: "1",
|
|
sender: "W5ISP-9",
|
|
lat: 30.123,
|
|
lon: -97.456,
|
|
received_at: ~U[2024-01-01 10:00:00Z]
|
|
}
|
|
|
|
packet2 = %{
|
|
id: "2",
|
|
sender: "W5ISP-9",
|
|
lat: 30.124,
|
|
lon: -97.457,
|
|
received_at: ~U[2024-01-01 10:05:00Z]
|
|
}
|
|
|
|
packet3 = %{
|
|
id: "3",
|
|
sender: "W5ISP-9",
|
|
lat: 30.125,
|
|
lon: -97.458,
|
|
received_at: ~U[2024-01-01 10:10:00Z]
|
|
}
|
|
|
|
visible_packets = %{"W5ISP-9:1" => packet1, "W5ISP-9:2" => packet2, "W5ISP-9:3" => packet3}
|
|
|
|
socket =
|
|
Map.put(socket, :assigns, %{
|
|
socket.assigns
|
|
| visible_packets: visible_packets,
|
|
tracked_callsign: "W5ISP-9",
|
|
packet_age_threshold: ~U[2024-01-01 09:00:00Z]
|
|
})
|
|
|
|
result_socket = DisplayManager.send_trail_line_for_tracked_callsign(socket)
|
|
|
|
push_events = get_in(result_socket.private, [:live_temp, :push_events]) || []
|
|
assert length(push_events) == 1
|
|
|
|
[[event_name, event_data]] = push_events
|
|
assert event_name == "show_trail_line"
|
|
|
|
assert event_data == %{
|
|
callsign: "W5ISP-9",
|
|
points: [
|
|
%{lat: 30.123, lng: -97.456, timestamp: "2024-01-01T10:00:00Z"},
|
|
%{lat: 30.124, lng: -97.457, timestamp: "2024-01-01T10:05:00Z"},
|
|
%{lat: 30.125, lng: -97.458, timestamp: "2024-01-01T10:10:00Z"}
|
|
]
|
|
}
|
|
end
|
|
|
|
test "filters by packet age threshold", %{socket: socket} do
|
|
packet1 = %{
|
|
id: "1",
|
|
sender: "W5ISP-9",
|
|
lat: 30.123,
|
|
lon: -97.456,
|
|
received_at: ~U[2024-01-01 09:00:00Z]
|
|
}
|
|
|
|
# Too old
|
|
packet2 = %{
|
|
id: "2",
|
|
sender: "W5ISP-9",
|
|
lat: 30.124,
|
|
lon: -97.457,
|
|
received_at: ~U[2024-01-01 10:05:00Z]
|
|
}
|
|
|
|
# Within threshold
|
|
|
|
visible_packets = %{"W5ISP-9:1" => packet1, "W5ISP-9:2" => packet2}
|
|
|
|
socket =
|
|
Map.put(socket, :assigns, %{
|
|
socket.assigns
|
|
| visible_packets: visible_packets,
|
|
tracked_callsign: "W5ISP-9",
|
|
packet_age_threshold: ~U[2024-01-01 10:00:00Z]
|
|
})
|
|
|
|
result_socket = DisplayManager.send_trail_line_for_tracked_callsign(socket)
|
|
|
|
push_events = get_in(result_socket.private, [:live_temp, :push_events]) || []
|
|
assert length(push_events) == 1
|
|
|
|
[[event_name, event_data]] = push_events
|
|
assert event_name == "show_trail_line"
|
|
|
|
assert event_data == %{
|
|
callsign: "W5ISP-9",
|
|
points: [%{lat: 30.124, lng: -97.457, timestamp: "2024-01-01T10:05:00Z"}]
|
|
}
|
|
end
|
|
|
|
test "includes historical packets in tracked trail at low zoom", %{socket: socket} do
|
|
visible_packet = %{
|
|
id: "1",
|
|
sender: "W5ISP-9",
|
|
lat: 30.124,
|
|
lon: -97.457,
|
|
received_at: ~U[2024-01-01 10:05:00Z]
|
|
}
|
|
|
|
historical_packet = %{
|
|
id: "2",
|
|
sender: "W5ISP-9",
|
|
lat: 30.123,
|
|
lon: -97.456,
|
|
received_at: ~U[2024-01-01 10:00:00Z]
|
|
}
|
|
|
|
socket =
|
|
Map.put(socket, :assigns, %{
|
|
socket.assigns
|
|
| visible_packets: %{"W5ISP-9" => visible_packet},
|
|
historical_packets: %{"hist-1" => historical_packet},
|
|
tracked_callsign: "W5ISP-9",
|
|
packet_age_threshold: ~U[2024-01-01 09:00:00Z]
|
|
})
|
|
|
|
result_socket = DisplayManager.send_trail_line_for_tracked_callsign(socket)
|
|
|
|
push_events = get_in(result_socket.private, [:live_temp, :push_events]) || []
|
|
[[event_name, event_data]] = push_events
|
|
|
|
assert event_name == "show_trail_line"
|
|
|
|
assert event_data.points == [
|
|
%{lat: 30.123, lng: -97.456, timestamp: "2024-01-01T10:00:00Z"},
|
|
%{lat: 30.124, lng: -97.457, timestamp: "2024-01-01T10:05:00Z"}
|
|
]
|
|
end
|
|
|
|
test "returns socket unchanged when no packets", %{socket: socket} do
|
|
socket =
|
|
Map.put(socket, :assigns, %{
|
|
socket.assigns
|
|
| visible_packets: %{},
|
|
tracked_callsign: "W5ISP-9",
|
|
packet_age_threshold: ~U[2024-01-01 10:00:00Z]
|
|
})
|
|
|
|
result_socket = DisplayManager.send_trail_line_for_tracked_callsign(socket)
|
|
|
|
push_events = get_in(result_socket.private, [:live_temp, :push_events]) || []
|
|
assert push_events == []
|
|
end
|
|
end
|
|
end
|