fhem 4 Nerds or users?

Begonnen von martinp876, 02 Oktober 2022, 08:52:11

Vorheriges Thema - Nächstes Thema

martinp876

ZitatMit addLog werden Readings aktiv von Devices abgefragt die keine Events erzeugen (sollen).
ok, also
addCacheLine schreibt eine frei definierte Zeile in den Cache - und dann in die Datenbank. Hierbei wird nichts weiter geprüft. Also Device oder Reading müssen nicht existieren.
Ah: Es erlaubt das setzen des Typs ohne Kontrolle. Ein Device kann dann mit 2 Typen im Log stehen... na ja - Typ werte ich sowieso nicht aus.

AddLog liest die Werte der Readings gemäß devicespec und logged diese. Wenn nicht, dann...

Nun bin ich ein Pedant wenn es um die Wortwahl geht. Ich will das Kommando schon am Wort verstehen.
- einmal geht es um eine Lien, dann um ein Log.
- einmal wird der Cache erwähnt, das andere mal nicht.
=> ich mache mir (weil eben Pedant) gedaken darüber, was mir die unterschiedliche Syntax sagen will.
Einfach wäre, wenn das absetzen eine forced-logs unabhängig von Async oder Sync ist. Man führt das Log einfach den Processing zu.
==> Es ist nicht beschrieben, was addCacheLog im Sync mode macht. Garnichts da kein Cache?

addLog kann bspw gut genutzt werden, um nach Mitternacht Readings zu "Forcen". Anwendung: ich nutze immer Event-OnChange-Reading .* . Das ist super - jedoch kann es sein, dass bspw die Wunschtemperatur eines HK erst um 7:00 geändert wird. In einem Graph welcher um Mitternacht beginnt fehlt also der Startwert. Eine Option wäre das regelmässig force-loggen des Wertes alles HK.

==> Nicht beschrieben ist, was addChacheLine macht, wenn mehrere Readings passend sind. Werden dann alle geloggt?

Unschön die eigenwllige Syntax beim Trenner von addCacheLine. Wäre auch mit Whitespace gegangen und " als klammer.

addCacheLine ist also ein "forceLog" oder besser addLog da u.a. auch der Timestamp gesetzt wird.
addLog ist demnach ein triggerLogReading. Hier wird kein Zeitstempel gesetzt und es wird nur ausgeführt, wenn auch das/ein Device existiert. Unit kann man nicht setzen (warum?). Und man kann auch ReadingNamen neu einbauen - was sich mit  addCacheLine überschneidet.

Zusammengefasst: ich hätte mir eine bessere Abgrenzung der Kommandos gewünscht - evtl ist es ja auch nur eines? Am meisten stört mich das "cache" im Namen. Diese Details verlangen dir zur Kompletten Definition der Kommandos einiges an erklärung ab, welche evtl nicht notwendig sind.

Wie wäre es gewesen mit
forcelog <devspec> <readingExp> [<defaultvalue>] [(<timestamp>|now)]
DevSepc: if devicematch is found all matched deivces are processed. If no match is found and devSpec is a valid name-string devspec is uesd as name (even if non-existant).
readingExp: all selected devices are searched for this reading-pattern. Any Match will be added to the Reading list to be processed.
default value: this will be set al value to each of the Device/Reading pair of the device/Reading list where the Reading does not exist.
timestamp: if given this will be set as timestamp. For "now" or it not given the current time will be used.

Unit und Type könnten genause addiert werden. Auch einfach wäre die Nutzung von Prefix m Kommando
forcelog <devspec> <readingExp> [-v:<defaultvalue>] [-t:(<timestamp>|now)]  [-u:unit]

Ich denke du kannst dir den Rest denken.

ZitatUnd das Verhältnis von Aufwand und Nutzen solcher Cleanup-Aktionen ist auch wichtig, zumal wir diese Tätigkeit völlig in unserer Freizeit leisten. Aber wem erzähle ich das ...
schon klar - auch ich werde für meinen Entwickeranteil nicht bezahlt - wen sagst du das.

Evtl sollte ich das(mein) Zeil noch einmal klarstellen:
Ein Modul sollte erst einmal einfach in Gan zubringensein und sich beherrschen lassen. Für Nerds sollte definitv! Optionen zu Verfügung stehen, lustige Sachen zu impemetieren (das ist das Ween von FHEM!)
=> wenn ich von Optionen und Funktionen überflutzt werden ist das kein guter Einstieg.
=> Typische Kommandos müssen vorgefertigt vorhanden sein um die Basisabeit zu erledigen. Basisarbeit bei einer Datenbank sind die primären Abfragen - welche man definieren sollte. Diese müssen bspw ohne SQL Kenntnisse erfolgen können


martinp876

Ich finde unsere Diskussion sehr interessant - möchte aber noch einmal anders anfangen. Wir sind schon im Detail - und meine Anregung in diesem Thread soll sein, etwas mehr "User" zu denken - Nerd ist schon sehr viel in FHEM.

Mit ist auch vollkommen klar, wie die Module entstanden sind, sich entwickeln und welche Probleme man hat ein einzelnes Kommando wieder auszuphasen. Viele Module sind gewachsen und nicht designed. Man hat mal angefangen, dann hat es sich entwickeln (war bei mir meist nicht anders). Um rückwirkend struktur in das User-Interface zu bekommen bedarf es großer Durchsetzungskraft. Könnte sich aber lohnen.

Daher die Anregung, deine (wichtige)  Funktion DB-logging ohne jegliche Hstorie , aber mit der Erfahrung zu betrachten und das Userinterface zu gestalten.
Wichtigste Frage: was sind die Use-Cases:
a) Generieren von Grafiken - diese Daten werden von Programmieren aus der DB geholt
b) lesen der letzten x Readings - weil ich wissen will, wie oft mein Device resetet, der Lichtschalter betätigt wird. Wann das letzte Mal sich en Reading geädert hat. => ein getLastEvents
c) statistik zur Auswertung, was wo wie oft passiert. Tabelle nach Monaten, Tagen oder Wochen sind denkbar.
d) welche Readings werden geloggt, seit wann und wie lange? Daraus kann/will ich schnell er erkennen, dass alles was ich will geloggt wird und nix anderes

Maintenance:
c) Ist meine DB noch connected? Automatischer Reconnect, Wie oft tritt das auf - Zähler. Der Admin-User muss beurteilen, ob die DB stabil connected ist.
d) wann wurde das letzte mal erfolgreich geschrieben
e) automatische Größenbeschränkung der Datenbank. Alte Einträge werden bspw. täglich oder wöchentlich (reicht auch) nach Kriterien gelöscht

Wenn es 2 Module geben muss (DBlog und DBrep) sollte diese klar und logisch abgegrenzt sein. Eigentlich will ich das schon am Namen sehen DBserver und DBreader
Ziel wäre bei mir immer, wenn ich ein Modul instanzieren erkenne ich die wichtigsten Kommandos sofort - ohne commandref. Nach möglich möglichkeit per drop-down.

Und haltet mir ungülige Kommandos fern. Wenn ich bspw im Sync mode bin gibt es keinen Cache.
-> alle cache kommandos werden ausgeblendet
-> beim Umschalten von async nach sync muss der cache gepusht werden.
-> ungültige Readings werden IMMER automatisch Entfernt.

