NEWS
Werte aus Influxdb Abfrage
-
Hallo zusammen,
ich bräuchte mal bitte eine grundsätzliche Hilfe zum Verständnis der aus der Influxdb Abfrage zurückgemeldeten werten. Besser gesagt der Weiterverarbeitung. Ich mache eine Query Abfrage und bekomme ein JSON Objekt zurück, wie auch in diversen Beispielen hier gezeigt. Die Werte bekomme ich auch korrekt zurückgemeldet, nur wie kann ich auf die einzelnen Werte zugreifen, das sollte doch auch ohne parsen gehen..?sendTo('influxdb.0', 'query', 'select "value" from "alias.0.Kueche.Kühlschrank.ENERGY_COUNTER" LIMIT 3', async function (result) { for (var i = 0; i < result.result.length; i++) { console.log('Rows: ' + JSON.stringify(result.result[i])); console.log(result.result[i]); } console.log(result.result.length) });
Als Beispiel... Laut Suche sollte die Schleife jeden Datensatz durchlaufen, allerdings bekomme ich immer nur einen Datensatz zurück, so dass die Schleife auch nur einmal durchläuft. Und weiter.. selbst wenn ich über den Select Befehl nur einen Datensatz auslese (MAX("VALUE")), kann ich nicht auf den Wert zugreifen, sonder bekomme entweder undefined oder das ganze JSON Objekt.
Hier das Debug Fenster:
12:02:10.791 info javascript.0 (1636) script.js.common.TestInflux: Rows: [{"value":13419.4,"ts":1660382651743},{"value":13436.8,"ts":1660383052585},{"value":13437.4,"ts":1660383172597}] 12:02:10.792 info javascript.0 (1636) script.js.common.TestInflux: [{'value':13419.4,'ts':1660382651743},{'value':13436.8,'ts':1660383052585},{'value':13437.4,'ts':1660383172597}] 12:02:10.793 info javascript.0 (1636) script.js.common.TestInflux: undefined 12:02:10.793 info javascript.0 (1636) script.js.common.TestInflux: 1
Vielen Dank vorab!
-
@frederik-buss sagte: Hier das Debug Fenster:
Wenn ich die Log-Ausgabe richtig interpretiere, müsste die Auswertung so aussehen:
for (var i = 0; i < result.result[0].length; i++) { console.log('Rows: ' + JSON.stringify(result.result[0][i])); console.log(result.result[0][i]); } console.log(result.result[0].length)
-
@paul53 Yep, das wars. Hätte ich auch selbst drauf kommen können, aber mit JSON stehe ich (noch) bissl auf Kriegsfuss.. Vielen Dank!
Was mich dennoch wundert, warum sind sämtliche anderen Beispiele die ich gefunden habe ohne den Zusatz, sprich nicht verschachtelt? Wurde da was im Influxdb Adapter geändert oder liegt das eher an einer vermurksten Konfiguration meinerseits? -
@frederik-buss sagte: Wurde da was im Influxdb Adapter geändert
Ich verwende Influxdb nicht, kenne mich also damit nicht aus.
-
Falls es jemanden interessiert: Ich habe ein Miniscript erstellt, welches jeden Tag um Mitternacht den Gesamtverbrauch der letzten 24 Stunden des Kühlschranks ermittelt und in eine Variable schreibt. Der Verbrauch wird mittels HMIP-PSM energy_counter in die Influx DB geschrieben. Fallstricke für Anfänger wie mich sind: Datum richtig in die Abfrage einbeziehen (Die Nullen für Nanosekunden haben seine Zeit gebraucht, bis ich dahinter kam) und dass die Query Abfrage bei Select "value" und Select max("value") unterschiedliche Felddefinitionen zurück gibt : result.result[0][0].value vs. result.result[0][0].max. Warum das Ergebnis hier so verschachtelt ist und bei allen anderen Beispielen aus der Suche verstehe ich immer noch nicht. Auch warum die Zeitumrechnerei so umständlich ist (Alle kürzeren Wege sind gescheitert) um auf den vorherigen Tag zu kommen ist mir rätselhaft. Vielleicht kann hier jemand Licht ins Dunkle bringen.
Jedenfalls funktioniert es so:var t, tgestern, tmax, tmin; t = (new Date().getTime()); tgestern = new Date(t); tgestern.setDate(tgestern.getDate() - 1); tgestern = tgestern.getTime(); schedule('{"time":{"exactTime":true,"start":"00:15"},"period":{"days":1}}', async function () { sendTo('influxdb.0', 'query', 'select max("value") from "alias.0.Kueche.Kühlschrank.ENERGY_COUNTER" where time > ' + tgestern + '000000', function (result) { tmax = result.result[0][0].max; }); sendTo('influxdb.0', 'query', 'select min("value") from "alias.0.Kueche.Kühlschrank.ENERGY_COUNTER" where time > ' + tgestern + '000000', function (result) { tmin = result.result[0][0].min; setState("0_userdata.0.Energie_Kuehlschrank24"/*Energie_Kuehlschrank24*/, tmax - tmin); console.log(getState("0_userdata.0.Energie_Kuehlschrank24").val); }); });
-
@frederik-buss
Das sieht sehr interessant aus. Welche Influxdb Version nutzt du? Kann die 2.0 auch mit SQL abgefragt werden? -
@frederik-buss sagte in Werte aus Influxdb Abfrage:
0].min; setState("0_userdata.0.Energie_Kuehlschrank24"/Energie_Kuehlschrank24/, tmax - tmin); console.log(getState("0_userdata.0.Energie_Kuehlschrank24").val);
An sowas ähnliches bin ich gerade auch dran. Ich baue mir die Querys mit Grafana zusammen, das geht am einfachsten und schnellsten.
Für die Verbräuche pro Tag benötigt man einen hochlaufenden Zähler. Die Query macht dann direkt die Differenz.Ich wollte das ganze dann noch soweit ausbauen, dass mir nicht nur vergangene Tage erzeugt werden, sondern auch Wochen, Monate, Quartale usw.
im Prinzip könnte man so eine komplette Statistik zusammenbauen von etlichen Geräten.Vielleicht hilft der anfängliche Code schon jemanden, aktuell leider wenig Zeit.
var Geraete = [ "0_userdata.0.Huawei.Meter.Energy_self_consumed", "0_userdata.0.Huawei.Meter.Energy_Export", "0_userdata.0.Huawei.Meter.Energy_Import", "0_userdata.0.Huawei.Meter.Energy_consumed", "zigbee.0.a4c138bf631f71bf.energy" ] var Timezone = "tz('Europe/Berlin')" var Data; var i; var reihen = 7 var past = "d" var Spaltenname; var Data_Column = {}; var sql_string Datenabfrage() async function Datenabfrage() { for (var i_index in Geraete) { i = Geraete[i_index]; sql_string = 'SELECT spread("value") FROM "' + i + '" WHERE time > now() - ' + reihen + '' + past + ' GROUP BY time(1d) fill(null) ORDER BY time DESC ' + Timezone + '' const result = await sendToAsync('influxdb.0', 'query', sql_string); Data = result[0] log(getObject(i).common.name) var i_Daten for (i_Daten in Data) { var Verbrauch = Data[i_Daten].spread var Time = Data[i_Daten].ts // Verbrauchswerte schreiben if (!await existsStateAsync('0_userdata.0.Stat.' + i + '.' + i_Daten + '.Verbrauch')) { await createStateAsync('0_userdata.0.Stat.' + i + '.' + i_Daten + '.Verbrauch', '', { name: Spaltenname, type: 'mixed', role: 'state' }); } await setStateAsync('0_userdata.0.Stat.' + i + '.' + i_Daten + '.Verbrauch', Verbrauch); // Timestamp schreiben if (!await existsStateAsync('0_userdata.0.Stat.' + i + '.' + i_Daten + '.Time')) { await createStateAsync('0_userdata.0.Stat.' + i + '.' + i_Daten + '.Time', '', { name: Spaltenname, type: 'mixed', role: 'state' }); } await setStateAsync('0_userdata.0.Stat.' + i + '.' + i_Daten + '.Time', formatDate(getDateObject(Time), "DD.MM.YY")); } } } /********************************SQL Sendto Wrapper ***************** */ function sendToAsync(instance, command, arg) { return new Promise((resolve, reject) => { sendTo(instance, command, arg, (result) => { if (result.error) { reject(result.error); } else { resolve(result.result); } }); }); }
-
@adsfa Sorry für die späte Rückmeldung, Urlaub... Laut influx -version ist das die 1.8.0. Ich bin jetzt keine Influx Spezialist, aber sollte die SQL Abfrage über die iobroker Instanz nicht in allen Versionen gehen?
-
@frederik-buss Danke
Soweit ich weiß geht das ab der neuen Version mit der Sprache FLUX in die ich mich aber nicht einarbeiten möchte.