arendst / Tasmota

Alternative firmware for ESP8266 and ESP32 based devices with easy configuration using webUI, OTA updates, automation using timers or rules, expandability and entirely local control over MQTT, HTTP, Serial or KNX. Full documentation at
https://tasmota.github.io/docs
GNU General Public License v3.0
22.16k stars 4.8k forks source link

Sum / integrate measured power over MQTT reportting time: Increase resolution of "period" field in MQTT SENSOR message #9101

Closed JsBergbau closed 4 years ago

JsBergbau commented 4 years ago

Have you looked for this feature in other issues and in the docs?
Yes Is your feature request related to a problem? Please describe.
A clear and concise description of what the problem is.

I have a Blitzwolf SHP6 smart socket measuring a induction hob. This device has a speciality. When using on low power mode it gives all power (2 kW) für a few seconds or less than a second. Measring this kind of load is quite tricky. To get exakt values I've used a "ELV Energy Master" to measure the exakt energy consumption, giving a reading of 0.972 kWh grafik In web interface the energy cosumption is with 1.08 kWh quite exact grafik

I've also compared with a TP-Link HS110 which gives 0,98 kWh used energy and thus is quite exact grafik

Every 10 seconds the current powervalue is sent via MQTT and stored in influxdb and evaluated with Grafana. This evaluation is not 100 % exact compared to the internal values, but still exact enough. For HS100 internally showing 0,98 kWh it gives 0.95 kWh in Grafana, which is only 3 % difference. Exact enough.

grafik

Now to the Tasmota / Blitzwolf device. Internally showing 1.08 kWh it gives in Grafana only 0.78 kWh. Thats almost 28 % difference to the measured value by the SHP6 device.

grafik

Please note that at about 12:51 Tasmota reports only 8 Watts while HS110 reports still about 1 kW till 12:59. That is because at that time induction hop was at a very low power setting, causing it to use full power only for a few seconds. And probably it didn't heat / use its full power when Tasmota reported the current value via MQTT and thus there is a huge difference in reported energy consumption and real energy consumption.

Describe the solution you'd like
My measurement period is 10 seconds, so every 10 seconds Tasmota reports the current power via MQTT. Suppose following load profile where Tasmota reports at second 10 its current value. 0-1s: 2000W 1-2s: 2000W 2-9s: 0W Tasmota would report 0 Watt via MQTT, however I'd like to report it the average / integrated power over the measurement periond. Here 2000 Ws + 2000 Ws = 4000 Ws 4000 Ws / 10 s = 400 W. So Tasmota should report here a power of 400 Watt. When integrating that value in Grafana you get the 4000 Ws as used energy.

Describe alternatives you've considered
Currently none. If you have other solutions for that problem, I'd like to hear.

Additional context
Of course this load profile is very special, but consider the standard report interval of 300 seconds. When switching on a heavy load 10 seconds before MQTT report, than too much power used is reported.

If it is helpful for you I can export the influxdb values as csv. This was not the first time I've encoutered this problem. This was just the first time where I documented it very well. I've already had the vice versa case, where too much power was reported via MQTT. Then report period was in sync with maximum power draw of the induction hob.

(Please, remember to close the issue when the problem has been addressed)

sfromis commented 4 years ago

If you want the energy consumption for each TelePeriod interval, look for the "Period" field in the JSON. How you plot this, is up to the tool and you. If you want reporting when energy usage jumps up/down, look for the PowerDelta command.

JsBergbau commented 4 years ago

Hi sfromis,

thanks for your help. The resolution of the period field is too low to use it. It seems to be Wh. On a 10 second period with 100 W load you get 0,27 Wh which results in a report of 0. One device drawing currently 388 Watt reports "1" in the period field however it would be 1,077777 Wh in the 10 seconds period. So perhaps the featurerequest should be changed to increase resolution of "period" value in MQTT message? The Powerdelta would produce too much messages. grafik Thats the curve of a refridgerator, value changes every measurement.

But even with a modern device with a inverter there is no constant power draw. So using PowerDelta would produce too much messages or would be too inaccurate. So increasing resolution of "period" field would be best solution. grafik

sfromis commented 4 years ago

If you want decimals on the Period field, use the WattRes command.

ascillato2 commented 4 years ago

Closing this issue as it has been answered.


Support Information

See Docs for more information. See Chat for more user experience. See Community for forum. See Code of Conduct

cod-xio commented 2 years ago

Hallo JsBergbau

Mit welche Tasmota einstellungen hast geschafft Blitzwolf in Grafana zum Visualisieren ?

Lg.

JsBergbau commented 2 years ago

Hallo cod-xio, ich nutze die Werte, die Tasmota via MQTT zur Verfügung stellt. Diese werden in Node-RED für InfluxDB aufbereitet, dort abgespeichert und in Grafana angezeigt.

cod-xio commented 2 years ago

Danke , Ich bin jezt drauf gekommen das ab v10.0 ist möglich direkt in InfluxDB zum speichern!

tkt2208 commented 2 years ago

ich nutze die Werte, die Tasmota via MQTT zur Verfügung stellt. Diese werden in Node-RED für InfluxDB aufbereitet, dort abgespeichert und in Grafana angezeigt.

Hi, kannst du mal bitte den Node-Red Flow zum aufbereiten der MQTT Daten zur Verfügung stellen? Ich bekomme das irgendwie selbst nicht hin. Danke

MfG der tkt

JsBergbau commented 2 years ago