Übrigens kann man beim Booten oder definieren auch automatisch Attribute setzen. Beim Reboot muss man etwas vorsichtig sein, geht aber auch. Der Anwender hat dann schon einmal die Wichtigsten Defaults vorliegenund kann diese ändern. Halte ich für exterm hilfreich, da diese Defaults dann nicht hidden sind.

Das ganze ist nicht komplett - ich hoffe die Idee ist verstanden.

Adimarantis

Hi Martin,

ich finde die Diskussion recht interessant. In meinem Modul (Signalbot) habe ich mir schon Gedanken gemacht, wie ich Dinge für den Anwender so einfach wie möglich halten kann. Da stoße ich allerdings als Programmierer auch oft an meine Grenzen, denn die ganzen "Tipps&Tricks" wie man FHEM Web dazu bekommt gewisse Dinge komfortabler zu gestalten sind nicht wirklich schön dokumentiert.

Ein paar Dinge die ich dazu realisiert habe sind
- Benutzerführung in der detailFn für den Registrierungsprozess
- Reduktion der langen "set" Listen durch kontextsensitive Liste (nur anbieten was gerade auch Sinn macht) und zweistufige set Befehle (also z.B. statt 5 set groupXXX Befehle, set group -> XXX -> argument - hat mir Rudi extra eingebaut :) )
- Hauptfunktionalität (bei mir das Senden einer Nachricht) zusätzlich als Widget am Anfang

Was ich mir auch gewünscht hätte, wäre die Möglichkeit die "set/get" Liste selbst zu sortieren, statt stur alphabetisch. Ist ein Grund für mein "send" Widget, da "s" leider im Alphabet recht weit hinten kommt und so bei "set" etwas an erster Stelle steht was eher nicht so häufig gebraucht wird. Der Author von Telegrambot hat das mit einem "_" vorneweg gelöst - unschön, dass man so einen Workaround braucht.

Alles was darunter kommt (Internals, Readings) nehme ich zugegebenermaßen als gegeben hin. Ich wüsste jetzt spontant nicht wie man die ganzen Internals ausblendet (bzw. relevante Daten beibehält), meine Readings sind auch gewachsen und könnten übersichtlicher sein.

Wenn ich da Richtung "User" gehen wollte, dann müssten die Internal und Readings in ihrer Form weg, und dafür die relevanten Infos ein einer schön aufbereiteten Form - so dass es eben bei "normaler" Aulösung auf eine Seite passt.
Statt der Attribute bräuchte man einen Config Editor, der möglichst noch mehr Hilfestellung gibt und die Einstellungen thematisch statt alphabetisch gruppiert sowie gleich auf gewisse Abhängigkeiten achtet.
Statt komplexer Syntax für die Favoritenliste müsste auch ein schöner Editor her.

All das übersteigt aber mein Wissen über die Möglichkeiten in FHEM Web. Da müsste erstmal ein gut dokumentiertes Baukasten System her -> halbwegs einheitliches Look&Feel und nicht jeder erfindet das Rad neu.

My 2 cents...

Jörg
Raspberry 4 + HM-MOD-RPI-PCB (pivCCU) + RfxTrx433XL + 2xRaspberry 1
Module: 50_Signalbot, 52_I2C_ADS1x1x , 58_RPI_1Wire, (50_SPI_MAX31865)

martinp876

Hallo Jörg,
korrekt, sortieren wäre cool. Ich habe an einigen Stellen die Komamndos, Readings und Attribute entsprechend gesetzt.
ZitatAlles was darunter kommt (Internals, Readings) nehme ich zugegebenermaßen als gegeben hin
Ich eigentlich nicht. Readings, ok. Internals: hier plädiere ich vehement für eine Sortierung der Standards. Also Name/Typ/Def und sonstige Teile gehören an die Spitze in eine fixe Reihenfolge.
ZitatIch wüsste jetzt spontant nicht wie man die ganzen Internals ausblendet (bzw. relevante Daten beibehält), meine Readings sind auch gewachsen und könnten übersichtlicher sein.
Nun, immer wenn du die Daten in der Hand hast ist es einfach, evlt aber anstrengend (für dich).  Alles was jemand anders setzt kannst du nicht beeinflussen.
1)Es ist dir sicher bekannt, dass internals nur in der ersten Ebene sichtbar sind. Wenn du also Daten benötigst kannst du diese in einem Sub-Hash verstecken.
2) alle Variablen welche mit "." beginnen sind erst einmal unsichtbar. Mit dem Attribut global showInternalValues kann man hier umschalten.

Man könnte viel besser machen. Einiges kannst du aber erreichen - allerdings kenne ich deine Anwendung nicht. in CUL_HM habe ich einiges Realisiert... auch hier ist einiges gewachsen - also nicht optimal aber ich bin weitgehend zufrieden.

Hier ein paar ideen welche ich realisiert habe - unter den Einschränkungen der FHEM Möglichkeiten. Hintergrund: CUL_HM bedient einige unterschiedliche Geräten (Homematic eben). Diese haben unterschiedliche Kommandos, Parameter und Attribute. Ziel ist, ausschliessliche gültige zuzulassen, alle anderen stringent verhindern.

