NDBC Salinity Time Series

Per-buoy salinity from the USF MBON Grafana dashboard

Code
library(dplyr)
library(ggplot2)
library(htmltools)
library(httr2)

source("R/plot_grafana_salinity_ts.R")
source("R/ndbc_time.R")

ndbc_stations <- list(
  list(name = "bkyf1", long_name = "Buoy_Key"),
  list(name = "bnkf1", long_name = "Butternut_Kay"),
  list(name = "bobf1", long_name = "Bob_Allen_Key"),
  list(name = "bwsf1", long_name = "Blackwater_Sound"),
  list(name = "dkkf1", long_name = "Duck_Key"),
  list(name = "gbtf1", long_name = "Garfield_Bight"),
  list(name = "hcef1", long_name = "Highway_Creek"),
  list(name = "jbyf1", long_name = "Joe_Bay"),
  list(name = "jkyf1", long_name = "Johnson_Key"),
  list(name = "lbsf1", long_name = "Little_Blackwater_Sound"),
  list(name = "lmdf1", long_name = "Little_Madeira_Bay"),
  list(name = "lrkf1", long_name = "Little_Rabbit_Key"),
  list(name = "lsnf1", long_name = "Long_Sound"),
  list(name = "mdkf1", long_name = "Middle_Key"),
  list(name = "mukf1", long_name = "Murray_Key"),
  list(name = "pkyf1", long_name = "Peterson_Key"),
  list(name = "tbyf1", long_name = "Terrapin_Bay"),
  list(name = "thrf1", long_name = "Thursday_Point"),
  list(name = "wrbf1", long_name = "Whipray_Basin")
)

from_ms <- GRAFANA_DEFAULT_FROM
to_ms <- GRAFANA_DEFAULT_TO

salinity_ts <- fetch_grafana_salinity_timeseries(
  from = from_ms,
  to = to_ms
)

report_time <- format(Sys.time(), "%Y-%m-%d %H:%M %Z", tz = ndbc_display_tz)
range_start <- format_ndbc_time(as.POSIXct(as.numeric(from_ms) / 1000, origin = "1970-01-01", tz = "UTC"))
range_end <- format_ndbc_time(as.POSIXct(as.numeric(to_ms) / 1000, origin = "1970-01-01", tz = "UTC"))

Each panel below matches Grafana panel 33 (In-situ salinity (psu) at ~1m depth from $Buoy) on the USF MBON South Florida Salinity dashboard. Time series are queried from the dashboard’s InfluxDB datasource via the Grafana /api/ds/query endpoint, using the same query and time range as the dashboard link you provided.

Report generated: 2026-07-27 10:14 EDT
Time range: 2024-07-14 09:58 EDT to 2026-07-14 09:58 EDT
Stations plotted: 17

Dashed lines mark the same low (25 PSU) and high (35 PSU) thresholds used on the Salinity Gauges page.

Buoy panels

Code
if (nrow(salinity_ts) == 0) {
  stop("No salinity time series returned from the Grafana datasource.")
}

htmltools::tagList(
  plot_grafana_salinity_panels(
    ndbc_stations,
    salinity_ts,
    from = from_ms,
    to = to_ms
  )
)