fix: harden mobile channel numeric params
This commit is contained in:
parent
35962c195b
commit
d234c313ca
4 changed files with 51 additions and 8 deletions
|
|
@ -258,7 +258,10 @@ defmodule Aprsme.Packets.PreparedQueries do
|
||||||
|
|
||||||
# Convert miles to meters for PostGIS (1 mile = 1609.34 meters)
|
# Convert miles to meters for PostGIS (1 mile = 1609.34 meters)
|
||||||
radius_meters = radius_miles * 1609.34
|
radius_meters = radius_miles * 1609.34
|
||||||
cutoff_time = DateTime.add(DateTime.utc_now(), -hours * 3600, :second)
|
cutoff_time =
|
||||||
|
DateTime.utc_now()
|
||||||
|
|> DateTime.truncate(:second)
|
||||||
|
|> DateTime.add(-hours * 3600, :second)
|
||||||
|
|
||||||
# Build point for spatial query
|
# Build point for spatial query
|
||||||
point = %Geo.Point{coordinates: {lon, lat}, srid: 4326}
|
point = %Geo.Point{coordinates: {lon, lat}, srid: 4326}
|
||||||
|
|
|
||||||
|
|
@ -163,7 +163,7 @@ defmodule AprsmeWeb.MobileChannel do
|
||||||
# Trim whitespace and control characters from query
|
# Trim whitespace and control characters from query
|
||||||
query = String.trim(query)
|
query = String.trim(query)
|
||||||
|
|
||||||
limit = Map.get(payload, "limit", 50)
|
limit = payload |> Map.get("limit", 50) |> ensure_integer(50)
|
||||||
limit = min(limit, 500)
|
limit = min(limit, 500)
|
||||||
|
|
||||||
results = search_callsign(query, limit)
|
results = search_callsign(query, limit)
|
||||||
|
|
@ -175,7 +175,7 @@ defmodule AprsmeWeb.MobileChannel do
|
||||||
def handle_in("subscribe_callsign", %{"callsign" => callsign} = payload, socket) do
|
def handle_in("subscribe_callsign", %{"callsign" => callsign} = payload, socket) do
|
||||||
Logger.info("Mobile websocket received subscribe_callsign: #{inspect(payload)}")
|
Logger.info("Mobile websocket received subscribe_callsign: #{inspect(payload)}")
|
||||||
|
|
||||||
hours_back = Map.get(payload, "hours_back", 24)
|
hours_back = payload |> Map.get("hours_back", 24) |> ensure_integer(24)
|
||||||
# Max 1 week
|
# Max 1 week
|
||||||
hours_back = min(hours_back, 168)
|
hours_back = min(hours_back, 168)
|
||||||
|
|
||||||
|
|
@ -278,6 +278,17 @@ defmodule AprsmeWeb.MobileChannel do
|
||||||
defp ensure_float(value) when is_binary(value), do: String.to_float(value)
|
defp ensure_float(value) when is_binary(value), do: String.to_float(value)
|
||||||
defp ensure_float(value), do: value
|
defp ensure_float(value), do: value
|
||||||
|
|
||||||
|
defp ensure_integer(value, _default) when is_integer(value), do: value
|
||||||
|
|
||||||
|
defp ensure_integer(value, default) when is_binary(value) do
|
||||||
|
case Integer.parse(String.trim(value)) do
|
||||||
|
{int, _} -> int
|
||||||
|
:error -> default
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
defp ensure_integer(_value, default), do: default
|
||||||
|
|
||||||
defp build_mobile_packet(packet) do
|
defp build_mobile_packet(packet) do
|
||||||
# Extract coordinates
|
# Extract coordinates
|
||||||
{lat, lon, _data_extended} = CoordinateUtils.get_coordinates(packet)
|
{lat, lon, _data_extended} = CoordinateUtils.get_coordinates(packet)
|
||||||
|
|
@ -335,8 +346,8 @@ defmodule AprsmeWeb.MobileChannel do
|
||||||
|
|
||||||
defp load_historical_packets(socket, bounds, payload) do
|
defp load_historical_packets(socket, bounds, payload) do
|
||||||
# Get optional parameters from payload
|
# Get optional parameters from payload
|
||||||
limit = Map.get(payload, "limit", 1000)
|
limit = payload |> Map.get("limit", 1000) |> ensure_integer(1000)
|
||||||
hours_back = Map.get(payload, "hours_back", 1)
|
hours_back = payload |> Map.get("hours_back", 1) |> ensure_integer(1)
|
||||||
|
|
||||||
# Ensure reasonable limits
|
# Ensure reasonable limits
|
||||||
limit = min(limit, 5000)
|
limit = min(limit, 5000)
|
||||||
|
|
|
||||||
|
|
@ -145,12 +145,12 @@ defmodule Aprsme.StreamingPacketsPubSubTest do
|
||||||
pid = Process.whereis(StreamingPacketsPubSub)
|
pid = Process.whereis(StreamingPacketsPubSub)
|
||||||
|
|
||||||
if pid do
|
if pid do
|
||||||
GenServer.stop(pid)
|
:erlang.unregister(StreamingPacketsPubSub)
|
||||||
end
|
end
|
||||||
|
|
||||||
on_exit(fn ->
|
on_exit(fn ->
|
||||||
if !Process.whereis(StreamingPacketsPubSub) do
|
if pid && !Process.whereis(StreamingPacketsPubSub) do
|
||||||
start_supervised!({StreamingPacketsPubSub, []})
|
true = Process.register(pid, StreamingPacketsPubSub)
|
||||||
end
|
end
|
||||||
end)
|
end)
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -261,6 +261,13 @@ defmodule AprsmeWeb.MobileChannelTest do
|
||||||
assert is_list(results)
|
assert is_list(results)
|
||||||
end
|
end
|
||||||
|
|
||||||
|
test "accepts string limit values", %{socket: socket} do
|
||||||
|
ref = push(socket, "search_callsign", %{"query" => "W5ISP", "limit" => "1"})
|
||||||
|
|
||||||
|
assert_reply ref, :ok, %{count: count}
|
||||||
|
assert count <= 1
|
||||||
|
end
|
||||||
|
|
||||||
test "normalizes callsign to uppercase", %{socket: socket} do
|
test "normalizes callsign to uppercase", %{socket: socket} do
|
||||||
ref = push(socket, "search_callsign", %{"query" => "w5isp"})
|
ref = push(socket, "search_callsign", %{"query" => "w5isp"})
|
||||||
|
|
||||||
|
|
@ -291,6 +298,12 @@ defmodule AprsmeWeb.MobileChannelTest do
|
||||||
# Should not crash even with hours_back > 168
|
# Should not crash even with hours_back > 168
|
||||||
end
|
end
|
||||||
|
|
||||||
|
test "accepts string hours_back values", %{socket: socket} do
|
||||||
|
ref = push(socket, "subscribe_callsign", %{"callsign" => "W5ISP-9", "hours_back" => "24"})
|
||||||
|
|
||||||
|
assert_reply ref, :ok, %{callsign: "W5ISP-9"}
|
||||||
|
end
|
||||||
|
|
||||||
test "normalizes callsign to uppercase", %{socket: socket} do
|
test "normalizes callsign to uppercase", %{socket: socket} do
|
||||||
ref = push(socket, "subscribe_callsign", %{"callsign" => "w5isp-9"})
|
ref = push(socket, "subscribe_callsign", %{"callsign" => "w5isp-9"})
|
||||||
|
|
||||||
|
|
@ -499,4 +512,20 @@ defmodule AprsmeWeb.MobileChannelTest do
|
||||||
refute Map.has_key?(pushed_packet, :path)
|
refute Map.has_key?(pushed_packet, :path)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
|
||||||
|
describe "subscribe_bounds with historical options" do
|
||||||
|
test "accepts string limit and hours_back values", %{socket: socket} do
|
||||||
|
ref =
|
||||||
|
push(socket, "subscribe_bounds", %{
|
||||||
|
"north" => 33.2,
|
||||||
|
"south" => 33.0,
|
||||||
|
"east" => -96.0,
|
||||||
|
"west" => -96.2,
|
||||||
|
"limit" => "10",
|
||||||
|
"hours_back" => "2"
|
||||||
|
})
|
||||||
|
|
||||||
|
assert_reply ref, :ok, %{message: "Subscribed to packet stream"}
|
||||||
|
end
|
||||||
|
end
|
||||||
end
|
end
|
||||||
|
|
|
||||||
Loading…
Add table
Reference in a new issue