1) es gibt immer ein get cmdList (short|long) welches sämtliche Kommandos dieser Entity auflistet - mit kompletter Syntax und ggf kleinem Text. Ich parse alle Kommandos exakt nach dieser Syntax - immer - in einer Funktion. Du erkennst Optionen, Defaults,... das ganze voll dynamisch. Sollte sich also eine neue Kombination ergeben wird diese eingepflegt. Die Sortierung gestalte ich
2) ein "get list (normal|full) sollte nie fehlen. list normal zeigtdas gleiche an wie das manuell eingetippte Kommando - nur ohne tippen. List full zeigt mir auch das, was ich nur sehen kann, wenn ich vorher attr global showInternalValues 1 mache an. Das ist ein no-go. Wenn ich einmal wirklich sehen will, was gespeicher ist muss das sofort gehen.
3) in Internals habe ich zu viel eingetragen. Hier plädiere ich für ein "get deviceInfo" mit einer Liste von optionen, was man darstellen soll - in einer entsprechenden Form. Internals ist m.E. einem Kurzstatus vorbehalten. Die meisten anderen Daten schaue ich mir nur gelegentlich an.
Selbstverständlich solltest du eine get Funktionvorbereiten um Daten automatisch abzufragen.
4) Bei CUL_HM haben die devices teils unendliche viele "Register", also Readings. Hier habe ich mehrere Methoden eingbaut, diese Sichtbar zu machen.
4a) Readings sind hidden also mit ".". Über ein "get" kann man die Register visualisieren - in tabellenform nach meinem Design
4b) über das Reading "expert" kann man einstellen, was man in den Readings sehen will. Das ist natürlich  dank der nahezu komplett fehlenden Unterstützung von FHEM wirklich arbeit. Ich baue den Punkt vor die Readings und nehme ihn weg, je nach mode. dabei mus sich sicherstellen, dass bei Abfragen (welche ich in der Hand habe) der Punkt ignoriert wird, also immer das korrekte Ergebniss kommt. Am Ende denke ich, dass es sich gelohnt hat. Dennoch hätte ich mir eine bessere Option des Kernal gewünscht.
=> damit kann ich die Readings wirklich kurz und übersichtlich halten und doch alles zu verfügung stellen - sogar auf 2 Ebenen, je nach Geschmack.
5) Obsolete Readings werden konsequent eliminiert (wenn identifizierbar).
6) für Attribute gilt gleiches wie für commands: nur gültige werden erlaubt
7) ich setze einige Attribute bei der Definition auf default Wert. Grund: ich bin der Meinung, dass einige Defaults dem Anwender gezeugt werden sollten. Das erhöht die Aufmerksamkeit. Weiter mache ich auch einen Vorschlag (attr webCmd) indem ich enen m.e. sinnvollen Default setzt.
7a) das Vorgehen hat zur Konsequenz, dass ich defaults von User-aktionen unterschieden muss. Insbesondere beim Reboot komme die Attribute in ungeordneter Folge zur Verarbeitung. Hier funktioniert der Parser nicht, da es abhängigkeiten gibt.
=> ich kann die Attribute beim Reboot erst prüfen, wenn alle da sind. Also ist es zwingend, sich einen Post-init-trigger zu setzen - wenn init_done auf 1 geht. Dann gebe ich CUL_HM die Zeit, Attribute zu prüfen, ggf auch zu löschen und Parameterlisten zu erstellen.
8) Wenn du abhängigkeiten zu anderen Entites hast, deren Namen oder Attributen, ist es deine Pflicht, eine Teilchen auf Stand zu halten. Du musst dich also über abhängige Änderungen informieren lassen und nachziehen. Ordentlich in Notify einhängen. Mein getuntes "Notify" erkenne renames von entites und passt die Einstellungen automatisch auf verschiedenen Ebenen an.
9) in CUL_HM kann man über "readingOnDead" erreichen, dasss selektierte Readings auf dead oder 0 gesetzt werden. Es hat mich aufgeregt  - und ist schlicht unterirdisch, dass, wenn sich ein device nicht meldet, immer noch Messwerte angezeigt werden. Wo gibts den so was.
10) semantisch korrekte Namen - konsequent genutzt. Hier habe ich sicher Defizite. Beispiel ist dblog üer das ich gerade brüte. "cache" ist m.E. schlicht falsch, wir haben hier einen WriteBuffer. Alle Kommandos und Attribute könne man also mit "wb" beginnen lassen. Damit wäre auch Synchron/Async erledigt Wir hätten einen Bufferd/non-buffered mode. Du musst deine Anwendung dahingehend durchforsten. Ein eingeführter Begriff ist nahezu nicht mehr zu entfernen.
11) Zeil meine rKommandos ist immer, es mit "click" zu lösen. Bei dbLog ist set count und set countNbl m.E. schlecht.Ich hätte sein set count (blocking|nonBlocking) definiet (oder blocking eliminiert)

Esgibt noch ein paar mehr details. Nicht von mir (und daher) aber Super isr das Interface zur Programmierung von Registern in CUL_HM. Das ist echt Usergeführt.

Wichtig ist auch, Ausgaben über pop-ups zu gestalten.
Ich habe lange gesucht nach einem Frontend. Mit TabletUI kann man Webseiten gestalten - bisher das Beste. Man kann alles, ist aber schonkompliziert amEnde etwas cooles zu bauen. Aber das alleine reicht nicht - nun habe ich den Kioskbrowser entdeckt. Das beide zusammen ermöglicht endlich, ein tablet zu Haussteuerung aufzustellen. Für jedermann erreichbar.
Jetzt kommts: Hier gibt es keinen "back" Button. Daher mussen alle Ausgaben auf der Seite erfolgen oder in enem Popup.

Sicher gibt es noch mehr, sich auszutauschen... und meine ideen sind weder einzig  noch alternativlos. Es ist ein Anfang, meine ich. Wenn FHEM aus der Basis heraus etwas mehr unsterstützen würden ginge deutlich mehr!

Adimarantis

Hi Martin,

internals lege ich grundsätzlich in $hash->{helper} und damit unsichtbar.
Trotzdem zähle ich 11 internals bei meinem Modul, von denen ich nur "STATE", "VERSION"  und "model" absichtlich setze (letzters wegen der statistics).
Vom Rest ist vielleicht gerade noch "TYPE" für den Anwender interessant. Der Rest braucht bloss Platz.
Readings aufräumen muss ich glücklicherweise eigentlich nicht, da die bei mir recht konstant sind. Lediglich mein "lastError" für aynchrone Fehlermeldungen sollte ich vielleicht nach eine Weile auf "ok" setzen - eine Fehlermeldung die schon Tage alt ist verwirrt erstmal (auch wenn man das am Datum erkennen könnte).

Thema fork() übrigens: Da habe ich bei Signalbot und auf RPI_1Wire (rewrite von GPIO4) viel Aufwand reingesetzt das ganz oder zumindest weitgehend zu vermeiden. Das sieht aber anscheinend nicht jeder so, wie ich schon bei Diskussionen gemerkt habe.

Aber vielleicht genug Beweihräucherung, wie toll wir das alles schon in unseren Modulen gelöst haben.
Auch wenn ich gerne einiges ändern würde, weigere ich mich einfach massig Zeit in Workarounds zu hängen, weil das FHEMWEB Framework es nicht hergibt - und das ist nunmal Stand der Dinge. Alle anderen Frontends erfordern, dass der User seine Oberfläche individuell zusammenstellt. Um mehr für "User" zu tun (und ggf. auch mehr zu gewinnen) muss der Standard besser werden.
Mal zusammengefasst:
-> Mehr Kontrolle für den Moduldesigner über Darstellung (alles ein/ausblendbar, sortierbar, dynamisch)
-> Widgetbaukasten um modulspezifische Ersatzdarstellungen für Internals, Readings, Attribute etc. zu machen: Tabellen, sich gegenseitig beinflussbare Pulldowns, Eingabefelder mit Syntaxcheck ("save" Button für mehrere Einstellungen gleichzeitig, der einen Plausicheck machen kann und dann Felder z.B. einfärbt die korrigiert werden müssen)
-> Designguidelines und Dokumentation dazu.

Ich denke viel geht sogar schon. FHEMWEB kann viel, ist aber alles versteckt. Wenn ich mir "Babble" anschaue, dann hat pah hier irgendwie eine Darstellung hingekriegt, in der man eben keine Internals etc. mehr sieht. Das ist aber irgendwie ein "Room" - in der Device Ansicht schaut es wieder "normal" aus.

Vielleicht braucht es dazu aber doch eine Alternative zu FHEMWeb die ein moderneres Look&Feel für "user" implementiert (FHEMWEB ist dann für "nerds" :) ).
Das muss aber dann trotzdem immer in der Lage sein einen Default View zu erzeugen, ohne dass der Anwender oder Moduldesigner Hand anlegen muss.
Problematisch wirds dann, wenn schon in die FHEMWEB Trickkiste gegriffen wurde - da funktioniert dann evtl. nicht mehr alles.
Dieser Default kann ja eher Minimalistisch sein - der Weg zum "nerd" Modus in FHEMWEB steht ja offen.

Leider ist das eine extrem aufwändige Grundrenovierung für die wahrscheinlich keiner Zeit bzw. notwendiges KnowHow hat.
Sowas geht auch nur kooperativ. Das Prinzip ein Modul - ein Maintainer wird da nicht mehr funktionieren.

