Hauptmenü

Richtige Verwendung von DOIF

Begonnen von dominik, 07 Mai 2016, 17:46:49

Vorheriges Thema - Nächstes Thema

dominik

Hallo zusammen,

mich würde mal interessieren wie ihr DOIF verwendet. Dabei interessieren mich nun nicht die möglichen Schaltungsvarianten, sondern eher die Programmierung. Aktuell sehe ich nämlich folgende 2 Ansätze:

- DOIF Programmierung auf Basis des Devices
Dabei werden unterschiedlichen Readings herangezogen und nur ein spezielles Devices gesteuert, hier die Kaffeemaschine
define DI_kaffeemaschine DOIF
([WeckerUhrzeit] and [Residents:presence] eq "present")
(set Kaffeemaschine on)
DOELSE
(set Kaffeemaschine off)


Hier muss man ziemlich gut darauf achten, dass auch alle Zustände erreicht werden können. Fragt man z.B. nur [Residents:presence] nach dem DOIF ab und im DOELSEIF eine Uhrzeit, dann könnte es passieren, dass der Aufruf für die Uhrzeit nie zustande kommt wenn man um diese Uhrzeit zu Hause ist.

- DOIF Programmierung auf Basis des Zustands
Dabei werden mehrere Devices für einen speziellen Zustand geschalten. Erinnert eher an notify.
define DI_wecker DOIF
([WeckerUhrzeit] and [Residents:presence] eq "present")
(set Kaffeemaschine on,
set BoseSoundTouch on)

define DI_presence DOIF
([Residents:presence] ne "present")
(set Kaffeemaschine off,
set WLAN off,
set BoseSoundTouch off)
DOELSE
(set WLAN on)


Nach Zustand geschalten kann man ziemlich schnell und unkompliziert weitere Devices für Zustände hinzufügen. Nur kann es passieren, dass man irgendwann den Überblick verliert und in einem DOIF das Device ausschaltet und im anderen DOIF gleichzeitig einschaltet.

Würde mich interessieren was eure Erfahrungen sind. Ich habe (leider) einen Mischbetrieb und weiß noch nicht so recht ob ich damit zufrieden bin.
fhempy -  https://github.com/fhempy/fhempy: GoogleCast, Tuya, UPnP, Ring, EQ3BT, Nespresso, Xiaomi, Spotify, Object Detection, ...
Kaffeespende: https://paypal.me/todominik

Damian

Zitat von: dominik am 07 Mai 2016, 17:46:49
Hallo zusammen,

mich würde mal interessieren wie ihr DOIF verwendet. Dabei interessieren mich nun nicht die möglichen Schaltungsvarianten, sondern eher die Programmierung. Aktuell sehe ich nämlich folgende 2 Ansätze:

- DOIF Programmierung auf Basis des Devices
Dabei werden unterschiedlichen Readings herangezogen und nur ein spezielles Devices gesteuert, hier die Kaffeemaschine
define DI_kaffeemaschine DOIF
([WeckerUhrzeit] and [Residents:presence] eq "present")
(set Kaffeemaschine on)
DOELSE
(set Kaffeemaschine off)


Hier muss man ziemlich gut darauf achten, dass auch alle Zustände erreicht werden können. Fragt man z.B. nur [Residents:presence] nach dem DOIF ab und im DOELSEIF eine Uhrzeit, dann könnte es passieren, dass der Aufruf für die Uhrzeit nie zustande kommt wenn man um diese Uhrzeit zu Hause ist.

- DOIF Programmierung auf Basis des Zustands
Dabei werden mehrere Devices für einen speziellen Zustand geschalten. Erinnert eher an notify.
define DI_wecker DOIF
([WeckerUhrzeit] and [Residents:presence] eq "present")
(set Kaffeemaschine on,
set BoseSoundTouch on)

define DI_presence DOIF
([Residents:presence] ne "present")
(set Kaffeemaschine off,
set WLAN off,
set BoseSoundTouch off)
DOELSE
(set WLAN on)


Nach Zustand geschalten kann man ziemlich schnell und unkompliziert weitere Devices für Zustände hinzufügen. Nur kann es passieren, dass man irgendwann den Überblick verliert und in einem DOIF das Device ausschaltet und im anderen DOIF gleichzeitig einschaltet.

Würde mich interessieren was eure Erfahrungen sind. Ich habe (leider) einen Mischbetrieb und weiß noch nicht so recht ob ich damit zufrieden bin.

Es ist immer gut für die spätere Nachvollziehbarkeit, wenn man ein bestimmtes Problem mit einem DOIF realisiert und nicht mit mehreren.

