max / makenotwork
| 1 | //! SyncKit fleet readout for monitoring agents. |
| 2 | //! |
| 3 | //! `GET /api/internal/synckit/client-versions` reports which SyncKit SDK |
| 4 | //! versions are actually syncing, aggregated from `sync_devices.client_version`. |
| 5 | //! SyncKit is client-side only, linked into mnw-cli, balanced_breakfast and |
| 6 | //! audiofiles, so there is no deployed version for PoM to poll the usual way; |
| 7 | //! this is the substitute, and it answers the better question anyway. |
| 8 | //! |
| 9 | //! Authed by [`AlertsAuth`], the same bearer PoM already carries. That |
| 10 | //! credential exists for monitoring agents running on other hosts, which is |
| 11 | //! exactly what polls this; `ServiceAuth` is the CLI's on-host token and reusing |
| 12 | //! it here would widen a blast radius for no reason. Deliberately not on the |
| 13 | //! public health body: which versions are in the field (including old, unpatched |
| 14 | //! ones) is an operator signal, not a public one. |
| 15 | |
| 16 | use |
| 17 | Json, |
| 18 | , |
| 19 | IntoResponse, |
| 20 | ; |
| 21 | use Deserialize; |
| 22 | use PgPool; |
| 23 | |
| 24 | use crate::; |
| 25 | |
| 26 | /// Default activity window. A month is long enough that a laptop opened weekly |
| 27 | /// still counts, short enough that a machine retired last year stops dragging an |
| 28 | /// ancient version through the readout. |
| 29 | const DEFAULT_WINDOW_DAYS: i32 = 30; |
| 30 | |
| 31 | /// Widest window we will aggregate over. Bounds the scan, and a year-wide |
| 32 | /// reading stops meaning "in the field" anyway. |
| 33 | const MAX_WINDOW_DAYS: i32 = 365; |
| 34 | |
| 35 | |
| 36 | pub |
| 37 | /// Count devices last seen within this many days. Clamped to |
| 38 | /// `1..=MAX_WINDOW_DAYS`. |
| 39 | days: , |
| 40 | |
| 41 | |
| 42 | pub async |
| 43 | State: , |
| 44 | _auth: AlertsAuth, |
| 45 | Query: , |
| 46 | |
| 47 | let days = q |
| 48 | .days |
| 49 | .unwrap_or |
| 50 | .clamp; |
| 51 | let versions = client_version_distribution.await?; |
| 52 | Ok |
| 53 | "window_days": days, |
| 54 | "devices": versions.iter.map., |
| 55 | "versions": versions, |
| 56 | |
| 57 | |
| 58 |