Mercurial > code > home > repos > homeauto
annotate service/powerEagle/plugs/powermeter_exporter.py @ 1754:92999dfbf321 default tip
add shelly support
author | drewp@bigasterisk.com |
---|---|
date | Tue, 04 Jun 2024 13:03:43 -0700 |
parents | add4ce853035 |
children |
rev | line source |
---|---|
1754 | 1 import asyncio |
1749
4b29ce991e59
cloudfree plug sends mqtt metrics, which we export to victoriametrics
drewp@bigasterisk.com
parents:
diff
changeset
|
2 import json |
4b29ce991e59
cloudfree plug sends mqtt metrics, which we export to victoriametrics
drewp@bigasterisk.com
parents:
diff
changeset
|
3 import logging |
4b29ce991e59
cloudfree plug sends mqtt metrics, which we export to victoriametrics
drewp@bigasterisk.com
parents:
diff
changeset
|
4 |
4b29ce991e59
cloudfree plug sends mqtt metrics, which we export to victoriametrics
drewp@bigasterisk.com
parents:
diff
changeset
|
5 from aiomqtt import Client |
4b29ce991e59
cloudfree plug sends mqtt metrics, which we export to victoriametrics
drewp@bigasterisk.com
parents:
diff
changeset
|
6 from prometheus_client import Counter, Gauge |
4b29ce991e59
cloudfree plug sends mqtt metrics, which we export to victoriametrics
drewp@bigasterisk.com
parents:
diff
changeset
|
7 from rdferry import StarletteServer |
4b29ce991e59
cloudfree plug sends mqtt metrics, which we export to victoriametrics
drewp@bigasterisk.com
parents:
diff
changeset
|
8 |
4b29ce991e59
cloudfree plug sends mqtt metrics, which we export to victoriametrics
drewp@bigasterisk.com
parents:
diff
changeset
|
9 logging.basicConfig(level=logging.DEBUG) |
4b29ce991e59
cloudfree plug sends mqtt metrics, which we export to victoriametrics
drewp@bigasterisk.com
parents:
diff
changeset
|
10 log = logging.getLogger() |
4b29ce991e59
cloudfree plug sends mqtt metrics, which we export to victoriametrics
drewp@bigasterisk.com
parents:
diff
changeset
|
11 |
4b29ce991e59
cloudfree plug sends mqtt metrics, which we export to victoriametrics
drewp@bigasterisk.com
parents:
diff
changeset
|
12 powermeter_reports = Counter('powermeter_reports', 'mqtt messages from powermeter', labelnames=['sensor']) |
4b29ce991e59
cloudfree plug sends mqtt metrics, which we export to victoriametrics
drewp@bigasterisk.com
parents:
diff
changeset
|
13 metrics = {} |
1754 | 14 for metric_name in [ |
15 ('powermeter_w'), | |
16 ('powermeter_apparent_power_va'), | |
17 ('powermeter_reactive_power_var'), | |
18 ('powermeter_factor'), | |
19 ('powermeter_voltage_v'), | |
20 ('powermeter_current_a'), | |
21 ('powermeter_temp_c'), | |
22 ]: | |
23 metrics[metric_name] = Gauge(metric_name, documentation='', labelnames=['sensor']) | |
1749
4b29ce991e59
cloudfree plug sends mqtt metrics, which we export to victoriametrics
drewp@bigasterisk.com
parents:
diff
changeset
|
24 |
4b29ce991e59
cloudfree plug sends mqtt metrics, which we export to victoriametrics
drewp@bigasterisk.com
parents:
diff
changeset
|
25 |
1754 | 26 def sonoff(sensor_label, msg): |
27 energy = msg['ENERGY'] | |
28 metrics['powermeter_w'].labels(sensor=sensor_label).set(energy['Power']) | |
29 metrics['powermeter_apparent_power_va'].labels(sensor=sensor_label).set(energy['ApparentPower']) | |
30 metrics['powermeter_reactive_power_var'].labels(sensor=sensor_label).set(energy['ReactivePower']) | |
31 metrics['powermeter_factor'].labels(sensor=sensor_label).set(energy['Factor']) | |
32 metrics['powermeter_voltage_v'].labels(sensor=sensor_label).set(energy['Voltage']) | |
33 metrics['powermeter_current_a'].labels(sensor=sensor_label).set(energy['Current']) | |
34 | |
35 | |
36 def shelly(sensor_label, msg): | |
37 metrics['powermeter_w'].labels(sensor=sensor_label).set(msg['apower']) | |
38 metrics['powermeter_voltage_v'].labels(sensor=sensor_label).set(msg['voltage']) | |
39 metrics['powermeter_current_a'].labels(sensor=sensor_label).set(msg['current']) | |
40 metrics['powermeter_apparent_power_va'].labels(sensor=sensor_label).set(msg['apower']) | |
41 metrics['powermeter_temp_c'].labels(sensor=sensor_label).set(msg['temperature']['tC']) | |
42 | |
43 | |
44 async def subscribe_to_sensor(topic, sensor_label, onMsg): | |
1749
4b29ce991e59
cloudfree plug sends mqtt metrics, which we export to victoriametrics
drewp@bigasterisk.com
parents:
diff
changeset
|
45 async with Client("mqtt2") as client: |
4b29ce991e59
cloudfree plug sends mqtt metrics, which we export to victoriametrics
drewp@bigasterisk.com
parents:
diff
changeset
|
46 await client.subscribe(topic) |
4b29ce991e59
cloudfree plug sends mqtt metrics, which we export to victoriametrics
drewp@bigasterisk.com
parents:
diff
changeset
|
47 async for message in client.messages: |
1754 | 48 try: |
49 msg = json.loads(message.payload) | |
50 onMsg(sensor_label, msg) | |
51 powermeter_reports.labels(sensor=sensor_label).inc() | |
52 except Exception: | |
53 log.error(f'{topic=} {sensor_label=}', exc_info=True) | |
54 | |
55 | |
56 async def request_shelly_statuses(topic, period=10): | |
57 async with Client("mqtt2") as client: | |
58 while True: | |
59 # todo: this adds lag- better to publish upon a /metrics request | |
60 # then block until all the statuses come in. | |
61 await client.publish(topic, 'status_update') | |
62 await asyncio.sleep(period) | |
1749
4b29ce991e59
cloudfree plug sends mqtt metrics, which we export to victoriametrics
drewp@bigasterisk.com
parents:
diff
changeset
|
63 |
4b29ce991e59
cloudfree plug sends mqtt metrics, which we export to victoriametrics
drewp@bigasterisk.com
parents:
diff
changeset
|
64 |
4b29ce991e59
cloudfree plug sends mqtt metrics, which we export to victoriametrics
drewp@bigasterisk.com
parents:
diff
changeset
|
65 server = StarletteServer() |
4b29ce991e59
cloudfree plug sends mqtt metrics, which we export to victoriametrics
drewp@bigasterisk.com
parents:
diff
changeset
|
66 server.serve(startup_tasks=[ |
1754 | 67 subscribe_to_sensor( topic="tele/st-wall-power/SENSOR", sensor_label='st_wall', onMsg=sonoff), |
68 subscribe_to_sensor( topic="tele/ki-fridge/SENSOR", sensor_label='ki_fridge', onMsg=sonoff), | |
69 subscribe_to_sensor( topic="tt-console-power/SENSOR", sensor_label='tt_console', onMsg=sonoff), | |
70 request_shelly_statuses(topic="ga-washer-power/command/switch:0"), | |
71 subscribe_to_sensor( topic="ga-washer-power/status/switch:0", sensor_label='ga_washer', onMsg=shelly), | |
72 request_shelly_statuses(topic="do-r-power/command/switch:0"), | |
73 subscribe_to_sensor( topic="do-r-power/status/switch:0", sensor_label='do_r', onMsg=shelly), | |
74 request_shelly_statuses(topic="ws-atx-power/command/switch:0"), | |
75 subscribe_to_sensor( topic="ws-atx-power/status/switch:0", sensor_label='ws_atx', onMsg=shelly), | |
76 ]) # yapf: disable |