Files

127 lines
2.7 KiB
Python

# -*- coding: utf-8 -*-
import json
import time
from collections import defaultdict, deque
import numpy as np
import paho.mqtt.client as mqtt
import matplotlib.pyplot as plt
MQTT_BROKER = "s960411f.ala.eu-central-1.emqxsl.com"
MQTT_PORT = 8883
MQTT_USER = "cma"
MQTT_PASS = "testcma"
TOPIC = "can/raw"
history = defaultdict(lambda: deque(maxlen=200))
# ----------------------------
# decoded time series
# ----------------------------
t_log = []
s1_log = []
s2_log = []
s3_log = []
# ----------------------------
# decode UVR67 frame (0x20D)
# ----------------------------
def decode_20d(payload):
s1 = payload[0] | (payload[1] << 8)
s2 = payload[2] | (payload[3] << 8)
s3 = payload[4] | (payload[5] << 8)
def conv(x):
if x == 0x3FFF or x == 0:
return None
return x / 10.0
return conv(s1), conv(s2), conv(s3)
# ----------------------------
# MQTT callback
# ----------------------------
def on_message(client, userdata, msg):
try:
data = json.loads(msg.payload.decode())
can_id = data["id"]
payload = data["data"]
timestamp = data.get("ts", time.time())
history[can_id].append((timestamp, payload))
# keep your debug print (but cleaner)
if can_id != 0x70D and can_id != 0x1CD:
print("ID:", hex(can_id), "Data:", payload)
# ----------------------------
# ONLY decode UVR67 temps here
# ----------------------------
if can_id == 0x20D:
s1, s2, s3 = decode_20d(payload)
t_log.append(timestamp)
s1_log.append(s1)
s2_log.append(s2)
s3_log.append(s3)
print(f"S1={s1}°C S2={s2}°C S3={s3}°C")
except Exception as e:
print("Parse error:", e)
# ----------------------------
# live plot
# ----------------------------
def plot_live():
plt.clf()
if len(t_log) < 2:
return
t0 = t_log[0]
t = [x - t0 for x in t_log]
plt.title("UVR67 Solar Temperatures")
plt.xlabel("Time (s)")
plt.ylabel("Temperature (°C)")
plt.plot(t, s1_log, label="S1 Collector")
plt.plot(t, s2_log, label="S2 Bottom tank")
plt.plot(t, s3_log, label="S3 Top tank")
plt.legend()
plt.grid(True)
plt.pause(0.1)
# ----------------------------
# MQTT setup
# ----------------------------
client = mqtt.Client()
client.username_pw_set(MQTT_USER, MQTT_PASS)
client.on_message = on_message
client.tls_set(ca_certs='./server-ca.crt')
client.connect(MQTT_BROKER, MQTT_PORT, 60)
client.subscribe(TOPIC, qos=1)
client.loop_start()
print("Listening for CAN frames...\n")
plt.ion()
# ----------------------------
# main loop
# ----------------------------
while True:
time.sleep(1)
plot_live()