Hi @tkt2208 sorry für die späte Antwort, habe die Nachricht übersehen. Hier der Flow. Danach einfach in die Influx-DB schreiben. Der Flow sorgt für gleichmäßige Zeitstempel, sodass dier Influx-DB RLE Kompression für Zeitstempel verwendet werden kann, außerdem wird noch der Bonobo Algorithmus https://github.com/JsBergbau/Bonobo-Timeseries-Data-Compression verwendet um die Daten möglichst platzsparend in Influx zu speichern, sodass die Daten besonders effizient komprimiert werden.

[
    {
        "id": "b8a9db87.6dc3e8",
        "type": "mqtt in",
        "z": "e2a29bb2.0ee9f",
        "name": "",
        "topic": "tele/+/SENSOR",
        "qos": "0",
        "datatype": "json",
        "broker": "977a2a5a.f1bfa8",
        "inputs": 0,
        "x": 120,
        "y": 620,
        "wires": [
            [
                "55d1db6a.d70f54"
            ]
        ]
    },
    {
        "id": "55d1db6a.d70f54",
        "type": "change",
        "z": "e2a29bb2.0ee9f",
        "name": "Extrahiere Sensorname, Zeit, Spannung und Leistung",
        "rules": [
            {
                "t": "change",
                "p": "topic",
                "pt": "msg",
                "from": "tele/(.*?)/SENSOR",
                "fromt": "re",
                "to": "$1",
                "tot": "str"
            },
            {
                "t": "set",
                "p": "payload",
                "pt": "msg",
                "to": "{\t    \"Leistung\" : **.Power,\t    \"Spannung\" : **.Voltage,\t    \"Zeit\" : **.Time\t}",
                "tot": "jsonata"
            }
        ],
        "action": "",
        "property": "",
        "from": "",
        "to": "",
        "reg": false,
        "x": 510,
        "y": 620,
        "wires": [
            [
                "4727695d.b294b8",
                "6c059d80.251dd4",
                "4d0f07b3.fdb418",
                "1cf39e6d.4b6ab2",
                "df7849f5.57a658",
                "f4b5be89.01a1d",
                "a01a255b.407418"
            ]
        ]
    },
    {
        "id": "f4b5be89.01a1d",
        "type": "function",
        "z": "e2a29bb2.0ee9f",
        "name": "Werte für bessere Speicherbarkeit formen",
        "func": "wert = msg.payload;\n\nfunction getFraction(zahl)\n{\n    switch(zahl)\n     {\n        case 0:\n             zahl = 0;\n             break;\n        case 0.1:\n            zahl = 0.125;\n            break;\n        case 0.2:\n            zahl = 0.1875;\n            break;\n        case 0.3:\n            zahl = 0.3125;\n            break;\n        case 0.4:\n            zahl = 0.4375;\n            break;\n        case 0.5:\n            zahl = 0.5;\n            break;\n        case 0.6:\n            zahl = 0.625;\n            break;\n        case 0.7:\n            zahl = 0.6875;\n            break;\n        case 0.8:\n            zahl = 0.8125;\n            break;\n        case 0.9:\n            zahl = 0.9375;\n            break;\n     }\n     return zahl;\n}\n\nfunction ZahlFormen(wert)\n{\n\n    fraction = wert - Math.trunc(wert);\n    \n    fraction = Math.abs(Math.round(fraction * 10) / 10)\n    \n    if (wert > 0)\n    {\n        wert = wert - fraction;\n        wert += getFraction(fraction)\n    }\n    else\n    {\n        wert = wert + fraction\n        wert -= getFraction(fraction)\n    }\n    return wert;\n}\n\nmsg.payload.Leistung = ZahlFormen(msg.payload.Leistung);\nmsg.payload.Spannung = ZahlFormen(msg.payload.Spannung);\n\nreturn msg;",
        "outputs": 1,
        "noerr": 0,
        "x": 1180,
        "y": 620,
        "wires": [
            [
                "2bb5a780.b0a108",
                "4ad1c91850be3486"
            ]
        ]
    },
    {
        "id": "2bb5a780.b0a108",
        "type": "change",
        "z": "e2a29bb2.0ee9f",
        "name": "Aufbereitung für Influx",
        "rules": [
            {
                "t": "set",
                "p": "measurement",
                "pt": "msg",
                "to": "TPLinks",
                "tot": "str"
            },
            {
                "t": "set",
                "p": "payload.time",
                "pt": "msg",
                "to": "($floor($millis()/10000))*10+10",
                "tot": "jsonata"
            },
            {
                "t": "set",
                "p": "payload",
                "pt": "msg",
                "to": "[\t    $.payload,\t    {\t        \"TPLink\" : $.topic\t    }\t    \t]",
                "tot": "jsonata"
            },
            {
                "t": "set",
                "p": "precision",
                "pt": "msg",
                "to": "s",
                "tot": "str"
            }
        ],
        "action": "",
        "property": "",
        "from": "",
        "to": "",
        "reg": false,
        "x": 1520,
        "y": 620,
        "wires": [
            [
                "d49bd0e1.84909",
                "90103a8.d7dde48"
            ]
        ]
    },
    {
        "id": "977a2a5a.f1bfa8",
        "type": "mqtt-broker",
        "name": "",
        "broker": "127.0.0.1",
        "port": "1883",
        "clientid": "",
        "autoConnect": true,
        "usetls": false,
        "protocolVersion": "4",
        "keepalive": "60",
        "cleansession": true,
        "birthTopic": "",
        "birthQos": "0",
        "birthPayload": "",
        "birthMsg": {},
        "closeTopic": "",
        "closeQos": "0",
        "closePayload": "",
        "closeMsg": {},
        "willTopic": "",
        "willQos": "0",
        "willPayload": "",
        "willMsg": {},
        "sessionExpiry": ""
    }
]