Da müsste das ganze FHEM Projekt in ein gemeinschaftliches OpenSource Projekt (GitHub?) umgewandelt werden, bei dem jeder PRs für jedes Modul machen darf.
Wäre vielleicht ohnehin ein erster Schritt. Habe schon so oft gesehen, dass Maintainer (aktuell) nicht erreichbar waren und zwar Fixes oder Anpassungen vorgeschlagen werden, aber sich keiner "traut" das auch einzuchecken (nicht dass man dann implizit plötzlich Maintainer wird).
Bei einem PR Ansatz sollte zwar möglichst der Maintainer Änderungen vornehmen und PRs akzeptieren. Wenn er aber nicht zeitnah reagiert und genug andere die Änderung gut finden, sollte sie genauso gemerged werden.

Jörg
Raspberry 4 + HM-MOD-RPI-PCB (pivCCU) + RfxTrx433XL + 2xRaspberry 1
Module: 50_Signalbot, 52_I2C_ADS1x1x , 58_RPI_1Wire, (50_SPI_MAX31865)

martinp876

Zitatom Rest ist vielleicht gerade noch "TYPE" für den Anwender interessant. Der Rest braucht bloss Platz.
genau meine Meinung. Diese Daten (auch manchmal interessant - aber wohl selten) muss man über ein "get deviceInfo" abfragen können - oder über ein InternalVal was auch hidden unterstützt.
==> Rudi müsste über seinen Schatten springen.

ZitatThema fork() übrigens: ...
Fork muss man sinnvoll einsetzen. Ich sehe das so:
Prio A) der operationelle Ablauf, also die Steuerung, das keepalive, die Device kommunikation dürfen nicht gestört werden. Ein einzelner Task sollte eine bestimmte Länge nicht überschreiten. HM IOs haben einen 30s timer - wenn das keepalive nicht kommt müssen sie neu synchronisieren. Viel schärfer sind die Timingvorgaben der HM Protokolle. Hier werden Antworten <<1s erwartet.
==> alles das display, manualle Abfragen u.ä. betrifft MUSS in den Hintergrund. Wenn einige Entwickler ihr Modul als den Nabel der Schöpfung einordnen kann ich das nicht verstehen.
==> wo genau die Grenze ist, ist scher zu Entschieden.

Forken) Ich hoffen jeden ist kla, dass beim Forken immer eine komplette Kopie des Prozesses gemacht wird. Je grösser der Prozess um so mehr resourcen werden der CPU genommen. Bei jeden Forken neu.
=> in CUL_HM / HMInfo forke ich für einen Config-check. Zum Einen benötige ich sowieso viele Informationen, und zum Anderen dauern die Auswertungen etwas. Und drittens wird das nur selten aufgerufen. Somit ein klassischer Fall für "forken".

Externener Prozess) in Presence hatte jemand zum Pingen der BT Teilnehmer einen externen Prozess erstellt. Optimal. Der Prozess wird ständig gebraucht und es braucht nahezu null info um einen Auftrag zu erteilen. Leider wurde IP-Ping über Forken in einer geradezu chaotischen Weise implementiert.
Im Falle von DBlog ist ein externer Prozess genau das, was man benötigt. Wenn ich aktuell eine Grafik erstellen lasse und 1 Jahr als Zeitraum eingeben bleibt alles stehen.... geht garnicht.

ZitatAber vielleicht genug Beweihräucherung, wie toll wir das alles schon in unseren Modulen gelöst haben.
klar - und das geht oft in die falsche Richtung los. Meine Beispiele sollen Anregungen sein, dass etwas geht. Es gibt auch deutliche bessere Lösungen - und jeder Fall liegt etwas anders.
ZitatUm mehr für "User" zu tun (und ggf. auch mehr zu gewinnen) muss der Standard besser werden.
genau weil ich dieser Meinung bin habe ich diesen Threat gestartet.

ZitatFHEMWEB kann viel, ist aber alles versteckt.
Korrekt. Ich nutze TabletUI - ist aber doch sehr anstrengend, eine sinnvolle und vor allem sinnvol programmierte Oberfläche zu schaffen.

ZitatDieser Default kann ja eher Minimalistisch sein - der Weg zum "nerd" Modus in FHEMWEB steht ja offen.
Und das ist wichtig. Ich wünsche mir einen Nerd-Zugang wenn ich einmal etwas sonderbares machen will. Aber  erst einmal sollte man einschalten und spielen können.

ZitatLeider ist das eine extrem aufwändige Grundrenovierung für die wahrscheinlich keiner Zeit bzw. notwendiges KnowHow hat.
Ich will eine "User-Admin" oberfläche (FHEM-web) um das System zu beherrschen und ein Tablet-UI für meine Frau (Kiosk Browser führe ich gerade ein).



martinp876

Noch ein Beispiel zu DBlog  - event filtering. das hätte man m.E. einfacher machen und beschreiben können.

define <name> DbLog <configfilename> <regexp>
<regexp> is identical to the specification of regex in the FileLog definition.

<regexp> sollte eigentich <eventFilter> heissen man beschreibt den Inhalt nicht die Syntax.
Die korrekte Syntax ist
define <name> DbLog <configfilename> [<eventFilter>]
da eventfilter optional ist.
in Filelog ist unklar, ob der Filter optional ist.
Ich bin wieder einmal der Ansicht, dass der Filter ein Attribut sein müsste. Unklar ist, ob mehrere Kombinationen zulässig sind wie man das implementiert. Also (wz:level.*|sz:temp.*). Die Beschreibung ist hier zu dünn.
Bei DBlog ist es demnach genauso unklar - hier hat man aber die Option, jedem Device ein Attribut mitzugeben. Nein, sogar zwei.
=> es hätte definitiv auch eines gereicht: DBeventFilter.
da es nun 2 sind stellt sich die Frage, wie das ganze verarbeitet wird. On Top kommt noch der DBlogSeletionMode.

Die Beschreibung ist schon cool:
ZitatExclude: DbLog behaves just as usual.
ok - aber was ist usual?
und warum braucht es den Mode, wenn es doch 2 Attribtute gibt? Ist ein Übersteuern notwendig?

Wenn ich nun include und exclude defnieren - und on Top noch den Übergreifenden Filter habe - wie geht das denn nun?
Kann man das nicht einfacher Beschreiben wie z.B.
event => filter by global Filter => apply DBexclude filter => apply DBinclude filter
noch etwas ausschmücken, damit kann ich etwas anfangen.
Einfacher ist
event => filter by global Filter => apply DB devicelevel filter
der Devicelevel Filter kann auch ausschliessen.

So und nun sind einfacher Anwender verunsicht - wird mein Event das nächste Mal auch geloggt? Nun helfen wir ihm doch. Einige Optionen:
- DBlog hat ein "get deviceFilter" welcher alle devices und deren Filter anzeigt. Auch die welche gar nicht geloggt werden oder die, welche alles loggen lassen.
- ein SimulateFilter macht in jeden Fall sind. Hier werden alle aktuell vorhandenen Readings dem Filter unterzogen und der User erhällt eine liste aller ereignisse, welche geloggt würden, würde das event eintreffen. Selbstredent kann man die Analyse auf devices ein schränken
=> Der User muss sich dann keine Gedanken machen und seltsame Evnts generieren.Wysiwyg war einmal in.

