mixin: move kubernetes to docs, dashboard and rendered rules to contrib

kubernetes/ moves to docs/kubernetes/, dashboard/ to contrib/dashboard/,
and the rendered Prometheus rules and alerts to contrib/monitoring/ with
a README that says how to use and regenerate them.

Signed-off-by: Jan-Otto Kröpke <mail@jkroepke.de>
This commit is contained in:
Jan-Otto Kröpke
2026-10-17 19:26:11 +00:00
parent 8e35c1e6a9
commit 018ec75223
39 changed files with 71 additions and 40 deletions
+2 -1
View File
@@ -59,7 +59,8 @@ A new alert touches six places, and CI checks all of them:
a runbook mentions against the metrics the exporter emits; the names in
the collector docs are not always current, so check the collector source.
5. A row in the alerts table of `README.md`.
6. The committed `windows_rules.yaml` and `windows_alerts.yaml`, regenerated
6. The committed `contrib/monitoring/windows_rules.yaml` and
`windows_alerts.yaml`, regenerated
with `mise run rules`; `mise run check-rules` fails in CI when they are
stale.
+7 -6
View File
@@ -24,7 +24,8 @@ Bundler using Go. `mise run` makes the pinned tools available automatically.
Only the dashboard depends on Jsonnet libraries, so `jb install` is not required
to generate rules. The rules rendered from the default configuration are
committed next to the sources, so they can be used without Jsonnet:
committed in [`contrib/monitoring`](../monitoring), so they can be used
without Jsonnet:
- `windows_rules.yaml`: recording rules.
- `windows_alerts.yaml`: alerting rules.
@@ -310,10 +311,10 @@ Fork users should override `runbookURLPattern` to match their published URL.
`grafanaDashboards` contains `windows-exporter.json`, the full sample dashboard
with all tabs in
[dashboard/windows-exporter-dashboard.json](../../dashboard/windows-exporter-dashboard.json),
[contrib/dashboard/windows-exporter-dashboard.json](../dashboard/windows-exporter-dashboard.json),
and a shorter dashboard per tab, such as `windows-exporter-cpu.json`, in
[dashboard](../../dashboard). They are Grafana v2 dashboards and need Grafana 13
or later. See the [dashboard documentation](../../dashboard/README.md) for their
[contrib/dashboard](../dashboard). They are Grafana v2 dashboards and need Grafana 13
or later. See the [dashboard documentation](../dashboard/README.md) for their
content.
The dashboard uses additive builders with [grafonnet](https://github.com/grafana/grafonnet),
@@ -360,7 +361,7 @@ Regenerate the committed files after changing the dashboard source:
mise run dashboard
```
This runs `jb install` and writes `../../dashboard/windows-exporter-*.json`.
This runs `jb install` and writes `../dashboard/windows-exporter-*.json`.
`mise run dashboards` is an alias. `mise run generate` builds both the rules and the
dashboard, while `mise run rules` builds only the rules. The same commands work
inside WSL; mise supplies the tool binaries on `PATH`.
@@ -510,7 +511,7 @@ prometheus "local" {
}
```
Then run `pint --config /path/to/local.pint.hcl lint windows_rules.yaml windows_alerts.yaml`
Then run `pint --config /path/to/local.pint.hcl lint ../monitoring/windows_rules.yaml ../monitoring/windows_alerts.yaml`
without `--offline`. See the [pint documentation](https://cloudflare.github.io/pint/)
for available checks.
+1 -1
View File
@@ -1,4 +1,4 @@
// Renders the sample dashboards into ../../dashboard. Run with
// Renders the sample dashboards into ../dashboard. Run with
// jsonnet -J vendor -S -m <directory>. The sample dashboards show every
// collector; mixin users select theirs with _config.collectors.
local manifest = import 'lib/manifest.libsonnet';
+10 -9
View File
@@ -8,7 +8,8 @@
[vars]
sources = "*.libsonnet *.jsonnet lib/*.libsonnet rules/*.libsonnet alerts/*.libsonnet dashboards/*.libsonnet tests/*.libsonnet tests/*.jsonnet"
fmt_flags = "-n 2 --max-blank-lines 2 --string-style s --comment-style s"
dashboards = "../../dashboard"
dashboards = "../dashboard"
rules = "../monitoring"
[tasks.generate]
description = "Generate Prometheus rules, alerts, and the dashboard"
@@ -16,10 +17,10 @@ alias = "default"
depends = ["rules", "dashboard"]
[tasks.rules]
description = "Generate Prometheus rules and alerts"
description = "Generate the Prometheus rules and alerts in contrib/monitoring"
run = [
"jsonnet -S rules.jsonnet > windows_rules.yaml",
"jsonnet -S alerts.jsonnet > windows_alerts.yaml",
"jsonnet -S rules.jsonnet > {{vars.rules}}/windows_rules.yaml",
"jsonnet -S alerts.jsonnet > {{vars.rules}}/windows_alerts.yaml",
]
[tasks.vendor]
@@ -40,12 +41,12 @@ cp "$out"/*.json {{vars.dashboards}}/
'''
[tasks.check-rules]
description = "Regenerate the rules and alerts and fail on uncommitted changes"
description = "Regenerate the rules and alerts in contrib/monitoring and fail on uncommitted changes"
depends = ["rules"]
run = '''
set -eu
git add --intent-to-add -- windows_rules.yaml windows_alerts.yaml
git diff --exit-code -- windows_rules.yaml windows_alerts.yaml
git add --intent-to-add -- {{vars.rules}}/windows_rules.yaml {{vars.rules}}/windows_alerts.yaml
git diff --exit-code -- {{vars.rules}}
'''
[tasks.check-dashboards]
@@ -97,8 +98,8 @@ for file in $(cat "$out/generated"); do
diff -u {{vars.dashboards}}/"$file" "$out/$file" \
|| { echo "{{vars.dashboards}}/$file is out of date; run mise run dashboard"; exit 1; }
done
promtool check rules windows_rules.yaml windows_alerts.yaml tests/custom_rules.yaml tests/custom_alerts.yaml ../../docs/upgrade/0.32.prom
pint --offline lint windows_rules.yaml windows_alerts.yaml
promtool check rules {{vars.rules}}/windows_rules.yaml {{vars.rules}}/windows_alerts.yaml tests/custom_rules.yaml tests/custom_alerts.yaml ../../docs/upgrade/0.32.prom
pint --offline lint {{vars.rules}}/windows_rules.yaml {{vars.rules}}/windows_alerts.yaml
pint --offline lint tests/custom_rules.yaml tests/custom_alerts.yaml
'''
+2 -2
View File
@@ -1,6 +1,6 @@
rule_files:
- ../windows_rules.yaml
- ../windows_alerts.yaml
- ../../monitoring/windows_rules.yaml
- ../../monitoring/windows_alerts.yaml
evaluation_interval: 1m
group_eval_order:
- windows-exporter-recording
+2 -2
View File
@@ -1,6 +1,6 @@
rule_files:
- ../windows_rules.yaml
- ../windows_alerts.yaml
- ../../monitoring/windows_rules.yaml
- ../../monitoring/windows_alerts.yaml
evaluation_interval: 1m
group_eval_order:
- windows-exporter-recording
+1 -1
View File
@@ -1,5 +1,5 @@
rule_files:
- ../windows_rules.yaml
- ../../monitoring/windows_rules.yaml
evaluation_interval: 1m
fuzzy_compare: true
-249
View File
@@ -1,249 +0,0 @@
groups:
- name: "windows-exporter"
rules:
- alert: "WindowsExporterDown"
annotations:
description: "Prometheus cannot scrape Windows exporter on {{ $labels.instance }} (job {{ $labels.job }})."
runbook_url: "https://prometheus-community.github.io/windows_exporter/runbooks/windowsexporterdown/"
summary: "Windows exporter is unreachable"
expr: |
up{job="windows_exporter"} == 0
for: "5m"
labels:
severity: "critical"
- alert: "WindowsCollectorFailed"
annotations:
description: "Collector {{ $labels.collector }} on {{ $labels.instance }} has failed for at least 5 minutes."
runbook_url: "https://prometheus-community.github.io/windows_exporter/runbooks/windowscollectorfailed/"
summary: "Windows collector failed"
expr: |
windows_exporter_collector_success{job="windows_exporter"} == 0
for: "5m"
labels:
severity: "warning"
- alert: "WindowsCollectorTimeout"
annotations:
description: "Collector {{ $labels.collector }} on {{ $labels.instance }} has not finished within the scrape timeout for 10 minutes."
runbook_url: "https://prometheus-community.github.io/windows_exporter/runbooks/windowscollectortimeout/"
summary: "Windows collector exceeds the scrape timeout"
expr: |
windows_exporter_collector_timeout{job="windows_exporter"} == 1
for: "10m"
labels:
severity: "warning"
- alert: "WindowsScrapeQueueTimeout"
annotations:
description: "Scrapes of {{ $labels.instance }} have timed out waiting for an earlier scrape to finish for 10 minutes."
runbook_url: "https://prometheus-community.github.io/windows_exporter/runbooks/windowsscrapequeuetimeout/"
summary: "Windows exporter scrapes time out in the queue"
expr: |
windows_exporter_scrape_queue_timeout{job="windows_exporter"} == 1
for: "10m"
labels:
severity: "warning"
- name: "windows-cpu"
rules:
- alert: "WindowsCPUHighUsage"
annotations:
description: "CPU usage on {{ $labels.instance }} has exceeded 90% for 15 minutes."
runbook_url: "https://prometheus-community.github.io/windows_exporter/runbooks/windowscpuhighusage/"
summary: "Windows CPU usage is high"
expr: |
windows:cpu_usage:ratio{job="windows_exporter"} * 100 > 90
for: "15m"
keep_firing_for: "5m"
labels:
severity: "warning"
- alert: "WindowsCPUSaturation"
annotations:
description: "More than 2 threads per logical processor have been waiting for CPU time on {{ $labels.instance }} for 15 minutes."
runbook_url: "https://prometheus-community.github.io/windows_exporter/runbooks/windowscpusaturation/"
summary: "Windows processor queue is long"
expr: |
windows:cpu_queue_per_core:ratio{job="windows_exporter"} > 2
for: "15m"
keep_firing_for: "5m"
labels:
severity: "warning"
- name: "windows-memory"
rules:
- alert: "WindowsMemoryHighUsage"
annotations:
description: "Physical memory usage on {{ $labels.instance }} has exceeded 90% for 15 minutes."
runbook_url: "https://prometheus-community.github.io/windows_exporter/runbooks/windowsmemoryhighusage/"
summary: "Windows memory usage is high"
expr: |
windows:memory_usage:ratio{job="windows_exporter"} * 100 > 90
for: "15m"
keep_firing_for: "5m"
labels:
severity: "warning"
- alert: "WindowsMemoryCommitHighUsage"
annotations:
description: "Committed memory on {{ $labels.instance }} has exceeded 90% of the commit limit for 15 minutes."
runbook_url: "https://prometheus-community.github.io/windows_exporter/runbooks/windowsmemorycommithighusage/"
summary: "Windows memory commit usage is high"
expr: |
windows:memory_committed:ratio{job="windows_exporter"} * 100 > 90
for: "15m"
keep_firing_for: "5m"
labels:
severity: "warning"
- alert: "WindowsMemoryPagingHigh"
annotations:
description: "Paging on {{ $labels.instance }} has exceeded 1000 pages per second for 15 minutes."
runbook_url: "https://prometheus-community.github.io/windows_exporter/runbooks/windowsmemorypaginghigh/"
summary: "Windows memory paging is high"
expr: |
windows:memory_swap_page_operations:rate{job="windows_exporter"} > 1000
for: "15m"
keep_firing_for: "5m"
labels:
severity: "warning"
- name: "windows-disk"
rules:
- alert: "WindowsDiskReadLatencyHigh"
annotations:
description: "Volume {{ $labels.volume }} on {{ $labels.instance }} has averaged more than 0.05 seconds per read operation for 15 minutes."
runbook_url: "https://prometheus-community.github.io/windows_exporter/runbooks/windowsdiskreadlatencyhigh/"
summary: "Windows disk read latency is high"
expr: |
windows:logical_disk_read_latency:seconds{job="windows_exporter", volume!=""} > 0.05
for: "15m"
keep_firing_for: "5m"
labels:
severity: "warning"
- alert: "WindowsDiskWriteLatencyHigh"
annotations:
description: "Volume {{ $labels.volume }} on {{ $labels.instance }} has averaged more than 0.05 seconds per write operation for 15 minutes."
runbook_url: "https://prometheus-community.github.io/windows_exporter/runbooks/windowsdiskwritelatencyhigh/"
summary: "Windows disk write latency is high"
expr: |
windows:logical_disk_write_latency:seconds{job="windows_exporter", volume!=""} > 0.05
for: "15m"
keep_firing_for: "5m"
labels:
severity: "warning"
- alert: "WindowsDiskAlmostFull"
annotations:
description: "Volume {{ $labels.volume }} on {{ $labels.instance }} has less than 10% free space. Windows may delay space metrics by 10–15 minutes."
runbook_url: "https://prometheus-community.github.io/windows_exporter/runbooks/windowsdiskalmostfull/"
summary: "Windows disk space is low"
expr: |
windows:logical_disk_free:ratio{job="windows_exporter", volume!=""} * 100 < 10
for: "15m"
keep_firing_for: "5m"
labels:
severity: "warning"
- alert: "WindowsDiskAlmostFull"
annotations:
description: "Volume {{ $labels.volume }} on {{ $labels.instance }} has less than 5% free space. Windows may delay space metrics by 10–15 minutes."
runbook_url: "https://prometheus-community.github.io/windows_exporter/runbooks/windowsdiskalmostfull/"
summary: "Windows disk space is low"
expr: |
windows:logical_disk_free:ratio{job="windows_exporter", volume!=""} * 100 < 5
for: "15m"
keep_firing_for: "5m"
labels:
severity: "critical"
- alert: "WindowsDiskFillingUp"
annotations:
description: "Volume {{ $labels.volume }} on {{ $labels.instance }} is predicted to fill within 24 hours."
runbook_url: "https://prometheus-community.github.io/windows_exporter/runbooks/windowsdiskfillingup/"
summary: "Windows disk is predicted to fill up"
expr: |
windows:logical_disk_free:ratio{job="windows_exporter", volume!=""} * 100 < 10
and predict_linear(windows_logical_disk_free_bytes{job="windows_exporter", volume!=""}[6h], 86400) < 0
for: "1h"
keep_firing_for: "5m"
labels:
severity: "warning"
- name: "windows-network"
rules:
- alert: "WindowsNetworkErrors"
annotations:
description: "Packet errors on interface {{ $labels.nic }} on {{ $labels.instance }} have exceeded 1% of all packets for 15 minutes."
runbook_url: "https://prometheus-community.github.io/windows_exporter/runbooks/windowsnetworkerrors/"
summary: "Windows network packet errors are high"
expr: |
(
(windows:net_received_errors:rate{job="windows_exporter", nic!=""} + windows:net_outbound_errors:rate{job="windows_exporter", nic!=""})
/ ((windows:net_received_packets:rate{job="windows_exporter", nic!=""} + windows:net_sent_packets:rate{job="windows_exporter", nic!=""}) > 0)
) * 100 > 1
for: "15m"
keep_firing_for: "5m"
labels:
severity: "warning"
- alert: "WindowsNetworkDiscards"
annotations:
description: "Packet discards on interface {{ $labels.nic }} on {{ $labels.instance }} have exceeded 1% of all packets for 15 minutes."
runbook_url: "https://prometheus-community.github.io/windows_exporter/runbooks/windowsnetworkdiscards/"
summary: "Windows network packet discards are high"
expr: |
(
(windows:net_received_discarded:rate{job="windows_exporter", nic!=""} + windows:net_outbound_discarded:rate{job="windows_exporter", nic!=""})
/ ((windows:net_received_packets:rate{job="windows_exporter", nic!=""} + windows:net_sent_packets:rate{job="windows_exporter", nic!=""}) > 0)
) * 100 > 1
for: "15m"
keep_firing_for: "5m"
labels:
severity: "warning"
- alert: "WindowsNetworkUtilizationHigh"
annotations:
description: "Traffic on interface {{ $labels.nic }} on {{ $labels.instance }} has exceeded 90% of its bandwidth in at least one direction for 15 minutes."
runbook_url: "https://prometheus-community.github.io/windows_exporter/runbooks/windowsnetworkutilizationhigh/"
summary: "Windows network interface utilization is high"
expr: |
(windows:net_received_utilization:ratio{job="windows_exporter", nic!=""} * 100 > 90)
or (windows:net_sent_utilization:ratio{job="windows_exporter", nic!=""} * 100 > 90)
for: "15m"
keep_firing_for: "5m"
labels:
severity: "warning"
- alert: "WindowsNetworkInterfaceFlapping"
annotations:
description: "Interface {{ $labels.nic }} on {{ $labels.instance }} has changed its operational status more than twice in 5m."
runbook_url: "https://prometheus-community.github.io/windows_exporter/runbooks/windowsnetworkinterfaceflapping/"
summary: "Windows network interface is flapping"
expr: |
max without (status) (changes(windows_net_nic_operation_status{job="windows_exporter", nic!="", status="up"}[5m])) > 2
for: "2m"
keep_firing_for: "5m"
labels:
severity: "warning"
- name: "windows-service"
rules:
- alert: "WindowsServiceNotRunning"
annotations:
description: "Service {{ $labels.service }} on {{ $labels.instance }} starts automatically but has not been running for 15 minutes."
runbook_url: "https://prometheus-community.github.io/windows_exporter/runbooks/windowsservicenotrunning/"
summary: "Windows automatic service is not running"
expr: |
max without (state) (windows_service_state{job="windows_exporter", service!="", state="running"} == 0)
and ignoring (start_mode) (windows_service_start_mode{job="windows_exporter", service!="", start_mode="auto"} == 1)
unless ignoring (display_name, run_as, path_name, delayed_start, trigger_start) (windows_service_info{job="windows_exporter", service!="", trigger_start="true"} == 1)
for: "15m"
labels:
severity: "warning"
- alert: "WindowsServiceCrashLooping"
annotations:
description: "Service {{ $labels.service }} on {{ $labels.instance }} has restarted more than 2 times in 15 minutes."
runbook_url: "https://prometheus-community.github.io/windows_exporter/runbooks/windowsservicecrashlooping/"
summary: "Windows service is restarting repeatedly"
expr: |
count without (process_id) (count_over_time(windows_service_process{job="windows_exporter", service!=""}[15m])) - 1 > 2
keep_firing_for: "5m"
labels:
severity: "warning"
- name: "windows-system"
rules:
- alert: "WindowsHostRebooted"
annotations:
description: "{{ $labels.instance }} rebooted {{ $value | humanizeDuration }} ago."
runbook_url: "https://prometheus-community.github.io/windows_exporter/runbooks/windowshostrebooted/"
summary: "Windows host has rebooted"
expr: |
(time() - windows_system_boot_time_timestamp{job="windows_exporter"}) < 600
and (time() - last_over_time(windows_system_boot_time_timestamp{job="windows_exporter"}[1h] offset 10m)) > 600
labels:
severity: "info"
-59
View File
@@ -1,59 +0,0 @@
groups:
- name: "windows-exporter-recording"
rules:
- expr: "1 - avg without (core, mode) (rate(windows_cpu_time_seconds_total{job=\"windows_exporter\", mode=\"idle\"}[5m]))"
record: "windows:cpu_usage:ratio"
- expr: "count without (core, mode) (windows_cpu_time_seconds_total{job=\"windows_exporter\", mode=\"idle\"})"
record: "windows:cpu_cores:count"
- expr: "avg without (core) (rate(windows_cpu_time_seconds_total{job=\"windows_exporter\"}[5m]))"
record: "windows:cpu_time:ratio_rate"
- expr: "(avg_over_time(windows_system_processor_queue_length{job=\"windows_exporter\"}[5m]) / (windows:cpu_cores:count{job=\"windows_exporter\"} > 0))"
record: "windows:cpu_queue_per_core:ratio"
- expr: "1 - (windows_memory_available_bytes{job=\"windows_exporter\"} / (windows_memory_physical_total_bytes{job=\"windows_exporter\"} > 0))"
record: "windows:memory_usage:ratio"
- expr: "windows_memory_physical_total_bytes{job=\"windows_exporter\"} - windows_memory_available_bytes{job=\"windows_exporter\"}"
record: "windows:memory_used:bytes"
- expr: "windows_memory_cache_bytes{job=\"windows_exporter\"} + windows_memory_modified_page_list_bytes{job=\"windows_exporter\"} + windows_memory_standby_cache_core_bytes{job=\"windows_exporter\"} + windows_memory_standby_cache_normal_priority_bytes{job=\"windows_exporter\"} + windows_memory_standby_cache_reserve_bytes{job=\"windows_exporter\"}"
record: "windows:memory_cached:bytes"
- expr: "(windows_memory_committed_bytes{job=\"windows_exporter\"} / (windows_memory_commit_limit_bytes{job=\"windows_exporter\"} > 0))"
record: "windows:memory_committed:ratio"
- expr: "rate(windows_memory_swap_page_operations_total{job=\"windows_exporter\"}[5m])"
record: "windows:memory_swap_page_operations:rate"
- expr: "(windows_logical_disk_free_bytes{job=\"windows_exporter\", volume!=\"\"} / (windows_logical_disk_size_bytes{job=\"windows_exporter\", volume!=\"\"} > 0))"
record: "windows:logical_disk_free:ratio"
- expr: "windows_logical_disk_size_bytes{job=\"windows_exporter\", volume!=\"\"} - windows_logical_disk_free_bytes{job=\"windows_exporter\", volume!=\"\"}"
record: "windows:logical_disk_used:bytes"
- expr: "clamp(1 - rate(windows_logical_disk_idle_seconds_total{job=\"windows_exporter\", volume!=\"\"}[5m]), 0, 1)"
record: "windows:logical_disk_busy:ratio"
- expr: "rate(windows_logical_disk_read_bytes_total{job=\"windows_exporter\", volume!=\"\"}[5m])"
record: "windows:logical_disk_read_bytes:rate"
- expr: "rate(windows_logical_disk_write_bytes_total{job=\"windows_exporter\", volume!=\"\"}[5m])"
record: "windows:logical_disk_write_bytes:rate"
- expr: "rate(windows_logical_disk_reads_total{job=\"windows_exporter\", volume!=\"\"}[5m])"
record: "windows:logical_disk_read_operations:rate"
- expr: "rate(windows_logical_disk_writes_total{job=\"windows_exporter\", volume!=\"\"}[5m])"
record: "windows:logical_disk_write_operations:rate"
- expr: "(rate(windows_logical_disk_read_seconds_total{job=\"windows_exporter\", volume!=\"\"}[5m]) / (rate(windows_logical_disk_reads_total{job=\"windows_exporter\", volume!=\"\"}[5m]) > 0))"
record: "windows:logical_disk_read_latency:seconds"
- expr: "(rate(windows_logical_disk_write_seconds_total{job=\"windows_exporter\", volume!=\"\"}[5m]) / (rate(windows_logical_disk_writes_total{job=\"windows_exporter\", volume!=\"\"}[5m]) > 0))"
record: "windows:logical_disk_write_latency:seconds"
- expr: "rate(windows_net_bytes_received_total{job=\"windows_exporter\", nic!=\"\"}[5m])"
record: "windows:net_received_bytes:rate"
- expr: "rate(windows_net_bytes_sent_total{job=\"windows_exporter\", nic!=\"\"}[5m])"
record: "windows:net_sent_bytes:rate"
- expr: "rate(windows_net_packets_received_total{job=\"windows_exporter\", nic!=\"\"}[5m])"
record: "windows:net_received_packets:rate"
- expr: "rate(windows_net_packets_sent_total{job=\"windows_exporter\", nic!=\"\"}[5m])"
record: "windows:net_sent_packets:rate"
- expr: "(rate(windows_net_bytes_received_total{job=\"windows_exporter\", nic!=\"\"}[5m]) / (windows_net_current_bandwidth_bytes{job=\"windows_exporter\", nic!=\"\"} > 0))"
record: "windows:net_received_utilization:ratio"
- expr: "(rate(windows_net_bytes_sent_total{job=\"windows_exporter\", nic!=\"\"}[5m]) / (windows_net_current_bandwidth_bytes{job=\"windows_exporter\", nic!=\"\"} > 0))"
record: "windows:net_sent_utilization:ratio"
- expr: "rate(windows_net_packets_received_errors_total{job=\"windows_exporter\", nic!=\"\"}[5m])"
record: "windows:net_received_errors:rate"
- expr: "rate(windows_net_packets_received_discarded_total{job=\"windows_exporter\", nic!=\"\"}[5m])"
record: "windows:net_received_discarded:rate"
- expr: "rate(windows_net_packets_outbound_errors_total{job=\"windows_exporter\", nic!=\"\"}[5m])"
record: "windows:net_outbound_errors:rate"
- expr: "rate(windows_net_packets_outbound_discarded_total{job=\"windows_exporter\", nic!=\"\"}[5m])"
record: "windows:net_outbound_discarded:rate"