Dein erstes Beispiel ist eher ungünstig, denn die Frage stellt sich: Wann soll deiner Meinung nach die Kaffeemaschine ausgehen?

Die wird nämlich auch dann ausgehen, wenn du zuhause bist. Du kannst ebenfalls Zeitintervalle definieren:

evtl. soetwas:


define DI_wecker DOIF
([[WeckerUhrzeit] - [Endzeit]] and [Residents:presence] eq "present")
(set Kaffeemaschine on, set BoseSoundTouch on, set WLAN on)
DOELSEIF ([Residents:presence] ne "present")
(set Kaffeemaschine off, set WLAN off, set BoseSoundTouch off)


Gruß

Damian

Programmierte FHEM-Module: DOIF-FHEM, DOIF-Perl, DOIF-uiTable, THRESHOLD, FHEM-Befehl: IF

dominik

Ich glaub das Beispiel hat meine Frage nicht ganz verdeutlicht.

So wie du schon geschrieben hast, habe ich für jedes "Problem" immer ein eigenes DOIF erstellt. Das führt dazu, dass ich z.B. die Bose SoundTouch aktuell in 5 DOIFs integriert habe:
DI_cominghome: Bose ein wenn home und Radio auf volume 25 stellen
DI_gotosleep: Bose aus wenn gotosleep, noch dazu alle anderen Geräte ausschalten bis auf WLAN
DI_presence: Bose aus wenn niemand daheim, noch dazu alle anderen Geräte ausschalten, WLAN ein wenn jemand daheim
DI_radio: Bose in der Früh ein und aus wenn Urlaub, noch dazu Kaffeemaschine ein
DI_tvon: Bose aus wenn TV an, noch dazu das Licht aus

Nun stell ich mir die Frage, ob ich ein
DI_bosesoundtouch
DI_kaffeemaschine
DI_wlan
...
oder mehrere zustandsabhängige DOIFs erstelle
DI_presence_state
DI_morning
DI_urlaub
DI_tvon
...

In der zustandsabhängigen Konstellation kann es passieren, dass ich in der Früh vor dem Wecker den TV einschalte, danach startet der Wecker und schaltet die Bose Box wieder ein, was ja nicht sein soll - zumindest für mich ;). Daher denke ich, dass eigentlich jedes Device nur in einem DOIF verwendet werden soll und jeder Zustand des Devices ebenfalls nur einmal definiert werden darf. So stellt man sicher, dass jeder Zustand auch genau richtig verwendet wird.
Damit wäre folgendes die Lösung...z.B. für DI_bosesoundtouch

define DI_bosesoundtouch DOIF
([WeckerUhrzeit] and [Residents:presence] eq "present")
(set Bose on)
DOELSEIF
([Residents:presence] ne "present" or
[TV] eq "present" or
[Urlaub] eq "ja")
(set Bose off)


Wenn ich nun aber im für den gleichen Zustand (Residents:presence=present, TV=present, Urlaub=ja) auch die Kaffeemaschine ausschalten will, so sollte ich m.E. ein neues DOIF für die Kaffeemaschine erstellen.
Nachteil:
- Wenn Devices auf Basis eines gleichen Zustands geschalten werden sollen, muss ich dennoch ein separates DOIF dafür bauen. Die Wartbarkeit des Zustands (hinzufügen/entfernen von weiteren Readings) ist damit schwieriger.
Vorteil:
- Ich sehe sofort wann das eine Device welchen Zustand haben soll. Die Fehlersuchen ist damit einfacher, da ich nicht mehrere DOIFs durchsuchen muss.

Wie siehst du das? Mir fehlt nämlich noch so ein "Best Practice Guide" für DOIF ;)
fhempy -  https://github.com/fhempy/fhempy: GoogleCast, Tuya, UPnP, Ring, EQ3BT, Nespresso, Xiaomi, Spotify, Object Detection, ...
Kaffeespende: https://paypal.me/todominik

Damian

Zitat von: dominik am 08 Mai 2016, 11:08:14
Ich glaub das Beispiel hat meine Frage nicht ganz verdeutlicht.

So wie du schon geschrieben hast, habe ich für jedes "Problem" immer ein eigenes DOIF erstellt. Das führt dazu, dass ich z.B. die Bose SoundTouch aktuell in 5 DOIFs integriert habe:
DI_cominghome: Bose ein wenn home und Radio auf volume 25 stellen
DI_gotosleep: Bose aus wenn gotosleep, noch dazu alle anderen Geräte ausschalten bis auf WLAN
DI_presence: Bose aus wenn niemand daheim, noch dazu alle anderen Geräte ausschalten, WLAN ein wenn jemand daheim
DI_radio: Bose in der Früh ein und aus wenn Urlaub, noch dazu Kaffeemaschine ein
DI_tvon: Bose aus wenn TV an, noch dazu das Licht aus