damit hatte ich 2 Attribute weg optimiert und eine Validierungsoption geschaffen, welch e definitiv von Usernund Nerds genutzt werden kann.

martinp876

nun habe ich doch im Code nachgesehen um zu verstehen, wie Include/Exclude funktioniert.
Hierbei hätte ich etwas Anregungen die Performance betreffend. Das Modul klinkt sich ja nun bei allen Readings und Events ein - somit erwarte ich maxmale Performance.
Kleinigkeit: Wenn man my $name     = $hash->{NAME}; definiert und den Namen extrahiert macht es sinn, diesen auch durchgängig zu nutzen. Bei dev_ahsh dito.

Ich sehe weiterhin dass der Include/Exclude string jedes mal frisch gelesen und zerlegt wird. Das ist nicht notwendig, so etwas macht man, wenn das Attribut gesetzt oder geändert wird. Man kann sich hier prächtig in die Notifies des Kernal einhängen und immer auf Stand bleiben.
Jedel Mal zerlegen geht eigentlich garnicht-

DS_Starter

Ich will mich nur nochmal ganz kurz zu der folgenden Aussage äußern:

Zitat
Wenn ich aktuell eine Grafik erstellen lasse und 1 Jahr als Zeitraum eingeben bleibt alles stehen.... geht garnicht.

Dir ist schon klar, dass dies nichts mit DbLog zu tun hat sondern mit den Attributen im FHEMWEB, oder ?
Du hattest ja schon configCheck ausgeführt, aber vermutlich den folgenden Inhalt geflissentlich ignoriert:

ZitatResult of plot generation method check

WARNING - at least one of your FHEMWEB devices has attribute "plotfork = 1" and/or attribute "plotEmbed = 2" not set.

WEB: plotfork=1 / plotEmbed=2
WEB.BLACK: plotfork=1 / plotEmbed=1
WEBSSChatBot: plotfork=1 / plotEmbed=2
WEBphone: plotfork=1 / plotEmbed=2
WEBtablet: plotfork=1 / plotEmbed=2

Recommendation: You should set attribute "plotfork = 1" and "plotEmbed = 2" in relevant devices. If these attributes are not set, blocking situations may occure when creating plots. Note: Your system must have sufficient memory to handle parallel running Perl processes. See also global attribute "blockingCallMax".

Ich wollte das nur fachlich richtig stellen weil es eher in die Kategorie FHEMWEB gehört was vermutlich auch noch in deiner Betrachtung Platz finden wird.

Nunja es freut mich jedenfalls dass du dich so intensiv mit DbLog beschäftigst. Dann habe ich wenigstens eine Stichpunktliste was ich alles überarbeiten könnte wenn ich mich mal wieder Zeit investieren will um mich mit dem Modul auseinanderzusetzen.
Vielen Dank für die viele Zeit die du hier investierst .... endlich mal jemand mit Durchblick, Respekt.




ESXi@NUC+Debian+MariaDB, PV: SMA, Victron MPII+Pylontech+CerboGX
Maintainer: SSCam, SSChatBot, SSCal, SSFile, DbLog/DbRep, Log2Syslog, SolarForecast,Watches, Dashboard, PylonLowVoltage
Kaffeekasse: https://www.paypal.me/HMaaz
Contrib: https://svn.fhem.de/trac/browser/trunk/fhem/contrib/DS_Starter

martinp876

nun, hatte ich nicht gesehen - sorry.
Habe es gleich geprüft.
1) plotfork war schon gesetzt
2) plotEmbed war nicht gesetzt - sollte also bei einem Raspi3 auf 2 defaulten.
=> damit sollte ich auf Stand sein. Deine Auswertung betrachtet nicht die Defaults. Verständlich, da sie nicht wirklich abfragbar sind. Sollte man auch ändern... wenn ich ein nicht gesetztes Attribut abfrage und dies einen default Wert hat. Dies ist aber wieder einmal ein Kernel Problem.

Zu dbLog abschliessend von meiner Seite (wir sind ja hier auf der Wunschseite :) ):
mir würde eine Lean-Version des DBlog gefallen, welche sich von den alten Zöpfen verabschiedet. Wir waren uns bei fast allem eigentlich einig, wie wir es machen würden. De facto würde ich bezüglich des User-Interface einen cleansweep machen und nur das realisieren, was sinn macht. Ich fasse noch einmal die kernpunkte zusammen (weil ich zusammenfassungen mag). Da ich bei einer Umstellung dieser Art erhebliche Probleme in der kompatibilität sehe würde ich an deiner Stelle den harten Schritt gehen und en dblogLean oder dglog2 auf den Markt bringen. Das aktuelle Modul würde ich als phase-out markieren und die Maintenance einstellen (wenn das 2. fertig ist).

Die Punkte welche ich mir wünsche
- nur history, kein current. Diese Auswahl aus allen Kommandos entfernen
- cache/async/... nach writeBuffer(-mode) umlabeln.  Alles hierzu beginnt mit "wb". Einschalten über Attribut wbTimer=0 (sofortiges schreiben ist faktisch ohne Buffer, also sync). wbMaxSize sind die maximalen Einträge im Buffer. Wenn erreicht wird geschrieben. Wenn schreiben schief geht wird der Buffer um max x% überzogen, dass wird weggeworfen. ==> es MUSS ein Limit geben. Auch wbTimer sollte einen Wertebereich haben 0=unbuffered, 300...80xxx(1 Tag) ist der zulässige Wertebereich - default ist 30min. 100000= use enMacSize only
- das Filtering hatten wir gerade
- alle config Angelegenheiten werden zur config-zeit erledigt (das sollte alle module so handhabe). Wenn also bspw ein Attribut dbFilter in jeder entity angeboten wird ist es die Pflicht von dbLog als faktischer owner auch die ünersicht zu behalten und es zur config-zeit zu verarbeiten.
-- typisch kommt man dann zum Ergebnis, dass man sich über alle attr/define/defmod/rename informieren lässt und hier anpasst.
-- dblog ist einem notify sehr ähnlich, eigentlich ist es eines - mit fixer exe. Da ich mit dem standard notify nicht einverstanden war habe ich es umgeschrieben und all das  - zumindest versucht - zu berücksichtigen. Bei mir klappts :) Will sagen, kein hexenwerk, sogar ich kann das
- dblog muss sich bei notify natürlich ordnungsgemäß enrolen - für alle Devices
- ein deamon-prozess sollte erstellt werden (da bin ich nicht fit - aber für die Könner sollte es kein Problem sein.
- ein Modul - so auch dbLog - sollte renames berücksichtigen. Das betrifft insbesondere den Filter aus dem Define. Ich werden diesen nie benutzen... eigentlich würde ich ihn streichen. Aber wenn er schon da ist müssen die Devices identifiziert werden, welche gefiltert werden. Und das bei jedem umbenennen und jeder neu-definition neu. Auch bei Attributänderungen wenn bspw devspec2array genutzt werden darf.
==> Grundsatz: wenn bspw ein rename eines devices stattfindet oder attribute gesetzt werden muss das system SOFORT genauso reagieren wie es nach einem reboot reagieren würde. Keine Diskussion möglich zu diesem Punkt.

Sicher werden/würden beim Überarbeiten weitere Punkte erkennbar...
Freut mich, wenn mein Anliegen zumindest verstanden ist.
freut mich richtig, wenn es (vielleicht auch nur in Teilen) umgesetzt wird.
Da ich auch nur begrenzt Zeit habe kann ich nicht immer am Ball bleiben.... ausser HomeAutomation habe ich noch ein weiteres Leben ;).
Jedenfalls danke fürs zuhören, wer bis hier unten gelesen hat.



