2.2 KiB
Forecast Derivation Internals
internal/forecast deterministically selects and summarizes normalized
forecast data. It has no transport, filesystem, CLI, subprocess, or report
registry dependency. The report-scoped caller is fact
contracts, which owns the choice of data required by each report.
Daily Derivation
BuildDailySummary builds one summary for one local civil day. The facts
layer calls it for Daily, Today, and Tomorrow reports; it does not provide a
multi-day or arbitrary-period summary constructor. timeutil.Period supplies
the shared half-open overlap rule used while selecting source values.
ResolveDayparts turns configured local clock ranges into windows. A range
whose end is not after its start continues into the next civil day. The
available daypart and timezone settings are defined in the
configuration reference.
The summary keeps selected hourly and narrative values, the discussion,
source warnings and provenance, alert overlaps, and one summary for each
resolved daypart. Daypart summaries derive their measurements, conditions,
weather indicators, and precipitation timing from normalized forecast
periods. BuildPrecipTiming is also available to the facts layer for a
report's selected hourly periods.
Boundaries And Failures
Daily-summary construction requires a bundle with hourly forecast data, valid precipitation probabilities, and valid daypart definitions. Optional normalized products remain absent when unavailable. Invalid alerts are ignored while valid overlaps are selected for the relevant day or daypart window.
Thresholds, text classification, unit normalization, and alert selection are package implementation rules. Report identity, period selection, and the resulting derived-fact shape are owned by fact contracts; external source semantics are owned by weather-data internals.
Verification
Focused internal/forecast tests exercise daily and overnight dayparts,
summary derivation, invalid precipitation data, precipitation timing, and
alert overlap handling. internal/facts tests cover the report-scoped caller:
go test ./internal/forecast ./internal/facts