Nun stell ich mir die Frage, ob ich ein
DI_bosesoundtouch
DI_kaffeemaschine
DI_wlan
...
oder mehrere zustandsabhängige DOIFs erstelle
DI_presence_state
DI_morning
DI_urlaub
DI_tvon
...

In der zustandsabhängigen Konstellation kann es passieren, dass ich in der Früh vor dem Wecker den TV einschalte, danach startet der Wecker und schaltet die Bose Box wieder ein, was ja nicht sein soll - zumindest für mich ;). Daher denke ich, dass eigentlich jedes Device nur in einem DOIF verwendet werden soll und jeder Zustand des Devices ebenfalls nur einmal definiert werden darf. So stellt man sicher, dass jeder Zustand auch genau richtig verwendet wird.
Damit wäre folgendes die Lösung...z.B. für DI_bosesoundtouch

define DI_bosesoundtouch DOIF
([WeckerUhrzeit] and [Residents:presence] eq "present")
(set Bose on)
DOELSEIF
([Residents:presence] ne "present" or
[TV] eq "present" or
[Urlaub] eq "ja")
(set Bose off)


Wenn ich nun aber im für den gleichen Zustand (Residents:presence=present, TV=present, Urlaub=ja) auch die Kaffeemaschine ausschalten will, so sollte ich m.E. ein neues DOIF für die Kaffeemaschine erstellen.
Nachteil:
- Wenn Devices auf Basis eines gleichen Zustands geschalten werden sollen, muss ich dennoch ein separates DOIF dafür bauen. Die Wartbarkeit des Zustands (hinzufügen/entfernen von weiteren Readings) ist damit schwieriger.
Vorteil:
- Ich sehe sofort wann das eine Device welchen Zustand haben soll. Die Fehlersuchen ist damit einfacher, da ich nicht mehrere DOIFs durchsuchen muss.

Wie siehst du das? Mir fehlt nämlich noch so ein "Best Practice Guide" für DOIF ;)

Ich denke man kann keine allgemeine Antwort dazu abgeben.

Wenn Kaffemaschine und Bose nur presens als Gemeinsamkeit haben und sonst unterschiedliche Schaltabhängigkeiten, dann würde ich sie separat in zwei verschiedenen DOIF-Modulen behandeln.

Allerdings würde ich das Einschalten und das Ausschalten des gleichen Aktors versuchen jeweils in einem DOIF-Modul abzubilden. Wie in der Commandref schon gesagt: Wer die Lampe anmacht, soll sie auch wieder ausmachen.

Es ist wie beim Programmieren: Man fängt an und stellt im Laufe der Zeit Gemeinsamkeiten fest, die man zusammenfassen kann; oder umgekehrt, eine vermeintliche Gemeinsamkeit hat mehr Ausnahmen als tatsächliche Gemeinsamkeiten und schon verlagert man den Code in eine neue Funktion.

Mehrere DOIF-Module, die wiederum "Gemeinsamkeiten" haben, kann man in einen gemeinsamen Raum packen. So habe ich bei mir Räume für Beschattung, Heizung usw.

Gruß

Damian

Programmierte FHEM-Module: DOIF-FHEM, DOIF-Perl, DOIF-uiTable, THRESHOLD, FHEM-Befehl: IF

dominik

Ich glaube dein Satz: "Wer die Lampe an macht, soll sie auch wieder aus machen" trifft es sehr gut!

Werde mal versuchen meine aktuell 35 DOIFs nach diesem Grundsatz umzustrukturieren. Ich hatte nämlich viele Ein- und Ausschaltvorgänge in verschiedene DOIFs getrennt, da komplett andere Readings dazu verwendet werden. Z.B. Einschalten nach Uhrzeit, Ausschalten nach Presence/Temperatur/...und für den "left home" Fall, wollte ich immer ein eigenes DOIF haben welches man schnell überblickt und damit sicher gehen kann, dass auch wirklich alles aus ist was aus sein soll.

Werde das mal umstrukturieren und dann berichten.
fhempy -  https://github.com/fhempy/fhempy: GoogleCast, Tuya, UPnP, Ring, EQ3BT, Nespresso, Xiaomi, Spotify, Object Detection, ...
Kaffeespende: https://paypal.me/todominik

Per

In der Regel habe ich meine DOIFs den Geräten zugeordnet, es gibt aber auch Ausnahmen.


Und manchmal habe ich sogar mehrere kaskadierte DOIFs für ein Gerät.