Page MenuHomeDevCentral

D2602.id6565.diff
No OneTemporary

D2602.id6565.diff

diff --git a/README.md b/README.md
--- a/README.md
+++ b/README.md
@@ -63,6 +63,43 @@
You can also create a check calling `check_http_200` without argument,
and it will test every site.
+### check_container_present
+
+#### Run the check
+
+With argument, check if the specified Docker container is running:
+`check_container_present foo`
+
+Without argument, compare the list of containers present with
+the expected one.
+
+The configuration is only required if you use it without argument.
+
+#### Available check types
+
+* check_docker_container: a list of expected containers
+
+#### Configuration example
+
+```yaml
+checks:
+ check_docker_container:
+ - foo
+ - bar
+```
+
+#### Requirements
+
+A Docker engine with CLI restructured, ie Docker 1.13+, is needed:
+ * To list the containers it uses `docker container ls`.
+ * To get more info on a container down,
+ it uses `docker container inspect`.
+
+#### Not features
+
+This check isn't intended to detect containers
+run with other engines like `systemd-nspawn`.
+
## Return values of checks
The checks use the standard Nagios/NRPE exit codes:
diff --git a/bin/check_container_present b/bin/check_container_present
new file mode 100755
--- /dev/null
+++ b/bin/check_container_present
@@ -0,0 +1,73 @@
+#!/usr/bin/env python3
+
+# -------------------------------------------------------------
+# Platform checks - Containers
+# - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
+# Project: Nasqueron
+# Description: Check if a container is present
+# License: BSD-2-Clause
+# -------------------------------------------------------------
+
+
+import sys
+
+from platformchecks import exitcode
+from platformchecks.checks import DockerContainerCheck
+from platformchecks.config import parse_config
+
+
+# -------------------------------------------------------------
+# Configuration
+# - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
+
+
+def get_containers():
+ return parse_config().get("checks", {}).get("check_containers", [])
+
+
+# -------------------------------------------------------------
+# Application entry point
+# - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
+
+
+def initialize_check_or_die():
+ check = DockerContainerCheck()
+ if not check.initialize():
+ print("UNKNOWN", check.error, file=sys.stderr)
+ sys.exit(exitcode.UNKNOWN)
+
+ return check
+
+
+def run_all(check, containers):
+ success = True
+ messages = []
+
+ for container in containers:
+ container_success, message = check.perform(container)
+
+ success &= container_success
+ messages.append(message)
+
+ print("\n".join(messages))
+ return exitcode.ok_or_critical(success)
+
+
+def run(check, container):
+ success, message = check.perform(container)
+
+ print(message)
+ return exitcode.ok_or_critical(success)
+
+
+if __name__ == "__main__":
+ argc = len(sys.argv)
+
+ container_check = initialize_check_or_die()
+
+ if argc < 2:
+ exitCode = run_all(container_check, get_containers())
+ else:
+ exitCode = run(container_check, sys.argv[1])
+
+ sys.exit(exitCode)
diff --git a/setup.cfg b/setup.cfg
--- a/setup.cfg
+++ b/setup.cfg
@@ -1,6 +1,6 @@
[metadata]
name = platform-checks
-version = 0.1.1
+version = 0.1.2
author = Sébastien Santoro
author_email = dereckson@espace-win.org
description = Platform checks NRPE / Nagios
diff --git a/src/platformchecks/checks/__init__.py b/src/platformchecks/checks/__init__.py
--- a/src/platformchecks/checks/__init__.py
+++ b/src/platformchecks/checks/__init__.py
@@ -1 +1,2 @@
from .http import HttpCheck
+from .docker import DockerContainerCheck
diff --git a/src/platformchecks/checks/docker.py b/src/platformchecks/checks/docker.py
new file mode 100644
--- /dev/null
+++ b/src/platformchecks/checks/docker.py
@@ -0,0 +1,65 @@
+# -------------------------------------------------------------
+# Platform checks
+# - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
+# Project: Nasqueron
+# Description: Check if a container is up
+# License: BSD-2-Clause
+# -------------------------------------------------------------
+
+
+import json
+import subprocess
+
+
+def inspect_container(container):
+ p = subprocess.run(["docker", "container", "inspect", container], capture_output=True)
+
+ if p.returncode > 0:
+ raise ValueError(p.stderr.decode().strip())
+
+ return json.loads(p.stdout)[0]
+
+
+def describe_state(state):
+ return f"{state['Status']} ({state['ExitCode']}) {state['FinishedAt']}"
+
+
+class DockerContainerCheck:
+ def __init__(self):
+ self.containers = []
+
+ self.error = ""
+
+ def initialize(self):
+ p = subprocess.run("docker container ls | awk '(NR>1) {print $NF}'", shell=True, capture_output=True)
+
+ if p.stderr:
+ self.error = p.stderr.decode().strip()
+ return False
+
+ self.containers = p.stdout.decode().strip().split("\n")
+ return True
+
+ def perform(self, container):
+ return self.has(container), self.build_message(container)
+
+ def has(self, container):
+ return container in self.containers
+
+ def build_message(self, container):
+ if self.has(container):
+ return f"{container} UP"
+
+ message = f"{container} DOWN"
+
+ try:
+ # Returns container state lik
+ state = inspect_container(container)["State"]
+ message += " " + describe_state(state)
+ except ValueError as ex:
+ # Detect cases when the container doesn't exist
+ message += " " + str(ex)
+ except subprocess.CalledProcessError:
+ pass
+
+ return message
diff --git a/src/platformchecks/exitcode.py b/src/platformchecks/exitcode.py
--- a/src/platformchecks/exitcode.py
+++ b/src/platformchecks/exitcode.py
@@ -11,3 +11,11 @@
WARNING = 1
CRITICAL = 2
UNKNOWN = 3
+
+
+def ok_or_critical(is_successful):
+ return OK if is_successful else CRITICAL
+
+
+def ok_or_warning(is_successful):
+ return OK if is_successful else WARNING

File Metadata

Mime Type
text/plain
Expires
Sun, Nov 24, 08:18 (12 h, 27 m)
Storage Engine
blob
Storage Format
Raw Data
Storage Handle
2259826
Default Alt Text
D2602.id6565.diff (6 KB)

Event Timeline