Adds spans to 15 previously-unmeasured hot paths so every question we might ask while tuning has a histogram to answer it: External I/O: - iem.fetch_iemre (gridded weather reanalysis) - mrms.list_latest / mrms.download (precip radar) - rtma.fetch_observation - ncei.fetch_metar (historical 5-min METAR backfill) - solar.fetch_indices (GFZ solar indices) - swpc.fetch (SWPC Kp/F10.7/X-ray) - giro.fetch (ionosonde) - qrz.request, geocoder.geocode (callsign enrichment) - srtm.download_tile (terrain tile download + gunzip) - hrrr.download_grib_ranges (parallel byte-range fetch phase) Subprocess: - wgrib2.extract_grid / extract_grid_from_file / extract_grid_from_file_mapped LiveView hot paths: - propagation.scores_at (map score fetch + cache hit/miss counter) - propagation.point_forecast (sparkline) - propagation.point_detail (click-to-inspect) - propagation.daily_outlook_at (/map outlook strip) Worker-level end-to-end: - worker.terrain_profile - worker.mechanism_classify - worker.mrms_fetch Each event is registered in Microwaveprop.PromEx.InstrumentPlugin as a Prometheus histogram (default / long buckets as appropriate) plus a counter for the scores_at cache hit/miss ratio. Prometheus at 10.0.15.25 will start seeing the new series on the next scrape after deploy.
43 lines
1.4 KiB
Elixir
43 lines
1.4 KiB
Elixir
defmodule Microwaveprop.Workers.MrmsFetchWorker do
|
|
@moduledoc """
|
|
Every ~2 minutes, pull the newest NOAA MRMS PrecipRate grid and cache
|
|
the regridded version (0.125° CONUS) in `Microwaveprop.Weather.MrmsCache`.
|
|
`Microwaveprop.Workers.AsosAdjustmentWorker` reads that cache on its
|
|
own tick to overlay real radar rain rates onto the score grid.
|
|
|
|
Runs on the `propagation` queue so it shares the scoring node's crontab
|
|
and isn't competing with the heavier HRRR pipeline for slots.
|
|
"""
|
|
use Oban.Worker, queue: :propagation, max_attempts: 2
|
|
|
|
alias Microwaveprop.Weather.MrmsCache
|
|
alias Microwaveprop.Weather.MrmsClient
|
|
|
|
require Logger
|
|
|
|
@impl Oban.Worker
|
|
def perform(%Oban.Job{}) do
|
|
Microwaveprop.Instrument.span([:worker, :mrms_fetch], %{}, fn ->
|
|
case MrmsClient.fetch_latest(MrmsCache.valid_time()) do
|
|
{:ok, valid_time, grid} ->
|
|
MrmsCache.broadcast_put(valid_time, grid)
|
|
|
|
Logger.info("MrmsFetch: cached #{map_size(grid)} cells at #{valid_time} (#{count_rainy(grid)} with rain)")
|
|
|
|
:ok
|
|
|
|
{:up_to_date, valid_time} ->
|
|
Logger.debug("MrmsFetch: cache already has #{valid_time}")
|
|
:ok
|
|
|
|
{:error, reason} ->
|
|
Logger.warning("MrmsFetch: skipped — #{inspect(reason)}")
|
|
:ok
|
|
end
|
|
end)
|
|
end
|
|
|
|
defp count_rainy(grid) do
|
|
Enum.count(grid, fn {_, v} -> v > 0 end)
|
|
end
|
|
end
|