diff --git a/check-netbox-machine-state.py b/check-netbox-machine-state.py index e52a6ba0..6b4dbbca 100755 --- a/check-netbox-machine-state.py +++ b/check-netbox-machine-state.py @@ -14,25 +14,30 @@ import os import sys from functools import reduce +from typing import TYPE_CHECKING import pynetbox -from sh import ErrorReturnCode, ping +import sh + +if TYPE_CHECKING: + from pynetbox.models import dcim, ipam ping_args = {"-c1", "-W1"} +_ping = sh.Command("ping") -def check_ping(destination: str | pynetbox.models.ipam.IpAddresses) -> bool: +def check_ping(destination: str | ipam.IpAddresses) -> bool: """Signal (True) that a machine is reachable when it should not be.""" destination = str(destination).split("/")[0] try: - _ = ping(destination, *ping_args) - except ErrorReturnCode: + _ = _ping(destination, *ping_args) + except sh.ErrorReturnCode: return False log.warning("Ping to destination %s was successfull, this will fail the script!", destination) return True -def check_machine(machine: pynetbox.models.dcim.Devices) -> bool: +def check_machine(machine: dcim.Devices) -> bool: """Detect reachability across all known addresses of a machine to avoid false negatives.""" attributes_to_check = {"oob_ip", "primary_ip", "primary_ip4", "primary_ip6"} machine_attributes = [getattr(machine, attr) for attr in attributes_to_check if getattr(machine, attr) is not None] @@ -58,8 +63,8 @@ def main(args: argparse.Namespace) -> int: def loglevel_to_int(loglevel: str) -> int: """Allow LOGLEVEL env var to set the default verbosity as if the user had passed that many -v flags.""" loglevel_step = logging.CRITICAL - logging.ERROR - max_loglevel = logging.CRITICAL / loglevel_step - return max_loglevel - int(getattr(logging, loglevel.upper(), None) / loglevel_step) + max_loglevel = logging.CRITICAL // loglevel_step + return max_loglevel - int(getattr(logging, loglevel.upper(), logging.ERROR) // loglevel_step) log = logging.getLogger(sys.argv[0] if __name__ == "__main__" else __name__) diff --git a/check-netbox-unused-machine-power.py b/check-netbox-unused-machine-power.py index 230840e2..c7c546c6 100755 --- a/check-netbox-unused-machine-power.py +++ b/check-netbox-unused-machine-power.py @@ -14,6 +14,7 @@ import netsnmp import pynetbox +from pynetbox.models import dcim BACHMANN_RELAY_ON = 19 # Bachmann PDU relay status value for "on" @@ -73,14 +74,14 @@ def green(s: str) -> str: return f"\x1b[32m{s}\x1b[0m" -def print_device(device: pynetbox.models.dcim.Devices, dev_pdu_power: dict, watts: int) -> None: +def print_device(device: dcim.Devices, dev_pdu_power: dict, watts: int) -> None: """Report device power consumption per PDU outlet for human review.""" s = " " if verbose else "" - dev_pdu_power = " ".join([f"{h}:{green(p) if s else red(p)}={w}W" for (h, p), (w, s) in dev_pdu_power.items()]) - print(f"{s}{device.name} status={device.status.value} {dev_pdu_power} ∑{watts}W") + pdu_power = " ".join([f"{h}:{green(p) if s else red(p)}={w}W" for (h, p), (w, s) in dev_pdu_power.items()]) + print(f"{s}{device.name} status={device.status.value} {pdu_power} ∑{watts}W") -def print_no_connection(device: pynetbox.models.dcim.Devices) -> None: +def print_no_connection(device: dcim.Devices) -> None: """Warn that power consumption for this device cannot be verified.""" if verbose: print(f"No connection for {device.name} ({device.display_url})", file=sys.stderr) diff --git a/pyproject.toml b/pyproject.toml index a7445507..a859de7d 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -138,6 +138,9 @@ max-complexity = 9 # Enable reformatting of code snippets in docstrings. docstring-code-format = true +[tool.ty.analysis] +allowed-unresolved-imports = ["netsnmp"] + [tool.ruff.lint.flake8-copyright] author = "SUSE LLC" notice-rgx = "Copyright"