Compare commits

...

3 commits

Author SHA1 Message Date
2d67a016b0 Add separate thresholds for upstream and downstream transfer rate
The old thresholds are the default and apply to both if they are not explicitly set.
2025-05-16 17:32:20 +02:00
f2d8454158 Improve code with temporary variable retransmits 2025-05-16 17:28:53 +02:00
9dd93fd7af Improve code formatting 2025-05-16 17:28:15 +02:00
2 changed files with 80 additions and 23 deletions

View file

@ -166,8 +166,10 @@ def determine_result(options, json_data) -> Tuple[int, Optional[List[str]]]:
Args:
options: An object with threshold attributes used for evaluation.
Expected attributes include:
- rate_warn (int): Warning threshold for bits per second.
- rate_crit (int): Critical threshold for bits per second.
- rate_up_warn (int): Warning threshold for upstream rate in bits per second.
- rate_up_crit (int): Critical threshold for upstream rate in bits per second.
- rate_down_warn (int): Warning threshold for downstream rate in bits per second.
- rate_down_crit (int): Critical threshold for downstream rate in bits per second.
- retrans_warn (int): Warning threshold for retransmissions (TCP only).
- retrans_crit (int): Critical threshold for retransmissions (TCP only).
- udp (bool): Whether the test was run over UDP (retransmissions are ignored if True).
@ -188,19 +190,34 @@ def determine_result(options, json_data) -> Tuple[int, Optional[List[str]]]:
if "error" in json_data:
nagexit(3, json_data["error"])
if options.rate_crit and options.rate_warn:
if json_data["end"]["sum_sent"]["bits_per_second"] <= options.rate_crit:
json_end = json_data['end']
bps_avg_up = json_end['sum_sent']['bits_per_second'] if options.bidir or not options.downstream else None
bps_avg_down = json_end['sum_sent_bidir_reverse']['bits_per_second'] if options.bidir else \
json_data['end']['sum_sent']['bits_per_second'] if options.downstream else None
if bps_avg_up is not None:
if options.rate_up_crit and bps_avg_up <= options.rate_up_crit:
rc = max(rc, 2)
statuslines.append("transfer rate below critical threshold")
elif json_data["end"]["sum_sent"]["bits_per_second"] <= options.rate_warn:
statuslines.append("upstream rate below critical threshold")
elif options.rate_up_warn and bps_avg_up <= options.rate_up_warn:
rc = max(rc, 1)
statuslines.append("transfer rate below warning threshold")
statuslines.append("upstream rate below warning threshold")
if bps_avg_down is not None:
if options.rate_down_crit and bps_avg_down <= options.rate_down_crit:
rc = max(rc, 2)
statuslines.append("downpstream rate below critical threshold")
elif options.rate_down_warn and bps_avg_down <= options.rate_down_warn:
rc = max(rc, 1)
statuslines.append("downstream rate below warning threshold")
if not options.udp and options.retrans_crit and options.retrans_warn:
if json_data["end"]["sum_sent"]["retransmits"] >= options.retrans_crit:
retransmits = json_data["end"]["sum_sent"]["retransmits"]
if retransmits >= options.retrans_crit:
rc = max(rc, 2)
statuslines.append("retransmissions over critical threshold")
elif json_data["end"]["sum_sent"]["retransmits"] >= options.retrans_warn:
elif retransmits >= options.retrans_warn:
rc = max(rc, 1)
statuslines.append("retransmissions over warning threshold")
@ -287,8 +304,10 @@ def build_perfdata(options, json_data: dict) -> List[str]:
- bidir (bool): Whether the test was bidirectional.
- downstream (bool): Whether to use reverse (download) direction.
- udp (bool): Whether the test used UDP (retransmissions ignored).
- rate_warn (int): Warning threshold for throughput (in bits/sec).
- rate_crit (int): Critical threshold for throughput.
- rate_up_warn (int): Warning threshold for upstream rate in bits per second.
- rate_up_crit (int): Critical threshold for upstream rate in bits per second.
- rate_down_warn (int): Warning threshold for downstream rate in bits per second.
- rate_down_crit (int): Critical threshold for downstream rate in bits per second.
- retrans_warn (int): Warning threshold for retransmissions (TCP only).
- retrans_crit (int): Critical threshold for retransmissions.
json_data (dict): Parsed iperf3 output containing measurement results.
@ -305,19 +324,19 @@ def build_perfdata(options, json_data: dict) -> List[str]:
json_end = json_data['end']
bps_avg_up = json_end['sum_sent']['bits_per_second'] if options.bidir or not options.downstream else None
bps_avg_down = json_end['sum_sent_bidir_reverse']['bits_per_second'] if options.bidir else json_data[
'end']['sum_sent']['bits_per_second'] if options.downstream else None
bps_avg_down = json_end['sum_sent_bidir_reverse']['bits_per_second'] if options.bidir else \
json_data['end']['sum_sent']['bits_per_second'] if options.downstream else None
if not options.udp:
retrans_sum_up = json_end['sum_sent']['retransmits'] if options.bidir or not options.downstream else None
retrans_sum_down = json_end['sum_sent_bidir_reverse']['retransmits'] if options.bidir else json_data[
'end']['sum_sent']['retransmits'] if options.downstream else None
retrans_sum_down = json_end['sum_sent_bidir_reverse']['retransmits'] if options.bidir else \
json_data['end']['sum_sent']['retransmits'] if options.downstream else None
if bps_avg_up is not None:
perfdata.append(build_single_perfdata("bps_avg_up", bits_per_second(
bps_avg_up), options.rate_warn, options.rate_crit))
bps_avg_up), options.rate_up_warn, options.rate_up_crit))
if bps_avg_down is not None:
perfdata.append(build_single_perfdata("bps_avg_down", bits_per_second(
bps_avg_down), options.rate_warn, options.rate_crit))
bps_avg_down), options.rate_down_warn, options.rate_down_crit))
if not options.udp:
if retrans_sum_up is not None:
@ -327,10 +346,10 @@ def build_perfdata(options, json_data: dict) -> List[str]:
perfdata.append(build_single_perfdata("retrans_sum_down", packets(
retrans_sum_down), options.retrans_warn, options.retrans_crit))
perfdata.append(build_single_perfdata("local_cpu", percent(
json_end['cpu_utilization_percent']['host_total'])))
perfdata.append(build_single_perfdata("remote_cpu", percent(
json_end['cpu_utilization_percent']['remote_total'])))
perfdata.append(build_single_perfdata("local_cpu",
percent(json_end['cpu_utilization_percent']['host_total'])))
perfdata.append(build_single_perfdata("remote_cpu",
percent(json_end['cpu_utilization_percent']['remote_total'])))
return perfdata
def check_iperf3(options):
@ -350,8 +369,10 @@ def check_iperf3(options):
- bidir (bool): Whether the test should be bidirectional.
- downstream (bool): Whether the test should use reverse mode (server to client).
- udp (bool): Whether the test should use UDP instead of TCP.
- rate_warn (int): Warning threshold for throughput (in bits/sec).
- rate_crit (int): Critical threshold for throughput.
- rate_up_warn (int): Warning threshold for upstream rate in bits per second.
- rate_up_crit (int): Critical threshold for upstream rate in bits per second.
- rate_down_warn (int): Warning threshold for downstream rate in bits per second.
- rate_down_crit (int): Critical threshold for downstream rate in bits per second.
- retrans_warn (int): Warning threshold for retransmissions (TCP only).
- retrans_crit (int): Critical threshold for retransmissions (TCP only).
- bytes (str): Optional. Data to transfer (e.g., '10M').
@ -383,6 +404,18 @@ if __name__ == "__main__":
thres_opts.add_option("-c", "--rate-critical", dest="rate_crit",
type="int", metavar="BITS", action="store",
help="Defines the transfer rate's critical threshold")
thres_opts.add_option("--rate-up-warning", dest="rate_up_warn",
type="int", metavar="BITS", action="store",
help="Defines the upstream rate's warning threshold")
thres_opts.add_option("--rate-up-critical", dest="rate_up_crit",
type="int", metavar="BITS", action="store",
help="Defines the upstream rate's critical threshold")
thres_opts.add_option("--rate-down-warning", dest="rate_down_warn",
type="int", metavar="BITS", action="store",
help="Defines the downstream rate's warning threshold")
thres_opts.add_option("--rate-down-critical", dest="rate_down_crit",
type="int", metavar="BITS", action="store",
help="Defines the downstream rate's critical threshold")
# retransmits
thres_opts.add_option("-W", "--retransmit-warning", dest="retrans_warn",
@ -431,6 +464,14 @@ if __name__ == "__main__":
if not opts.remote or opts.time <= 0:
parser.print_help()
sys.exit(3)
if not opts.rate_up_warn:
opts.rate_up_warn = opts.rate_warn
if not opts.rate_down_warn:
opts.rate_down_warn = opts.rate_warn
if not opts.rate_up_crit:
opts.rate_up_crit = opts.rate_crit
if not opts.rate_down_crit:
opts.rate_down_crit = opts.rate_crit
check_iperf3(opts)

View file

@ -42,6 +42,22 @@ object CheckCommand "iperf3" {
description = "defines the transfer rate's critical threshold"
value = "$check_iperf3_rate_critical$"
}
"--rate-up-warning" = {
description = "defines the upstream rate's warning threshold"
value = "$check_iperf3_rate_up_warning$"
}
"--rate-up-critical" = {
description = "defines the upstream rate's critical threshold"
value = "$check_iperf3_rate_up_critical$"
}
"--rate-down-warning" = {
description = "defines the downstream rate's warning threshold"
value = "$check_iperf3_rate_down_warning$"
}
"--rate-down-critical" = {
description = "defines the downstream rate's critical threshold"
value = "$check_iperf3_rate_down_critical$"
}
"--retransmission-warning" = {
description = "defines the transfer retransmission's warning threshold"
value = "$check_iperf3_retransmission_warning$"