martinp876

So - Themawechsel zu "propably associated":
=> ich halte dieses Feature für extrem wichtig und hilfreich, wenn man bei wachsenden Systemen als Admin den Überblick behalten will.
Allerdings muss ich feststellen, dass ich mit der aktuellen Implementierung nahezu komplett unzufrieden bin. So kann ich eigentlich nichts mit anfangen.
Es mag an den Anforderungen und dem Anspruch liegen, welche man sich stellt, wenn man so etwas baut.

Aktuell bewerte ich die Implementierung als: muss einfach zu implementieren sein, wenig code, automatisch. Kein Anspruch auf Vollständigkeit oder Bezug.

Mein Anspruch ist:
- max effort, eine vollständige List der Abhängigkeiten zu erzeugen
- klassifizieren der Abhängigkeiten
- evlt 2nd level dependancies anzeigen.

Aktuell werden abhängigkeinten aus den "defines" er einzelnen entites destiliert. Taucht ein devicename  im define einer entits auf ist das wohl eine Abhägigkeit. Also "define aaa myType bbb:ccc:ddd" => aaa hat abhängigkeinten zu bbb, ccc und ddd.
=> das ist schon etwas flach. Schon wenn man mit reg-exp arbeitet oder devspec tauchen extreme Lücken auf.

Btw: damit wird mir auch klar, warum Rudi darauf besteht, die eigentlichen Attribute eines Notify im define zu verarbeiten. Ausmeiner sicht ist und bleibt das ... sagen wir unsauber.

geht das besser? nun - klar geht das. Man muss nur stringent umsetzen, was es schon gibt. Bei Abhängigkeiten ist notify das perfekte Beispiel - und sollte (nach meinem Wusch) auch sinngemäß bei allen anderen modulen so umgesetzt werden:

Notify hat trigger und executes. Es kommen events von devices herein und es werden ggf andere devices angetriggerd (execute-section).
Die trigger-devices wären eigentlich einfach zu identifizieren. Egal ob in Kommandizeile oder per Attribut - es gibt immer einen "string" welcher die triggering-devices identifiziert. Dabei ist es wurscht on es ein devspec, eine liste oder eine regexp ist. Was zulässig ist wird in der Spec den Notify festgelegt.
=> nun ist es Aufgabe des notify alle devices zu identifizieren, welche in diese liste gehören - ZUR CONFIG-ZEIT!!! Notify wird sich dann für alle devices enrolen um trigger zu erhalten.
=> konsequenz ist, dass notify sich über config Änderngen informieren lässt, wenn notendig. Notify wird dann Anpassungen vornehmen und sich unrolen der enrolen.
=> es wird notwendig sein, sich beim Reboot erst nach dem init_done zu enrolen - vorher macht es keinen Sinn, da die Attribute fehlen.

Einst habe ich eine renovierung des notfy vorgeschlagen - diese habe ich bei mir realisiert (eine Frühe Versionsteht noch im Forum)

=> macht man es also richtig kann man probably associated  aus der Enrolement -Tabelle entnehmen. Und zwar KOMPETT! Aktuell wird das komplett ignoriert - schade.
=> das kann man alles einführen, ohne das User-interface zu verändern!

So nun habe wir die input-trigger komplett abgefrühstückt.
Bei den exeutes wird es schwerer. Der User kann hier wilde Dinge machen bis hin zu perl-code. Hier ist wird man also keine komplette Liste garantieren können. Man kann aber einiges erfassen:
wenn fhem-kommandos abgesetzt werden kann man die Empfänger tracken - und vermelden.
wenn diese spezifiziert sind kann man das ebenso.

Sonderfall. Lightscene - hier will man ggf eine 2. Stufe einbauen und erkennen, welche entites über light-scene getriggert werden.

So und nun - was will ich an Auswertung geliefert bekommen. Associated reicht mir natürlich nicht. In welcher Beziehung stehen die Entits?

Zu jeder Beziehung will ich den Typ wissen. Wie das aussehen soll habe ich noch nicht komplett durchdacht - und es gibt sowieso nicht nur eine korrekte Lösung.
So sehe ich folgende notwendigkeinten
My entity
- is triggered by (Bsp: notifies welche meine entity triggern, auch Scene welche es nutzen
- triggers (welche notifies lassen sich durch meine Readings triggern?)
- Trigger level (neuer Begriff). Wie oben schon erwähnt ist es die Pflicht einiger Entites sich übe config Änderungen informieren zu lassen. Das ist eine komplett andere Baustelle als Events und Readings auszuwerten. Somit muss ich unterschieden  zwischen triggers-config und triggers-event.
- direct-triggers und direct-triggered sind ebenfall Optionen. Bei CUL_HM und sicher auch bei anderen "familien" kann man devices direkt verknüpfen. Das will ich selbstredend auch dargestellt haben.
- display und logging würde ich in eine eigene Kategorie packen. Also fhemweb, dblog und filelog.
- Physikalische Beziehungen (kanäle eines devics)

So weit bin ich nun erst einmal. Selbstverständlich will man dann das ganze per get abrufen können. Systemweit wäre das ein Aufgabe für global. Auch in jedem Device kann man das abfragen.

Wofür das gut ist... sollte auf der Hand liegen. Will ich mein System pflegen und ein Device austauschen will ich wissen, was ich einst gemacht haben. Wer schaltet alles mein Licht an? Wo muss ich es berücksichtigen? Bin ich nach einem Rename noch aktuell? Was ist passiert - besser was ist Stand?

Ohne Disziplin beim Aufsetzen der  Module kann man das Ziel nicht erreichen (daher mein Abschied vom standard-notify - zu schlecht). Wenn man aber sich an die eigenen Ansätze hält wäre es gar nicht so komplex.
=> mein Wunsch ist also eine Beziehungsabelle mit der man arbeiten kann.
=> da ich schon bei notify und Freunden gescheitert bin werde ich mich bei Gelegenheit ans Werk machen, es selbst zu bauen. Unsaubere Module wir notify könne nicht berücksichtigt werden - daher nutze ich ausschließliche mein "ntf" :)




martinp876

Anbei mein erster Versuch zu impementieren / darzustellen was ich bei DBlog für den User erwarte. Also alles deutlich vereinfacht - weniger Attribute,... hatten wir schon.

in Myutils habe ich meine ersten Versuche realisiert, die Datenbank admistrieren zu können. Aktuell benötige ich 5 Kommandos (also setup/connect usw werden sowieso gebraucht)
getDBfilter devices:({.*},<regexp>|devspec)[,(<regexp>|devspec)[,...]]
getDBStat devices:({.*},<regexp>|devspec)[,(<regexp>|devspec)[,...]] readings:[({.*}|<regexp>)[,<regexp>[,...]]] spawn:[{{m}|d|w|y)] spawnCnt:[{{12}|1..24)]
getDBinfo devices:({.*},<regexp>|devspec)[,(<regexp>|devspec)[,...]] readings:[({.*}|<regexp>)[,<regexp>[,...]]] lines:[({5}|<count>)] statistics:[({n}|y)])
getDBdelPrep devices:({.*},<regexp>|devspec)[,(<regexp>|devspec)[,...]] readings:[({.*}|<regexp>)[,<regexp>[,...]]]
getDBdelExe [({-}|confirm)]


