Show HRRR queue position on contact detail page
When HRRR data is loading, display how many jobs are ahead in the queue so users can estimate wait time.
This commit is contained in:
parent
1c2879c466
commit
66de041886
1 changed files with 71 additions and 24 deletions
|
|
@ -2,8 +2,6 @@ defmodule MicrowavepropWeb.ContactLive.Show do
|
|||
@moduledoc false
|
||||
use MicrowavepropWeb, :live_view
|
||||
|
||||
require Logger
|
||||
|
||||
alias Microwaveprop.Propagation.BandConfig
|
||||
alias Microwaveprop.Propagation.Scorer
|
||||
alias Microwaveprop.Radio
|
||||
|
|
@ -16,6 +14,8 @@ defmodule MicrowavepropWeb.ContactLive.Show do
|
|||
alias Microwaveprop.Workers.HrrrFetchWorker
|
||||
alias Microwaveprop.Workers.TerrainProfileWorker
|
||||
|
||||
require Logger
|
||||
|
||||
@earth_radius_m 6_371_000.0
|
||||
|
||||
@impl true
|
||||
|
|
@ -32,7 +32,7 @@ defmodule MicrowavepropWeb.ContactLive.Show do
|
|||
solar = load_solar(contact)
|
||||
hrrr_path = Weather.hrrr_profiles_for_path(contact)
|
||||
hrrr = List.first(hrrr_path)
|
||||
{hrrr, contact} = maybe_enqueue_hrrr(hrrr, contact)
|
||||
{hrrr, contact, hrrr_jobs_ahead} = maybe_enqueue_hrrr(hrrr, contact)
|
||||
terrain = Terrain.get_terrain_profile(contact.id)
|
||||
contact = maybe_enqueue_terrain(terrain, contact)
|
||||
contact = maybe_enqueue_weather(weather, contact)
|
||||
|
|
@ -58,6 +58,7 @@ defmodule MicrowavepropWeb.ContactLive.Show do
|
|||
obs_sort_order: "asc",
|
||||
sounding_sort_by: "station_name",
|
||||
sounding_sort_order: "asc",
|
||||
hrrr_jobs_ahead: hrrr_jobs_ahead,
|
||||
expanded_soundings: MapSet.new()
|
||||
)}
|
||||
end
|
||||
|
|
@ -150,6 +151,7 @@ defmodule MicrowavepropWeb.ContactLive.Show do
|
|||
assign(socket,
|
||||
contact: contact,
|
||||
hrrr: hrrr,
|
||||
hrrr_jobs_ahead: 0,
|
||||
elevation_profile: elevation_profile,
|
||||
propagation_analysis: propagation_analysis
|
||||
)}
|
||||
|
|
@ -297,34 +299,75 @@ defmodule MicrowavepropWeb.ContactLive.Show do
|
|||
end
|
||||
end
|
||||
|
||||
defp maybe_enqueue_hrrr(hrrr, %{hrrr_status: :complete} = contact), do: {hrrr, contact}
|
||||
defp maybe_enqueue_hrrr(hrrr, %{hrrr_status: :complete} = contact), do: {hrrr, contact, 0}
|
||||
|
||||
defp maybe_enqueue_hrrr(hrrr, contact) when not is_nil(hrrr) do
|
||||
Radio.set_enrichment_status!([contact.id], :hrrr_status, :complete)
|
||||
{hrrr, %{contact | hrrr_status: :complete}}
|
||||
{hrrr, %{contact | hrrr_status: :complete}, 0}
|
||||
end
|
||||
|
||||
defp maybe_enqueue_hrrr(nil, contact) do
|
||||
lat = contact.pos1 && contact.pos1["lat"]
|
||||
lon = contact.pos1 && (contact.pos1["lon"] || contact.pos1["lng"])
|
||||
|
||||
if lat && lon && contact.hrrr_status in [:pending, :failed] do
|
||||
valid_time = HrrrClient.nearest_hrrr_hour(contact.qso_timestamp)
|
||||
{rlat, rlon} = Weather.round_to_hrrr_grid(lat, lon)
|
||||
cond do
|
||||
lat && lon && contact.hrrr_status in [:pending, :failed] ->
|
||||
valid_time = HrrrClient.nearest_hrrr_hour(contact.qso_timestamp)
|
||||
{rlat, rlon} = Weather.round_to_hrrr_grid(lat, lon)
|
||||
|
||||
Oban.insert(
|
||||
HrrrFetchWorker.new(%{
|
||||
"lat" => rlat,
|
||||
"lon" => rlon,
|
||||
"valid_time" => DateTime.to_iso8601(valid_time)
|
||||
})
|
||||
{:ok, job} =
|
||||
Oban.insert(
|
||||
HrrrFetchWorker.new(%{
|
||||
"lat" => rlat,
|
||||
"lon" => rlon,
|
||||
"valid_time" => DateTime.to_iso8601(valid_time)
|
||||
})
|
||||
)
|
||||
|
||||
Radio.set_enrichment_status!([contact.id], :hrrr_status, :queued)
|
||||
jobs_ahead = if job.id, do: count_hrrr_jobs_ahead(job.id), else: 0
|
||||
{nil, %{contact | hrrr_status: :queued}, jobs_ahead}
|
||||
|
||||
lat && lon && contact.hrrr_status == :queued ->
|
||||
valid_time = HrrrClient.nearest_hrrr_hour(contact.qso_timestamp)
|
||||
{rlat, rlon} = Weather.round_to_hrrr_grid(lat, lon)
|
||||
{nil, contact, count_hrrr_jobs_ahead_by_args(rlat, rlon, valid_time)}
|
||||
|
||||
true ->
|
||||
{nil, contact, 0}
|
||||
end
|
||||
end
|
||||
|
||||
defp count_hrrr_jobs_ahead(job_id) do
|
||||
import Ecto.Query
|
||||
|
||||
Microwaveprop.Repo.one(
|
||||
from(j in Oban.Job,
|
||||
where: j.queue == "hrrr",
|
||||
where: j.state in ["available", "scheduled", "retryable", "executing"],
|
||||
where: j.id < ^job_id,
|
||||
select: count(j.id)
|
||||
)
|
||||
)
|
||||
end
|
||||
|
||||
defp count_hrrr_jobs_ahead_by_args(lat, lon, valid_time) do
|
||||
import Ecto.Query
|
||||
|
||||
args = %{"lat" => lat, "lon" => lon, "valid_time" => DateTime.to_iso8601(valid_time)}
|
||||
|
||||
job_id =
|
||||
Microwaveprop.Repo.one(
|
||||
from(j in Oban.Job,
|
||||
where: j.queue == "hrrr",
|
||||
where: j.state in ["available", "scheduled", "retryable", "executing"],
|
||||
where: fragment("? @> ?", j.args, ^args),
|
||||
select: j.id,
|
||||
limit: 1
|
||||
)
|
||||
)
|
||||
|
||||
Radio.set_enrichment_status!([contact.id], :hrrr_status, :queued)
|
||||
{nil, %{contact | hrrr_status: :queued}}
|
||||
else
|
||||
{nil, contact}
|
||||
end
|
||||
if job_id, do: count_hrrr_jobs_ahead(job_id), else: 0
|
||||
end
|
||||
|
||||
defp load_solar(contact) do
|
||||
|
|
@ -548,8 +591,7 @@ defmodule MicrowavepropWeb.ContactLive.Show do
|
|||
<div class="text-sm text-base-content/50 italic">
|
||||
<%= if @contact.terrain_status == :queued do %>
|
||||
<span class="flex items-center gap-2">
|
||||
<span class="loading loading-spinner loading-sm"></span>
|
||||
Computing terrain profile...
|
||||
<span class="loading loading-spinner loading-sm"></span> Computing terrain profile...
|
||||
</span>
|
||||
<% else %>
|
||||
No terrain profile available.
|
||||
|
|
@ -722,7 +764,10 @@ defmodule MicrowavepropWeb.ContactLive.Show do
|
|||
<% :queued -> %>
|
||||
<span class="flex items-center gap-2">
|
||||
<span class="loading loading-spinner loading-sm"></span>
|
||||
Fetching HRRR atmospheric data (this will take a while)...
|
||||
Fetching HRRR atmospheric data
|
||||
<%= if @hrrr_jobs_ahead > 0 do %>
|
||||
({@hrrr_jobs_ahead} {if @hrrr_jobs_ahead == 1, do: "job", else: "jobs"} ahead in queue)
|
||||
<% end %>
|
||||
</span>
|
||||
<% :unavailable -> %>
|
||||
HRRR data unavailable for this contact time.
|
||||
|
|
@ -825,8 +870,10 @@ defmodule MicrowavepropWeb.ContactLive.Show do
|
|||
<div>{length(@surface_observations)} stations</div>
|
||||
<%= if @surface_observations != [] do %>
|
||||
<div>
|
||||
{Calendar.strftime(hd(@surface_observations).observed_at, "%H:%M")} –
|
||||
{Calendar.strftime(List.last(@surface_observations).observed_at, "%H:%M")} UTC
|
||||
{Calendar.strftime(hd(@surface_observations).observed_at, "%H:%M")} – {Calendar.strftime(
|
||||
List.last(@surface_observations).observed_at,
|
||||
"%H:%M"
|
||||
)} UTC
|
||||
</div>
|
||||
<% end %>
|
||||
</div>
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue