SQL Server monitoring, seventeen new checks and a stall-proof system collector
This release adds a new CheckMSSQL module for monitoring Microsoft SQL Server, a large batch of new Windows checks covering disks, security hygiene and patch state, richer keywords across many existing checks, and fixes a long-standing class of collector stalls caused by slow WMI providers.
✨ Highlights
- 🗄️ New CheckMSSQL module. Five new commands monitor Microsoft SQL Server over ODBC: connectivity/health, arbitrary T-SQL queries, database state and log usage, backup age and SQL Agent jobs. Windows integrated authentication by default, with optional SQL authentication.
- 🆕 Twelve more new check commands. Disk writability (
check_disk_write), UNC share free space (check_uncpath), Storage Spaces (check_storagepool), VSS snapshots (check_shadowcopy), SMB shares (check_share), Microsoft Defender (check_defender), local account hygiene (check_local_accounts), group membership drift (check_group_members), pending reboot (check_pending_reboot), hotfix age (check_patch_age), print queues (check_printqueue) and paging I/O (check_swap_io). - ⚙️ The system collector no longer freezes on slow WMI providers. Slow every-12-second collections (network, temperature, CPU frequency, battery, OS updates) now run on their own thread, so a blocking WMI query no longer stretches
check_cputime windows or drops samples (#1378). - 📃 Multi-line check output. The new
list-separatoroption on every filter-based check lets long results render one item per line, which Nagios-compatible frontends show as summary + long output (#1370). - 🔥 check_firewall now reports the effective, group-policy-aware state. A firewall enabled or disabled through group policy previously reported its pre-policy local state (#1351).
- ⏱️ Per-disk I/O latency.
check_disk_ioandcheck_disk_healthgainread_latency,write_latencyandtotal_latencykeywords in milliseconds, on both Windows and Linux (#1369). - 🐛 Fixed
disable = cpu_frequencysilently stalling check_cpu. Disabling CPU frequency collection also disabled CPU load sampling (#1368). - 🐧 Linux packages now ship executable scripts. Bundled scripts lost their execute bit when installed by DEB/RPM packages. Thanks to Fabio Fantoni for this and for REUSE/SPDX compliance fixes.
🔍 Detailed changes
🗄️ CheckMSSQL — new module for monitoring Microsoft SQL Server
A new Windows module connecting over ODBC with Windows integrated authentication by default and optional SQL authentication (password stored as a masked settings key). The ODBC driver is auto-detected, preferring the newest "ODBC Driver NN for SQL Server" and falling back to the legacy "SQL Server" driver; on modern drivers TrustServerCertificate=yes is applied by default (overridable via trust-cert/encrypt). Login and query timeouts keep checks from ever hanging the agent, and unreachable servers report UNKNOWN with the full ODBC diagnostic chain.
| Command | Purpose |
|---|---|
check_mssql
| Connectivity and health: version, patch level, edition, uptime with time-unit thresholds |
check_mssql_query
| Arbitrary T-SQL with returned columns exposed as filter keywords and perfdata |
check_mssql_databases
| Database state, recovery model and sizes, plus log usage from DBCC SQLPERF(LOGSPACE)
|
check_mssql_backup
| Age of last full/diff/log backup from msdb; never-backed-up reported as -1 and critical by default |
check_mssql_jobs
| SQL Agent job outcomes, duration and in-flight runs (is_running)
|
check_mssql_backup excludes COPY_ONLY and snapshot backups by default so an ad-hoc dev backup or a VSS agent cannot mask a failing backup job (include-copy-only / include-snapshot opt back in). A new end-to-end scenario, Monitoring a SQL Server host, combines the module with service, disk, memory, PDH and event log checks and documents a low-privilege monitoring login.
check_mssql_backup "critical=full_age > 26h or full_age = -1" "warn=log_age > 2h"
💾 CheckDisk — writability probes, UNC paths, Storage Spaces, VSS and SMB shares
| Command | Purpose |
|---|---|
check_disk_write
| Verify a disk is actually writable: exclusive-create a probe file, write, read back, delete. Never touches a file it did not create; probe size capped at 1M |
check_uncpath
| Free space on a UNC path (server share), with optional alternate credentials |
check_storagepool
| Storage Spaces pool health and capacity |
check_shadowcopy
| VSS snapshot recency, count and shadow-storage usage per volume |
check_share
| List SMB shares or verify that specific required shares exist |
Existing disk checks were extended as well:
check_disk_ioandcheck_disk_healthexpose average per-I/O latency (read_latency,write_latency,total_latency, unit ms) with perfdata and metrics (#1369). On Windows the values are computed from rawPERF_AVERAGE_TIMERcounters (the formatted WMI class truncates realistic latencies to 0); on Linux from/proc/diskstats. Thresholds like"warn=total_latency > 20" "crit=total_latency > 50"work regardless of workload shape.check_drivesizegainsrequire(aliasmandatory-drives): the check goes CRITICAL if any listed drive is missing, even when scanning wildcards.check_drivesizeandcheck_disk_healthcan report physical-disk device state (health and operational status).check_filesgains aggregate file-size metrics and a folder count.
🛡️ CheckSecurity — Defender, local accounts and group membership
| Command | Purpose |
|---|---|
check_defender
| Microsoft Defender status: signature/scan age, real-time and tamper protection, engine/signature versions |
check_local_accounts
| Local account hygiene: enabled/disabled, locked, password-required/expires, built-in admin/guest |
check_group_members
| Local group membership (default Administrators) with alerting on members not on an expected allow-list |
🖥️ CheckSystem — patch state, reboot state, print queues and paging I/O
| Command | Purpose |
|---|---|
check_pending_reboot
| Whether the system is waiting for a reboot, aggregating servicing, Windows Update, file-rename, computer-rename and domain-join signals |
check_patch_age
| Installed-hotfix hygiene: time since the newest hotfix and presence of specific required hotfixes |
check_printqueue
| Print queues: queue depth, oldest-job age, offline and error states per printer |
check_swap_io
| System paging (swap) I/O rates: pages/bytes paged in and out per second |
📈 check_process — background CPU sampling, owners and more memory keywords
check_process delta=true previously sampled inside the check, slept one second and sampled again — stalling every query by a second. CPU deltas are now published by an opt-in background collector (process cpu setting, mirroring process history) that diffs the process table once a second; the check overlays a rolling per-PID CPU% onto a normal no-sleep enumeration. With the collector off, delta=true fails fast with UNKNOWN naming the setting instead of reporting misleading values, and memory/handle fields now keep their real absolute values in delta mode.
Other process-check additions: process owner resolution (with user filtering), an rss alias for working set, thread count, working set and page file percentages, peak memory keywords and system-wide thread/memory totals. Also fixed: the time keyword always reported 0 unless delta sampling was on.
➕ More keywords and options for existing checks
| Check | Addition |
|---|---|
check_network
| Per-interface packet rates, errors and discards (packets_in, packets_out, ...) with perfdata and metrics; NIC team membership (team, team_status) and WMI source keywords
|
check_service
| summary option emitting aggregate state counts (running_services, stopped_services, paused_services, pending_services, service_count) for dashboard rollups
|
check_os_version
| CPU architecture, Windows build revision and inventory-only BIOS fields (serial, version, manufacturer); fixed version detection for Windows 10/11 and Vista/Server 2008 |
check_os_updates
| Support for Defender definition updates and update rollups |
check_cpu_frequency
| Socket information and load percentage |
check_tasksched
| Next run time and missed-run tracking, task URI and hidden properties, default perfdata for task state and missed-run counters |
check_eventlog
| User SID retrieval and filtering; more efficient bookmark handling (plus a bookmark bug fix) |
check_pdh
| Built-in memory_pages_sec counter (\Memory\Pages/sec); more robust resolution of localized counter names
|
⚙️ CheckSystem collector — no more stalls from slow WMI providers (#1378)
The background collector ran network, temperature, CPU frequency, battery and OS update collection on the same 1 Hz thread as CPU/memory/PDH sampling. The network collection queries Win32_PerfRawData_Tcpip_* via WMI with no timeout; when the WMI Performance Adapter service restarts (roughly every 16 minutes on an idle server) that query blocks for 21–24 seconds, freezing the whole collector — stretching check_cpu time windows and dropping samples. The five slow collections now run on their own thread, so a slow provider costs one stale cycle for that metric instead of a frozen collector.
The follow-up hardening fixed a subtle shared-state bug: CheckSystem, CheckEventLog and CheckLogFile all created the same named shutdown event, so stopping or reloading any one of them silently killed the others' background threads — and the name let any co-resident process signal it and disable monitoring from outside. All three now use unnamed, per-instance events with proper cleanup, and a transient COM initialization failure at boot now retries instead of permanently disabling collection.
📃 Filters and output — multi-line lists and REST-safe booleans
-
list-separator(#1370): every filter-based check now accepts a separator for%(list),%(ok_list),%(warn_list),%(crit_list),%(problem_list)and%(detail_list), with\n,\r,\tand\\escapes; real-time filters get a matchinglist separatorsettings key. The decoded separator is also exposed to templates as%(sep)so the line can break before the first item:check_users "top-syntax=%(status): %(count) user(s) logged on:%(sep)%(list)" "detail-syntax=%(user) [%(state)]" "list-separator=\n" OK: 7 user(s) logged on: administrator [active] user1 [active]The default (
,) is unchanged and templates pass through byte-for-byte. -
Valued booleans on common options.
debug,show-allandescape-htmlrejected thex=trueform used by REST (answering with usage text instead of running); they now acceptx=true/x=falsewhile the bare CLI form keeps working. -
%(problem_list)leak fixed. Real-time filters reuse one filter instance;%(problem_list)kept accumulating items from every previous event batch.
🔥 check_firewall — effective, group-policy-aware state (#1351)
check_firewall read only the local policy store, so a firewall configured through local or AD group policy reported its pre-policy state — a GP-disabled firewall showed as enabled and vice versa. The group-policy resultant values (EnableFirewall, default inbound/outbound actions) are now overlaid on the local store, matching Get-NetFirewallProfile -PolicyStore ActiveStore, including the legacy pre-Vista "Protect all network connections" StandardProfile key. A new policy keyword exposes whether a profile's settings come from local or group policy.
🐛 Bug fixes
disable = cpu_frequencyin the CheckSystem collector also disabled CPU load sampling, silently stallingcheck_cpu(#1368).check_processtimekeyword always reported 0 without delta sampling.- A CheckEventLog bookmark bug could skew incremental event log scanning.
📦 Packaging and licensing
- Linux DEB/RPM packages now install the bundled scripts with their execute permission, and
check_ok.shgained its missing shebang, so they can be invoked directly as external-script commands (thanks Fabio Fantoni). - REUSE/SPDX compliance: third-party attributions for bundled CMake modules and binaries are now correctly declared, and the SBOM no longer misattributes them (thanks Fabio Fantoni).
⚠️ Upgrade notes
check_process delta=truebehaviour changed: it now requires the newprocess cpucollector setting to be enabled and returns UNKNOWN (naming the setting) when it is off, instead of sleeping one second inside the check. With the collector on, memory and handle fields report absolute values in delta mode rather than 1-second differences. Default installs (not usingdelta=true) are unaffected.- CheckMSSQL is a new optional module; it is not loaded by default. Enable it and see the new Monitoring a SQL Server host scenario in the docs.
- All other changes are additive; existing configurations render byte-for-byte as before.
Full Changelog: 0.14.1...0.15.0