SenHub Agent 0.2.3¶
2026-06-12 · security & resilience release
The security wave: every audit-flagged hardening lands at once.
Self-updates are signature-verified (minisign, fail-closed), all
network listeners default to loopback with explicit opt-in for
remote access, the OTLP receiver gains token auth, CIDR allow-lists
and rate limiting, snmp_poll speaks SNMPv3, and a long series
of resilience fixes (bounded push buffers, atomic config reads,
goroutine-leak class elimination, stale-series eviction) hardens
long-running fleets.
Action may be required
Network listeners now bind 127.0.0.1 by default. Configs
generated by agent install always set bind_address explicitly
and are not affected. Hand-written configs that relied on the old
bind-all default while being polled remotely must add an explicit
bind_address. See the Changed section below.
New¶
- New security Self-updates are now signature-verified: the agent checks a detached minisign signature over each release archive against a public key embedded at build time, and refuses unsigned or tampered artifacts (fail-closed; rejections surface as
senhub.agent.update.rejected). (#266) - New security The OTLP receiver gains optional ingress protections:
bearer_tokenauth (HTTP header or gRPC metadata),allowed_cidrssource allow-list and arate_limit_rpstoken-bucket limiter — recommended whenever the receiver is opened beyond loopback. (#278) - New SNMP
snmp_pollsupports SNMPv3 (USM auth + privacy, security level derived from the configured protocols). (#156) - New SNMP
snmp_pollgainsmib_paths: a custom mapping may omitmetricand have its name resolved from operator-supplied MIB files at startup. (#291)
Fixed¶
- Fixed OTLP Stale series eviction (
staleness_ttl, default 10m) — series whose probe was removed or denied no longer re-export forever with fresh timestamps from the persisted store (zombie metrics seen twice in production recettes). (#308) - Fixed topology A transient sweep failure no longer deletes the device tree in the consumer; sources are unregistered on probe shutdown; unchanged entity heartbeats are suppressed between refreshes. (#272)
- Fixed SNMP
senhub.snmp.upnow reflects whether the device answered, not whether a UDP socket opened — a powered-off switch finally reports down. (#156) - Fixed security SNMPv3 passphrases and community strings are masked in logs. (#156)
- Fixed security
agent config showmasks secrets by default; cleartext output now requires the explicit--resolvedflag. (#279) - Fixed security
agent installon Linux now writes the hardened systemd unit the packages ship — daemon runs as the dedicatedsenhubuser (created at install) with all capabilities dropped, instead of an implicit root unit.install --user rootkeeps the legacy behavior; existing units are never rewritten on upgrade. (#280) - Fixed security The Windows administrator check uses the process token elevation API instead of probing
\\.\PHYSICALDRIVE0, which broke on hosts without that device. (#280) - Fixed PRTG The PRTG push closes its HTTP response — it leaked one connection per sync cycle. (#277)
- Fixed checks
icmp_checkdefaults to privileged raw sockets on Linux when running as root — unprivileged datagram ICMP is disabled by default on Ubuntu/Debian (ping_group_range) and silently reported every target down; the permission error now carries an actionable hint. (#357)
Changed¶
- Changed security All network listeners now default to loopback (127.0.0.1) instead of all interfaces: the HTTP API (
bind_address), the OTLP receiver probe (address), the SNMP trap receiver (bind_address) and the syslog probe — whose bind address was previously hardcoded to 0.0.0.0 and is now configurable (bind_address). Accepting remote senders/pollers requires an explicit opt-in, and binding all interfaces logs a startup warning. Action required only for hand-written configs that omitted the bind parameter while relying on remote access — addbind_address: "0.0.0.0"(or a specific interface IP) to the relevant section; configs generated byagent installalways wrote it explicitly. (#278) - Changed outputs The never-implemented Zabbix HTTP endpoint (always 501) is removed;
endpoints: [zabbix]now fails fast at startup. The Zabbix integration is redesigned as a native active agent, deferred (#169).
Changed (metric names)¶
The OTel names of eight Windows/hardware rate metrics carried a
per_second suffix in the NAME, which the Prometheus-compatibility
layers then doubled with the unit-derived suffix
(senhub_system_disk_io_per_second_bytes_per_second through an OTel
collector). The unit now drives the suffix alone; the resulting
Prometheus names are the ones the metrics reference always documented.
| Before (OTel name) | After (OTel name) | Prometheus name (both ingestion paths) |
|---|---|---|
senhub.system.cpu.dpcs_per_second |
senhub.system.cpu.dpcs |
senhub_system_cpu_dpcs_per_second |
senhub.system.cpu.dpcs_queued_per_second |
senhub.system.cpu.dpcs_queued |
senhub_system_cpu_dpcs_queued_per_second |
senhub.system.cpu.interrupts_per_second |
senhub.system.cpu.interrupts |
senhub_system_cpu_interrupts_per_second |
senhub.system.paging.faults_per_second |
senhub.system.paging.faults |
senhub_system_paging_faults_per_second |
senhub.system.paging.operations_per_second |
senhub.system.paging.operations |
senhub_system_paging_operations_per_second |
senhub.system.disk.operations_per_second |
senhub.system.disk.operations |
senhub_system_disk_operations_per_second |
senhub.system.disk.io_per_second |
senhub.system.disk.io |
senhub_system_disk_io_bytes_per_second |
senhub.hardware.physical_disk.link_speed_bits_per_second |
senhub.hardware.physical_disk.link_speed |
senhub_hardware_physical_disk_link_speed_bits_per_second |
Internal¶
- Internal Shared
snmpcorepackage — one printability semantics, value rendering, version mapping and v3 USM tables consumed by both SNMP probes. (#291)