Ich bin ein Freund der strickten Syntax-Beschreibung. De-facto werden ich die Kommandos nach der Beschreibung aus. Es läuft in meinen Module ein "commandParser" welcher prüft, ob die Syntax eingehalten ist. Die Liste der Kommandos ist als "get" abzurufen- der Anwender kann sich also auf den Inhalt verlassen, da es auch exakt so kodiert ist.
geprüft wird:
- Anzahl der Parameter min/max
- Wertebereiche (so definiert)
- default werte
- Optionslisten (wenn möglich) werden in die Kommandos eingepflegt.
In CUL_HM gibt es noch dynamische Parameterlisten automatisiert - das geht hier zu weit.
Syntax ist strict, also einfach zu lernen.
[]: optional
(.|.|.): Lite von werten (optionsliste)
<> : beschriebener wert -also undefinierter String
xx..yy: Wertebeireich
{}default wert (macht nur sinn, wenn der Parameter optional ist.
Das Schöne ist, bei der Kommandoauswertung sind alle Parameter gesetzt, auch die optionalen, welche weggelassen wurden. Und der Anwender sieht, was der Default ist.
=> für mich Userfreundliche
=> wäre cool, wenn so etwas eine Zentralfunktion ist. Es lässt sich ALLES! realisieren. mit "..." wird die Parameter-Zählung übersprungen.

Zu den Funktionen:
getDBfilter gibt mir eine Liste der Readings des Device welche geloggt werden, wenn ein Event generiert ist. Die Liste kann man nach Devices und Readings mit regexp filtern. Devices auch mit DevSpec. Ich habe geschlampt, da ich nur mit Include arbeite. Die systematisch Implementierung sollte über den real genutzten Filter geprüft werden.
=> praktische Überprüfung der Einstellungen, so ähnlich wie eine Simulation.

getDBinfo ist eine einfache Abfrage aus der Datenbank. Es sind keine SQL Kenntnisse notwendig. Die Abfrage ist optimiert auf Performance. Der Nutzen:
liste aller Readings eines Device (lines = 1) oder einer Gruppe von Devices
Liste der letzten x Readings (lines = x) oder events. Ich kann auf die Schnelle alle powerOn events abfragen - oder die letzten 3. einfach "getDbInfo .* powerOn 3"
Das kann ich mit den Tabelt am Sofa bedienen.

getDBStat gibt mir Auskunft über die nutzung der Datenbank. Mittelfristig sehr wichtig meine ich. Ich bekomme eine Tabelle der Events mit 2 bis 24 Spalten in welchen die Anzahl der Ereignisse gezählt sind. Ich bevorzuge monatlich.
Nutzen: Ich kann erkennen, ob die Anzahl der Readings zu meinen erwartungen oasst und für alle gleiche Readings ähnlich ist.
Ich kann erkennen, welche Readings unangemessen Daten erzeugen. (Bei Temp Messwerten werden ich mir etwas einfallen lassen, da 0,1Grad schicht nicht geloggt werden müssen)
=> hierzu weiter unten mehr

getDBdelPrep Vorgereitung zum Löschen von Readings aus der Datenbank. mit diesem Kommando werden alle Device/Reading paare identifizert, welche gelöscht werden sollen.
Da löschen eine Quittung verlangt muss ein getDBdelExe mit confirm folgen - sonst wird das Löschen abgesagt. Es wie aktuell über ein Attribut freizu schalten ist mir zu gefährlich!
Hier besteht noch optimierungsbedarf. Bspw "keep the latest xxx entries" oer "Lösche alles vor <datum>"

Performance:
Ich habe meinen Stand der Erkenntnisse eingepflegt. Wenn es jemand besser kann würde ich gerne lernen.
Das ganze geht nicht non-blocking - wobei ich forken ablehne. En Sub-prozess muss her - werde ich mir noch bauen.
Bei den Versuchen konnte ich Erkenntnisse gewinnen und meine Befürchtungen bestätigen, was es bedeutet und wie man vorgehen sollte. Viele Daten machen Auswertungen langsam (oh wunder) -also sollte man nsbesondere es dem "user"  einfach machen, daten zu sparen.
1) event on change reading .* löst etliche Probleme. Damit erübrigt sich auf das komische Interval-Zeug in den DB-filtern.
1a) mit Event-on-change-reading .* kann es zu Problemen in der Grafik kommen. Lässt sich lösen. Einfach einen Wert um 23:59 und um 00:01 erzwingen. Funktioniert be mir wunderbar. das sind im Jahr 720 Werte je Device/Reading  welche es benötigen. Zur Gegenrechnung: ein CUL_HM Thermostat schickt alle 3min denn Staus, gemessene temp, desired-tem, valvePos und sonst noch etwas. Zusammen sind das in der  Stunde 60 Werte, im Jahr 175200 Werte je Reading. Und die meisten bleiben gleich.
=> schafft Wege und erklärt dem Anwender wie es sein System sinnvoll einrichtet.

Ich gehe beim Anwender(admin) davon aus, dass er listen erzeugen kann. Regexp (einfache) können auch noch viele. Und zum Schluss devspec - die gehobenen Klasse der FHEM Anwender.
FEHM Nerds können die Kommandos auch nutzen - und hätten weiterhin den Zugriff auf volle SQL-Kommandos. Und wenn ihnen die Datenflut gefällt können sie das steuern. Nerds machen, was sie wollen - dürfen sie ja auch.


martinp876

habe mich etwas tiefer mit dbLog beschäfftigt und werde es nun endlich für meine Anwendung nutzbar zu machen.
1) es gibt einige Details mehr zu beachten, also ich anfänglich vor hatte
2) technisch habe ich keine Probleme mit den beiden Modulen!!! Ich haben  nicht hineingeschaut - aber das habe ich auch nicht vor.
3) was probleme hervorruft ist die Performance. Damit sollte man einen User nicht alleine lassen. Dazu also meine heutigen Einlassungen

Performance: hier sind 2 Facetten zu betrachten
a) non-blocking. Das ist primär. Kommandos können hier sehr schnell lange dauern. ein Sub-prozess wäre also sinnvoll.
aa) es ist en timeout eingebaut, welcher fhem wieder frei gibt. das sind per default 100s. Wer will 100s auf das schalten eines Lichts warten, weil jemand einen DB-job gestartet hat? Das muss besser werden... also alles auslagern
ab) wenn dblog abbricht wird der Datenbank-prozess nicht gestoppt. Die CP wird also weiter belastet, die Datenbank sowieso. Bei Veränderungen, also delete/update wird die Datenbank weiter verändert - im Hintergrund. Dabei hat der User "abbruch" signalisiert bekommen
b) Die CPU Performance ist natürlich auch ein Problem. Mein System ist faktisch stehen geblieben... keine Lichter meher schaltbar,... ein no-go.


Wie bekommt man das system schneller? nun, erst einmal weniger Daten loggen. Das ist primär!. Das sollte man dem Anwender klar machen und eine einfache prozedur festlegen, wie er es erreichen kann. Man kann viel des nachfolgenden in DBlog erledigen - ich plädiere aber auf System-vorhandene Einstellungen. Man muss nicht alles doppelt machen.

