sensor-snmp: counter semantics — rates, wrap/reset detection, units, typed syntax #527

Closed
opened 2026-07-23 08:11:03 +00:00 by p13marc · 0 comments
p13marc commented 2026-07-23 08:11:03 +00:00 (Migrated from github.com)

Part of #525.

Problem

snmp_value_to_telemetry (zensight-sensor-snmp/src/poller.rs) publishes raw wire values with no semantics:

  • Counter32/Counter64 are published as-is — every consumer (GUI, exporters) sees lifetime octet counts, not rates. No wrap handling (Counter32 wraps in ~5.7 min on a saturated 100 Mb link), no agent-restart/reset detection.
  • Timeticks is emitted as a Counter (hundredths of a second) instead of a duration.
  • OidEntry.syntax (Counter32/Gauge32/... from the MIB table, mib.rs) is stored but never used for typing or scaling.
  • TelemetryPoint carries no unit metadata anywhere (zensight-common/src/telemetry.rs).

Proposal

  • Per-(device, OID) state in the poller: previous value + timestamp → publish a derived rate metric alongside the raw counter (e.g. if/1/ifInOctets stays, add if/1/ifInOctets.rate or a rate=per_second label — pick one convention and document it in docs/reference.md).
  • Counter wrap detection (32- and 64-bit) and reset detection (new value < old and not a plausible wrap, or sysUpTime went backwards → drop the interval, don't publish a negative/garbage rate).
  • Timeticks → Gauge seconds.
  • Use MIB syntax to drive typing/scaling instead of relying solely on the wire tag.
  • Unit metadata: extend TelemetryPoint with an optional unit field (serde-default, CBOR-tolerant) or standardize a unit label — decide in-issue; breaking the wire model is allowed (coordinate with exporters + GUI).

Acceptance

  • Saturating a simulated Counter32 across a wrap produces a correct continuous rate.
  • Agent restart produces one suppressed interval, then correct rates — no negative spikes.
  • sysUpTime renders as a duration in the GUI without frontend special-casing.
  • Prometheus exporter passes rates/units through sensibly (documented behavior).
Part of #525. ## Problem `snmp_value_to_telemetry` (`zensight-sensor-snmp/src/poller.rs`) publishes raw wire values with no semantics: - Counter32/Counter64 are published as-is — every consumer (GUI, exporters) sees lifetime octet counts, not rates. No wrap handling (Counter32 wraps in ~5.7 min on a saturated 100 Mb link), no agent-restart/reset detection. - Timeticks is emitted as a `Counter` (hundredths of a second) instead of a duration. - `OidEntry.syntax` (Counter32/Gauge32/... from the MIB table, `mib.rs`) is stored but **never used** for typing or scaling. - `TelemetryPoint` carries no unit metadata anywhere (`zensight-common/src/telemetry.rs`). ## Proposal - Per-(device, OID) state in the poller: previous value + timestamp → publish a derived **rate** metric alongside the raw counter (e.g. `if/1/ifInOctets` stays, add `if/1/ifInOctets.rate` or a `rate=per_second` label — pick one convention and document it in `docs/reference.md`). - Counter wrap detection (32- and 64-bit) and reset detection (new value < old and not a plausible wrap, or sysUpTime went backwards → drop the interval, don't publish a negative/garbage rate). - Timeticks → `Gauge` seconds. - Use MIB `syntax` to drive typing/scaling instead of relying solely on the wire tag. - Unit metadata: extend `TelemetryPoint` with an optional `unit` field (serde-default, CBOR-tolerant) or standardize a `unit` label — decide in-issue; breaking the wire model is allowed (coordinate with exporters + GUI). ## Acceptance - Saturating a simulated Counter32 across a wrap produces a correct continuous rate. - Agent restart produces one suppressed interval, then correct rates — no negative spikes. - sysUpTime renders as a duration in the GUI without frontend special-casing. - Prometheus exporter passes rates/units through sensibly (documented behavior).
Sign in to join this conversation.
No milestone
No project
No assignees
1 participant
Notifications
Due date
The due date is invalid or out of range. Please use the format "yyyy-mm-dd".

No due date set.

Dependencies

No dependencies set.

Reference
marcpardo/zensight#527
No description provided.