8000 Add PlatformCollector to collect information about the platform (#152) · pythonAI/client_python@91171a0 · GitHub
[go: up one dir, main page]

Skip to content 8000

Commit 91171a0

Browse files
mortenljbrian-brazil
authored andcommitted
Add PlatformCollector to collect information about the platform (prometheus#152)
Add PlatformCollector to collect information about the platform Python, machine and system information is collected once at startup, and exposed as labels on a metric with value 1.
1 parent c2e4bda commit 91171a0

File tree

4 files changed

+138
-0
lines changed

4 files changed

+138
-0
lines changed

README.md

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -206,6 +206,13 @@ other processes, for example:
206206
ProcessCollector(namespace='mydaemon', pid=lambda: open('/var/run/daemon.pid').read())
207207
```
208208

209+
8000 ### Platform Collector
210+
211+
The client also automatically exports some metadata about Python. If using Jython,
212+
metadata about the JVM in use is also included. This information is available as
213+
labels on the `python_info` metric. The value of the metric is 1, since it is the
214+
labels that carry information.
215+
209216
## Exporting
210217

211218
There are several options for exporting metrics.

prometheus_client/__init__.py

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@
33
from . import core
44
from . import exposition
55
from . import process_collector
6+
from . import platform_collector
67

78
__all__ = ['Counter', 'Gauge', 'Summary', 'Histogram']
89
# http://stackoverflow.com/questions/19913653/no-unicode-in-all-for-a-packages-init
@@ -31,6 +32,9 @@
3132
ProcessCollector = process_collector.ProcessCollector
3233
PROCESS_COLLECTOR = process_collector.PROCESS_COLLECTOR
3334

35+
PlatformCollector = platform_collector.PlatformCollector
36+
PLATFORM_COLLECTOR = platform_collector.PLATFORM_COLLECTOR
37+
3438

3539
if __name__ == '__main__':
3640
c = Counter('cc', 'A counter')
Lines changed: 58 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,58 @@
1+
#!/usr/bin/env python
2+
# -*- coding: utf-8
3+
from __future__ import unicode_literals
4+
5+
import platform as pf
6+
7+
from . import core
8+
9+
10+
class PlatformCollector(object):
11+
"""Collector for python platform information"""
12+
13+
def __init__(self, registry=core.REGISTRY, platform=None):
14+
self._platform = pf if platform is None else platform
15+
info = self._info()
16+
system = self._platform.system()
17+
if system == "Java":
18+
info.update(self._java())
19+
self._metrics = [
20+
self._add_metric("python_info", "Python platform information", info)
21+
]
22+
if registry:
23+
registry.register(self)
24+
25+
def collect(self):
26+
return self._metrics
27+
28+
@staticmethod
29+
def _add_metric(name, documentation, data):
30+
labels = data.keys()
31+
values = [data[k] for k in labels]
32+
g = core.GaugeMetricFamily(name, documentation, labels=labels)
33+
g.add_metric(values, 1)
34+
return g
35+
36+
def _info(self):
37+
major, minor, patchlevel = self._platform.python_version_tuple()
38+
return {
39+
"version": self._platform.python_version(),
40+
"implementation": self._platform.python_implementation(),
41+
"major": major,
42+
"minor": minor,
43+
"patchlevel": patchlevel
44+
}
45+
46+
def _java(self):
47+
java_version, _, vminfo, osinfo = self._platform.java_ver()
48+
vm_name, vm_release, vm_vendor = vminfo
49+
return {
50+
"jvm_version": java_version,
51+
"jvm_release": vm_release,
52+
"jvm_vendor": vm_vendor,
53+
"jvm_name": vm_name
54+
}
55+
56+
57+
PLATFORM_COLLECTOR = PlatformCollector()
58+
"""PlatformCollector in default Registry REGISTRY"""

tests/test_platform_collector.py

Lines changed: 69 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,69 @@
1+
from __future__ import unicode_literals
2+
3+
import unittest
4+
5+
from prometheus_client import CollectorRegistry, PlatformCollector
6+
7+
8+
class TestPlatformCollector(unittest.TestCase):
9+
def setUp(self):
10+
self.registry = CollectorRegistry()
11+
self.platform = _MockPlatform()
12+
13+
def test_python_info(self):
14+
PlatformCollector(registry=self.registry, platform=self.platform)
15+
self.assertLabels("python_info", {
16+
"version": "python_version",
17+
"implementation": "python_implementation",
18+
"major": "pvt_major",
19+
"minor": "pvt_minor",
20+
"patchlevel": "pvt_patchlevel"
21+
})
22+
23+
def test_system_info_java(self):
24+
self.platform._system = "Java"
25+
PlatformCollector(registry=self.registry, platform=self.platform)
26+
self.assertLabels("python_info", {
27+
"version": "python_version",
28+
"implementation": "python_implementation",
29+
"major": "pvt_major",
30+
"minor": "pvt_minor",
31+
"patchlevel": "pvt_patchlevel",
32+
"jvm_version": "jv_release",
33+
"jvm_release": "vm_release",
34+
"jvm_vendor": "vm_vendor",
35+
"jvm_name": "vm_name"
36+
})
37+
38+
def assertLabels(self, name, labels):
39+
for metric in self.registry.collect():
40+
for n, l, value in metric.samples:
41+
if n == name:
42+
assert l == labels
43+
return
44+
assert False
45+
46+
47+
class _MockPlatform(object):
48+
def __init__(self):
49+
self._system = "system"
50+
51+
def python_version_tuple(self):
52+
return "pvt_major", "pvt_minor", "pvt_patchlevel"
53+
54+
def python_version(self):
55+
return "python_version"
56+
57+
def python_implementation(self):
58+
return "python_implementation"
59+
60+
def system(self):
61+
return self._system
62+
63+
def java_ver(self):
64+
return (
65+
"jv_release",
66+
"jv_vendor",
67+
("vm_name", "vm_release", "vm_vendor"),
68+
("os_name", "os_version", "os_arch")
69+
)

0 commit comments

Comments
 (0)
0