I) event-on-change-reading .*
das sollte man immer (IMMER) einbauen. Das erübrigt dann auch die aufräum-kommandos in dbrep (duplicates). das in dbrep vorhandene Kommando macht eh nicht was ich brauche. Der Reihe nach
Ia) nur Änderungen loggen und notifizieren ist immer das mittel der Wahl. Man kann alles lösen, was jemand hier anführen wird. Die Datenflut rechtfertigt es in keinem Fall
Ib) typisches Problem ist die Grafik. Bei statschen Werten fehlt oft der Start-wert - oder Endwert. Das sieht hässlich aus. Nun, das ist lösbar. Grafiken beginnen in unseren Fällen immer an GANZEN TAGEN. Also schreibe ich per Notify um Mitternacht immer die kritischen Werte für 23:59 und 00:01 in die Datanbank. Das ist notwendig für sehr langsame Werte - also Wunsch-temp. gemessene temp ändert sich sowieso
Ic) das Implementerte entfernen von Duplikaten hilft mir also nicht, da der letzte Wert behalten wird (braucht niemand) aber an den tagenGrenzen nichts zu finden ist.
II) schnell ändernde Werte
gemessene Temperatur ändert sich ständig. 0,1° kann ich aber sowieso nicht darstellen. Ich generiere also einen geglätteten Wert. Der zu loggenden Messwert wird nur geändert, wenn er min 0,3° abweicht. Zusammen mit "Event-on-change-readings" reduziert sich ein Log gigantisch!

Die Aufgabe ist also, methoden zu generieren, mit denen der Anwender einfach eine schlanke Datenbank betreiben kann - mit Werten die er braucht und keine, welche nur Balast sind.

Ich brüte noch darüber - vielleicht hat jemand eine gute Idee.
Der Nerd in mir baut natürlich etwas lokal auf - ich komme vorran... dem User will ich so etwas nicht zumuten. Das Aufräumen der Datenbank ist ätzend - auch mit etwas tieferem Wissen

==> das Anzeigen von Grafiken ist schlicht zu langsam. Jahres-ansichten sind eine Katastrophe.

martinp876

heute eine Einlassung zu Datenhygiene. Wie kann man - für  normal-User  - die geloggten Daten sinnvoll gestalten. Wie kann ein User dies in den Griff bekommen.
Meine Datenbank ist - da ich sie einfach habe laufen lassen (so solll es m.E. sein) auf über 2 GB angewachsen. Grundsätzlich hatte ich schon einiges eingeschränkt - was nicht unbedingt selbstverständlich ist.
Grundsätzlich sollte geloggt werden zum Zwecke der späteren Auswertung. Grafiken oder manuelle Auswertungen in Sonderfällen.
Viele Daten bedeuten lange Auswertungen. Die Datenbank hat ein eigenleben und verbraucht erheblich CPU im Hintergrund - was am Ende das Ganze System verlangsamt. Ein Nerd wird sich dessen annehmen - aber eigentlich sollte es mehr plug&play bieten.

Nun - zu betrachten ist
Breite: Welche Readings sollen geloggt werden
Tiefe: Wie lang sollen Daten gespeichert werden
Höhe: welche Werte eines Readings sollen abgelegt werden.

Breite:
Dieser Teil ist schwierig. Der User muss entschieden, as er will. Dennoch kann die Datenbank applikation unterstützen in dem sie den User zeigt, was er eingestellt hat. (mein voriges Beispiel "simFilter". Halte ich für zwingend und längst überfällig. Zum 2. wäre eine Systematik hilfreich - d.h. alle meine HK Thermstate sollten gleich sein. Ein neues sollte automatisch mit den Filtern versehen werden. Ist aber nicht einfach - eine gute Idee ist gefragt, um es EINFACH für den User zu implementieren.

Tiefe:
das ist einfach. Man kann die Zeit begrenzen und die Datenbank löscht Einträge älter als XXXX . Das wird regelmäßig geprüft. ggf kann die Grenze die Filegröße  als Maßzahl nehmen.
Ich denke 2 -3 Jahre werde ich bei mir einstellen. Muss ich wohl extern machen.

Höhe:
Das ist nun der wirklich interessante Teil - hier kann man einiges machen und erreichen!!.
a) keine Doppelten Werte
event-on-change-reading ist das stichwort. Doppelte Werte sind definitiv nicht notwendig und eines sinnvollen Systems nicht würdig. Es gibt hier aus meiner Sicht eine Fussangel: Grafiken. die Linien beginnen erst mit dem ersten Wert im Zeitraum und enden mit dem Letzten. Das wäre einfach lösbar - wenn man nur will. Wir dein Zeitraum 1.1.2022 - 31.1.2022 dargestellt muss die Datenbank den letzten Wertvor 1.1.2022 automatisch zur Werteliste addieren. Für den Endwert ist der letzte Wert bis ans Ende oder zum aktuellen Datum verlängern.
=> Die Abfrage ist ziemlich einfach - kann sogar ich selbst erstellen (habe es schon)

b) jitter entfernen.
Bei Messwerten jittert der Wert gerne um die Auflösung - also um die letzte dargestellte Stelle. Bei Temperaturen beobachte ich das regelmäßig - und für eine Grafische Dastellung , auch über lange Zeiträume - brauche ich keine 0.1°. +-0,2° sind schon viel besser - mir reichen sogar -+0,4°. Ein Smoother ist also sinnvoll.
Ich habe hierzu ein notify gebaut welches das erledigt und Readings mit "S" postfix addiert. geloggt werden dann sind weichgezeichneten.
=> die Auswertungen sind bei mir am Start - be Bedarf könnte ich helfen.

Ich halte es für ein unding, dass ein user sich um solche Dinge kümmern muss um ein effizientes System an den Start zu bekommen. daher hier dieser Post.

Ich werden wohl wieder alles selbst bauen (habe das meiste...). Wirklich hilfreich wäre der Grafik-extender welche die angefragten Messewerte am Anfang und Ende des Zeitraums "verlängert". Wenn das nicht eingebaut wird werde ich es wohl auch selbst machen.
=> Wer erwartet, dass ein normal-user so etwas auf die Reihe bekommt - oder die Muse und Zeit investiert? Daher siehe ich FHEM als ein Nerd-System. Alles machbar - man muss es aber selbst tun.

CoolTux

Hallo Martin,

Deine Arbeit, hier bei den Anmerkungen, aber auch Deine eigenen Entwicklungen welche Du in fremde Module investierst sind hilfreich und sicherlich sinnvoll für andere Entwickler. Auf jeden Fall für den Modulautor dessen Modul Du erweiterst.

Was spricht dagegen Deine Erweiterungen welche Du machst dem Modulauthor per Patch zu kommen zu lassen?
Ansonsten empfinde ich die meisten Deiner Anmerkungen hier als wirklich Hilfreich und man merkt das Du Dir hier echt Gedanken gemacht hast. Über einen längeren Zeitraum.

Grüße
Du musst nicht wissen wie es geht! Du musst nur wissen wo es steht, wie es geht.
Support me to buy new test hardware for development: https://www.paypal.com/paypalme/MOldenburg
My FHEM Git: https://git.cooltux.net/FHEM/
Das TuxNet Wiki:
https://www.cooltux.net