ambient-local-exporter/pkg/weather/metrics.go
Ryan D McGuire 19823ea08f
All checks were successful
Build and Publish / release (push) Successful in 3m51s
Weather service proxy support
2025-01-12 17:23:32 -05:00

166 lines
9.2 KiB
Go

package weather
import (
"context"
"gitea.libretechconsulting.com/rmcguire/go-app/pkg/config"
"gitea.libretechconsulting.com/rmcguire/go-app/pkg/otel"
"github.com/rs/zerolog"
"go.opentelemetry.io/otel/attribute"
"go.opentelemetry.io/otel/metric"
semconv "go.opentelemetry.io/otel/semconv/v1.26.0"
)
type WeatherMetrics struct {
// Weather Metrics
TempOutdoorF metric.Float64Gauge
TempIndoorF metric.Float64Gauge
HumidityOudoor metric.Int64Gauge
HumidityIndoor metric.Int64Gauge
WindSpeedMPH metric.Float64Gauge
WindGustMPH metric.Float64Gauge
MaxDailyGust metric.Float64Gauge
WindDir metric.Int64Gauge
WindDirAvg10m metric.Int64Gauge
UV metric.Int64Gauge
SolarRadiation metric.Float64Gauge
HourlyRainIn metric.Float64Gauge
EventRainIn metric.Float64Gauge
DailyRainIn metric.Float64Gauge
WeeklyRainIn metric.Float64Gauge
MonthlyRainIn metric.Float64Gauge
YearlyRainIn metric.Float64Gauge
TotalRainIn metric.Float64Gauge
BatteryStatus metric.Int64Gauge
BaromRelativeIn metric.Float64Gauge
BaromAbsoluteIn metric.Float64Gauge
DewPointF metric.Float64Gauge
WindChillF metric.Float64Gauge
// Internal Telemetry
UpdatesReceived metric.Int64Counter
appCtx context.Context
cfg *config.AppConfig
meter metric.Meter
recorder *MetricRecorder
}
var MetricPrefix = "weather"
func MustInitMetrics(appCtx context.Context) *WeatherMetrics {
wm := &WeatherMetrics{
appCtx: appCtx,
cfg: config.MustFromCtx(appCtx),
recorder: &MetricRecorder{ctx: appCtx, l: zerolog.Ctx(appCtx)},
}
wm.meter = otel.GetMeter(appCtx, "weather", "metrics")
// Weather Metrics
wm.TempOutdoorF, _ = wm.meter.Float64Gauge(MetricPrefix+"_temp_outdoor_f",
metric.WithDescription("Outdoor Temperature in Faherenheit"))
wm.TempIndoorF, _ = wm.meter.Float64Gauge(MetricPrefix+"_temp_indoor_f",
metric.WithDescription("Indoor Temperature in Faherenheit"))
wm.HumidityOudoor, _ = wm.meter.Int64Gauge(MetricPrefix+"_humidity_outdoor",
metric.WithDescription("Outdoor Humidity %"))
wm.HumidityIndoor, _ = wm.meter.Int64Gauge(MetricPrefix+"_humidity_indoor",
metric.WithDescription("Indoor Humidity %"))
wm.WindSpeedMPH, _ = wm.meter.Float64Gauge(MetricPrefix+"_wind_speed_mph",
metric.WithDescription("Wind Speed in MPH"))
wm.WindGustMPH, _ = wm.meter.Float64Gauge(MetricPrefix+"_wind_gust_mph",
metric.WithDescription("Wind Gust in MPH"))
wm.MaxDailyGust, _ = wm.meter.Float64Gauge(MetricPrefix+"_max_daily_gust",
metric.WithDescription("Max Daily Wind Gust"))
wm.WindDir, _ = wm.meter.Int64Gauge(MetricPrefix+"_wind_dir",
metric.WithDescription("Wind Direction in Degrees"))
wm.WindDirAvg10m, _ = wm.meter.Int64Gauge(MetricPrefix+"_wind_dir_avg_10m",
metric.WithDescription("Wind Direction 10m Average"))
wm.UV, _ = wm.meter.Int64Gauge(MetricPrefix+"_uv",
metric.WithDescription("UV Index"))
wm.SolarRadiation, _ = wm.meter.Float64Gauge(MetricPrefix+"_solar_radiation",
metric.WithDescription("Solar Radiation in W/㎡"))
wm.HourlyRainIn, _ = wm.meter.Float64Gauge(MetricPrefix+"_hourly_rain_in",
metric.WithDescription("Hourly Rain in Inches"))
wm.EventRainIn, _ = wm.meter.Float64Gauge(MetricPrefix+"_event_rain_in",
metric.WithDescription("Event Rain in Inches"))
wm.DailyRainIn, _ = wm.meter.Float64Gauge(MetricPrefix+"_daily_rain_in",
metric.WithDescription("Daily Rain in Inches"))
wm.WeeklyRainIn, _ = wm.meter.Float64Gauge(MetricPrefix+"_weekly_rain_in",
metric.WithDescription("Weekly Rain in Inches"))
wm.MonthlyRainIn, _ = wm.meter.Float64Gauge(MetricPrefix+"_monthly_rain_in",
metric.WithDescription("Monthly Rain in Inches"))
wm.YearlyRainIn, _ = wm.meter.Float64Gauge(MetricPrefix+"_yearly_rain_in",
metric.WithDescription("Yearly Rain in Inches"))
wm.TotalRainIn, _ = wm.meter.Float64Gauge(MetricPrefix+"_total_rain_in",
metric.WithDescription("Total Rain in Inches"))
wm.BatteryStatus, _ = wm.meter.Int64Gauge(MetricPrefix+"_battery_status",
metric.WithDescription("Per-component battery status"))
wm.BaromRelativeIn, _ = wm.meter.Float64Gauge(MetricPrefix+"_barometric_pressure_relative_in",
metric.WithDescription("Relative Pressure in Inches of Mercury"))
wm.BaromAbsoluteIn, _ = wm.meter.Float64Gauge(MetricPrefix+"_barometric_pressure_absolute_in",
metric.WithDescription("Absolute Pressure in Inches of Mercury"))
wm.DewPointF, _ = wm.meter.Float64Gauge(MetricPrefix+"_dew_point_f",
metric.WithDescription("Dew Point in Faherenheit"))
wm.WindChillF, _ = wm.meter.Float64Gauge(MetricPrefix+"_wind_chill_f",
metric.WithDescription("Wind Chill in Faherenheit"))
// Internal Telemetry
wm.UpdatesReceived, _ = wm.meter.Int64Counter(MetricPrefix+"_updates_received",
metric.WithDescription("Metric Updates Processed by Exporter"))
return wm
}
func (wm *WeatherMetrics) Update(u *WeatherUpdate) {
attributes := []attribute.KeyValue{
semconv.ServiceVersion(wm.cfg.Version),
}
if u.StationType != nil {
attributes = append(attributes,
attribute.String("station_type", *u.StationType))
}
if u.StationConfig != nil {
if u.StationConfig.Name != "" {
attributes = append(attributes,
attribute.String("station_name", u.StationConfig.Name))
}
if u.StationConfig.Equipment != "" {
attributes = append(attributes,
attribute.String("station_equipment", u.StationConfig.Equipment))
}
}
wm.recorder.Record(&RecordOpts{Float64Gauge: wm.TempOutdoorF, FloatVal: u.TempOutdoorF, Field: FieldTempOutdoorF, Attributes: attributes, Station: u.StationConfig})
wm.recorder.Record(&RecordOpts{Float64Gauge: wm.TempIndoorF, FloatVal: u.TempIndoorF, Field: FieldTempIndoorF, Attributes: attributes, Station: u.StationConfig})
wm.recorder.Record(&RecordOpts{Int64Gauge: wm.HumidityOudoor, IntVal: u.HumidityOudoor, Field: FieldHumidityOudoor, Attributes: attributes, Station: u.StationConfig})
wm.recorder.Record(&RecordOpts{Int64Gauge: wm.HumidityIndoor, IntVal: u.HumidityIndoor, Field: FieldHumidityIndoor, Attributes: attributes, Station: u.StationConfig})
wm.recorder.Record(&RecordOpts{Float64Gauge: wm.WindSpeedMPH, FloatVal: u.WindSpeedMPH, Field: FieldWindSpeedMPH, Attributes: attributes, Station: u.StationConfig})
wm.recorder.Record(&RecordOpts{Float64Gauge: wm.WindGustMPH, FloatVal: u.WindGustMPH, Field: FieldWindGustMPH, Attributes: attributes, Station: u.StationConfig})
wm.recorder.Record(&RecordOpts{Float64Gauge: wm.MaxDailyGust, FloatVal: u.MaxDailyGust, Field: FieldMaxDailyGust, Attributes: attributes, Station: u.StationConfig})
wm.recorder.Record(&RecordOpts{Int64Gauge: wm.WindDir, IntVal: u.WindDir, Field: FieldWindDir, Attributes: attributes, Station: u.StationConfig})
wm.recorder.Record(&RecordOpts{Int64Gauge: wm.WindDirAvg10m, IntVal: u.WindDirAvg10m, Field: FieldWindDirAvg10m, Attributes: attributes, Station: u.StationConfig})
wm.recorder.Record(&RecordOpts{Int64Gauge: wm.UV, IntVal: u.UV, Field: FieldUV, Attributes: attributes, Station: u.StationConfig})
wm.recorder.Record(&RecordOpts{Float64Gauge: wm.SolarRadiation, FloatVal: u.SolarRadiation, Field: FieldSolarRadiation, Attributes: attributes, Station: u.StationConfig})
wm.recorder.Record(&RecordOpts{Float64Gauge: wm.HourlyRainIn, FloatVal: u.HourlyRainIn, Field: FieldHourlyRainIn, Attributes: attributes, Station: u.StationConfig})
wm.recorder.Record(&RecordOpts{Float64Gauge: wm.EventRainIn, FloatVal: u.EventRainIn, Field: FieldEventRainIn, Attributes: attributes, Station: u.StationConfig})
wm.recorder.Record(&RecordOpts{Float64Gauge: wm.DailyRainIn, FloatVal: u.DailyRainIn, Field: FieldDailyRainIn, Attributes: attributes, Station: u.StationConfig})
wm.recorder.Record(&RecordOpts{Float64Gauge: wm.WeeklyRainIn, FloatVal: u.WeeklyRainIn, Field: FieldWeeklyRainIn, Attributes: attributes, Station: u.StationConfig})
wm.recorder.Record(&RecordOpts{Float64Gauge: wm.MonthlyRainIn, FloatVal: u.MonthlyRainIn, Field: FieldMonthlyRainIn, Attributes: attributes, Station: u.StationConfig})
wm.recorder.Record(&RecordOpts{Float64Gauge: wm.YearlyRainIn, FloatVal: u.YearlyRainIn, Field: FieldYearlyRainIn, Attributes: attributes, Station: u.StationConfig})
wm.recorder.Record(&RecordOpts{Float64Gauge: wm.TotalRainIn, FloatVal: u.TotalRainIn, Field: FieldTotalRainIn, Attributes: attributes, Station: u.StationConfig})
wm.recorder.Record(&RecordOpts{Float64Gauge: wm.BaromRelativeIn, FloatVal: u.BaromRelativeIn, Field: FieldBaromRelativeIn, Attributes: attributes, Station: u.StationConfig})
wm.recorder.Record(&RecordOpts{Float64Gauge: wm.BaromAbsoluteIn, FloatVal: u.BaromAbsoluteIn, Field: FieldBaromAbsoluteIn, Attributes: attributes, Station: u.StationConfig})
wm.recorder.Record(&RecordOpts{Float64Gauge: wm.DewPointF, FloatVal: u.DewPointF, Field: FieldDewPointF, Attributes: attributes, Station: u.StationConfig})
wm.recorder.Record(&RecordOpts{Float64Gauge: wm.WindChillF, FloatVal: u.WindChillF, Field: FieldWindChillF, Attributes: attributes, Station: u.StationConfig})
// Batteries
for _, battery := range u.Batteries {
batAttr := attributes
batAttr = append(batAttr, attribute.String("component", battery.Component))
wm.recorder.Record(&RecordOpts{Int64Gauge: wm.BatteryStatus, IntVal: battery.Status, Field: FieldBatteries, Attributes: batAttr, Station: u.StationConfig})
}
wm.UpdatesReceived.Add(wm.appCtx, 1)
}