This commit is contained in:
+7
-6
@@ -153,6 +153,7 @@ class Batterie extends IPSModule implements VerbraucherSchnittstelle
|
||||
parent::ApplyChanges();
|
||||
|
||||
$this->aktualisiereVariablen();
|
||||
$this->bereinigeUngueltigenSollwert();
|
||||
$this->registriereMesswertmeldungen();
|
||||
$this->WriteAttributeBoolean('RegisterInitialisiert', false);
|
||||
|
||||
@@ -219,7 +220,7 @@ class Batterie extends IPSModule implements VerbraucherSchnittstelle
|
||||
case 'Aktiv':
|
||||
$this->SetValue('Aktiv', (bool) $wert);
|
||||
if (!(bool) $wert) {
|
||||
$this->setzeZustand('SollwertGueltig', false);
|
||||
$this->verwerfeSollwert();
|
||||
$this->SetTimerInterval('VorgabeTimeout', 0);
|
||||
}
|
||||
$this->aktualisiere(true);
|
||||
@@ -235,7 +236,7 @@ class Batterie extends IPSModule implements VerbraucherSchnittstelle
|
||||
|
||||
case 'VorgabeTimeout':
|
||||
$this->SetTimerInterval('VorgabeTimeout', 0);
|
||||
$this->setzeZustand('SollwertGueltig', false);
|
||||
$this->verwerfeSollwert();
|
||||
$this->aktualisiere(true);
|
||||
return;
|
||||
|
||||
@@ -249,7 +250,7 @@ class Batterie extends IPSModule implements VerbraucherSchnittstelle
|
||||
return;
|
||||
|
||||
case 'SichererZustand':
|
||||
$this->setzeZustand('SollwertGueltig', false);
|
||||
$this->verwerfeSollwert();
|
||||
$this->schreibeRegister(0, true);
|
||||
$this->aktualisiere(true);
|
||||
return;
|
||||
@@ -313,7 +314,7 @@ class Batterie extends IPSModule implements VerbraucherSchnittstelle
|
||||
(int) $this->leseZustand('Sollleistung')
|
||||
)
|
||||
) {
|
||||
$this->setzeZustand('SollwertGueltig', false);
|
||||
$this->verwerfeSollwert();
|
||||
$this->aktualisiere(false);
|
||||
}
|
||||
$this->planeMeldung();
|
||||
@@ -419,7 +420,7 @@ class Batterie extends IPSModule implements VerbraucherSchnittstelle
|
||||
(int) $this->leseZustand('Sollleistung')
|
||||
)
|
||||
) {
|
||||
$this->setzeZustand('SollwertGueltig', false);
|
||||
$this->verwerfeSollwert();
|
||||
}
|
||||
$this->pruefeVorgabeTimeout($jetzt);
|
||||
|
||||
@@ -596,7 +597,7 @@ class Batterie extends IPSModule implements VerbraucherSchnittstelle
|
||||
if ($letzteVorgabe <= 0
|
||||
|| $jetzt - $letzteVorgabe >= $this->ReadPropertyInteger('VorgabeTimeout')
|
||||
) {
|
||||
$this->setzeZustand('SollwertGueltig', false);
|
||||
$this->verwerfeSollwert();
|
||||
$this->SetTimerInterval('VorgabeTimeout', 0);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -4,6 +4,13 @@ Alle wesentlichen Aenderungen an Enelix EMS werden in dieser Datei dokumentiert.
|
||||
|
||||
## Unreleased
|
||||
|
||||
- Verbraucher: Beim Verwerfen einer Manager-Vorgabe wird auch die gespeicherte
|
||||
und sichtbare Sollleistung auf 0 W gesetzt. Gilt fuer Batterie, beide
|
||||
Ladestationen, Pufferspeicher, Verbraucher 1-Stufig, Waermepumpe und
|
||||
Warmwassererwaermer. Bereits ungueltige Altwerte werden beim Anwenden der
|
||||
Instanzkonfiguration bereinigt. Gueltige Vorgaben, lokale Schutzprogramme,
|
||||
Mindestlaufzeiten und der Nachrichtenvertrag bleiben erhalten.
|
||||
|
||||
- Manager: SDL-/Regelenergie als separate Istleistungsquelle mit optionalem SOC,
|
||||
Leistungsfaktor und getrennten Anzeigeoptionen fuer Energiefluss und Diagramme.
|
||||
SDL wird unabhaengig von der Anzeige aus Hauslast und neuer Hausenergie
|
||||
|
||||
@@ -144,6 +144,7 @@ class LadestationGateway extends IPSModule implements VerbraucherSchnittstelle
|
||||
|
||||
$this->initialisiereLokaleEinstellungen();
|
||||
$this->aktualisiereVariablen();
|
||||
$this->bereinigeUngueltigenSollwert();
|
||||
$this->WriteAttributeBoolean('GatewayVerbunden', false);
|
||||
$this->WriteAttributeInteger('LetzterGesetzterStrom', -1);
|
||||
$this->WriteAttributeBoolean('LadestartFuerVerbindungGesendet', false);
|
||||
@@ -179,7 +180,7 @@ class LadestationGateway extends IPSModule implements VerbraucherSchnittstelle
|
||||
$this->starteRegeluebergang();
|
||||
} else {
|
||||
$this->beendeRegeluebergang();
|
||||
$this->setzeZustand('SollwertGueltig', false);
|
||||
$this->verwerfeSollwert();
|
||||
}
|
||||
$this->aktualisiere(true);
|
||||
return;
|
||||
@@ -192,7 +193,7 @@ class LadestationGateway extends IPSModule implements VerbraucherSchnittstelle
|
||||
$this->starteRegeluebergang();
|
||||
} else {
|
||||
$this->beendeRegeluebergang();
|
||||
$this->setzeZustand('SollwertGueltig', false);
|
||||
$this->verwerfeSollwert();
|
||||
}
|
||||
$this->aktualisiere(true);
|
||||
return;
|
||||
@@ -215,7 +216,7 @@ class LadestationGateway extends IPSModule implements VerbraucherSchnittstelle
|
||||
|
||||
case 'VorgabeTimeout':
|
||||
$this->SetTimerInterval('VorgabeTimeout', 0);
|
||||
$this->setzeZustand('SollwertGueltig', false);
|
||||
$this->verwerfeSollwert();
|
||||
$this->aktualisiere(true);
|
||||
return;
|
||||
|
||||
@@ -322,7 +323,7 @@ class LadestationGateway extends IPSModule implements VerbraucherSchnittstelle
|
||||
true
|
||||
)
|
||||
) {
|
||||
$this->setzeZustand('SollwertGueltig', false);
|
||||
$this->verwerfeSollwert();
|
||||
$this->aktualisiere(false);
|
||||
}
|
||||
$this->SetTimerInterval('RueckmeldungVerzoegert', 100);
|
||||
@@ -559,7 +560,7 @@ class LadestationGateway extends IPSModule implements VerbraucherSchnittstelle
|
||||
if (in_array($sollleistung, $angebot, true)) {
|
||||
return $sollleistung;
|
||||
}
|
||||
$this->setzeZustand('SollwertGueltig', false);
|
||||
$this->verwerfeSollwert();
|
||||
}
|
||||
|
||||
if (
|
||||
|
||||
@@ -139,6 +139,7 @@ class LadestationStandAlone extends IPSModule implements VerbraucherSchnittstell
|
||||
|
||||
$this->initialisiereLokaleEinstellungen();
|
||||
$this->aktualisiereVariablen();
|
||||
$this->bereinigeUngueltigenSollwert();
|
||||
|
||||
// Ein persistiertes Ladeende nach Neueinrichtung oder Modulupdate einmal neu pruefen.
|
||||
$this->setzeZustand('FahrzeugGeladen', false);
|
||||
@@ -190,7 +191,7 @@ class LadestationStandAlone extends IPSModule implements VerbraucherSchnittstell
|
||||
$this->starteRegeluebergang();
|
||||
} else {
|
||||
$this->beendeRegeluebergang();
|
||||
$this->setzeZustand('SollwertGueltig', false);
|
||||
$this->verwerfeSollwert();
|
||||
}
|
||||
$this->aktualisiere(true);
|
||||
return;
|
||||
@@ -203,7 +204,7 @@ class LadestationStandAlone extends IPSModule implements VerbraucherSchnittstell
|
||||
$this->starteRegeluebergang();
|
||||
} else {
|
||||
$this->beendeRegeluebergang();
|
||||
$this->setzeZustand('SollwertGueltig', false);
|
||||
$this->verwerfeSollwert();
|
||||
}
|
||||
$this->aktualisiere(true);
|
||||
return;
|
||||
@@ -224,7 +225,7 @@ class LadestationStandAlone extends IPSModule implements VerbraucherSchnittstell
|
||||
|
||||
case 'VorgabeTimeout':
|
||||
$this->SetTimerInterval('VorgabeTimeout', 0);
|
||||
$this->setzeZustand('SollwertGueltig', false);
|
||||
$this->verwerfeSollwert();
|
||||
$this->aktualisiere(true);
|
||||
return;
|
||||
|
||||
@@ -275,7 +276,7 @@ class LadestationStandAlone extends IPSModule implements VerbraucherSchnittstell
|
||||
if ((bool) $this->leseZustand('SollwertGueltig')
|
||||
&& !in_array((int) $this->leseZustand('Sollleistung'), $this->leseLeistungsangebot(), true)
|
||||
) {
|
||||
$this->setzeZustand('SollwertGueltig', false);
|
||||
$this->verwerfeSollwert();
|
||||
$this->aktualisiere(false, false);
|
||||
}
|
||||
$this->SetTimerInterval('RueckmeldungVerzoegert', 100);
|
||||
@@ -560,7 +561,7 @@ class LadestationStandAlone extends IPSModule implements VerbraucherSchnittstell
|
||||
if (in_array($sollleistung, $angebot, true)) {
|
||||
return $sollleistung;
|
||||
}
|
||||
$this->setzeZustand('SollwertGueltig', false);
|
||||
$this->verwerfeSollwert();
|
||||
$ersatz = 0;
|
||||
foreach ($angebot as $leistungswert) {
|
||||
if ($leistungswert > $sollleistung) {
|
||||
|
||||
@@ -112,6 +112,7 @@ class VerbraucherPufferspeicher extends IPSModule implements VerbraucherSchnitts
|
||||
parent::ApplyChanges();
|
||||
|
||||
$this->aktualisiereVariablen();
|
||||
$this->bereinigeUngueltigenSollwert();
|
||||
try {
|
||||
$this->pruefeKonfiguration();
|
||||
} catch (Throwable $fehler) {
|
||||
@@ -150,7 +151,7 @@ class VerbraucherPufferspeicher extends IPSModule implements VerbraucherSchnitts
|
||||
case 'Aktiv':
|
||||
$this->SetValue('Aktiv', (bool) $wert);
|
||||
if (!(bool) $wert) {
|
||||
$this->setzeZustand('SollwertGueltig', false);
|
||||
$this->verwerfeSollwert();
|
||||
}
|
||||
$this->regelzyklus(true);
|
||||
return;
|
||||
@@ -208,7 +209,7 @@ class VerbraucherPufferspeicher extends IPSModule implements VerbraucherSchnitts
|
||||
if ((bool) $this->leseZustand('SollwertGueltig')
|
||||
&& !in_array((int) $this->leseZustand('Sollleistung'), $angebot, true)
|
||||
) {
|
||||
$this->setzeZustand('SollwertGueltig', false);
|
||||
$this->verwerfeSollwert();
|
||||
$this->regelzyklus(false);
|
||||
}
|
||||
$this->SetTimerInterval('RueckmeldungVerzoegert', 100);
|
||||
@@ -290,7 +291,7 @@ class VerbraucherPufferspeicher extends IPSModule implements VerbraucherSchnitts
|
||||
if ($letzteVorgabe <= 0
|
||||
|| $jetzt - $letzteVorgabe > $this->ReadPropertyInteger('VorgabeTimeout')
|
||||
) {
|
||||
$this->setzeZustand('SollwertGueltig', false);
|
||||
$this->verwerfeSollwert();
|
||||
}
|
||||
|
||||
$ziel = 0;
|
||||
@@ -301,7 +302,7 @@ class VerbraucherPufferspeicher extends IPSModule implements VerbraucherSchnitts
|
||||
} elseif ((bool) $this->leseZustand('SollwertGueltig')) {
|
||||
$ziel = (int) $this->leseZustand('Sollleistung');
|
||||
if (!in_array($ziel, $angebot, true)) {
|
||||
$this->setzeZustand('SollwertGueltig', false);
|
||||
$this->verwerfeSollwert();
|
||||
$ziel = 0;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -118,6 +118,7 @@ class VerbraucherEinStufig extends IPSModule implements VerbraucherSchnittstelle
|
||||
parent::ApplyChanges();
|
||||
|
||||
$this->aktualisiereVariablen();
|
||||
$this->bereinigeUngueltigenSollwert();
|
||||
$this->registriereMeldungen();
|
||||
|
||||
try {
|
||||
@@ -158,7 +159,7 @@ class VerbraucherEinStufig extends IPSModule implements VerbraucherSchnittstelle
|
||||
case 'Aktiv':
|
||||
$this->SetValue('Aktiv', (bool) $wert);
|
||||
if (!(bool) $wert) {
|
||||
$this->setzeZustand('SollwertGueltig', false);
|
||||
$this->verwerfeSollwert();
|
||||
$this->SetTimerInterval('VorgabeTimeout', 0);
|
||||
}
|
||||
$this->aktualisiere(true);
|
||||
@@ -214,7 +215,7 @@ class VerbraucherEinStufig extends IPSModule implements VerbraucherSchnittstelle
|
||||
if ((bool) $this->leseZustand('SollwertGueltig')
|
||||
&& !in_array((int) $this->leseZustand('Sollleistung'), $this->leseLeistungsangebot(), true)
|
||||
) {
|
||||
$this->setzeZustand('SollwertGueltig', false);
|
||||
$this->verwerfeSollwert();
|
||||
}
|
||||
$this->planeMeldung();
|
||||
return;
|
||||
@@ -254,7 +255,7 @@ class VerbraucherEinStufig extends IPSModule implements VerbraucherSchnittstelle
|
||||
true
|
||||
)
|
||||
) {
|
||||
$this->setzeZustand('SollwertGueltig', false);
|
||||
$this->verwerfeSollwert();
|
||||
}
|
||||
|
||||
$aktiv = (bool) $this->GetValue('Aktiv');
|
||||
@@ -474,7 +475,7 @@ class VerbraucherEinStufig extends IPSModule implements VerbraucherSchnittstelle
|
||||
if ($letzteVorgabe <= 0
|
||||
|| $jetzt - $letzteVorgabe >= $this->ReadPropertyInteger('VorgabeTimeout')
|
||||
) {
|
||||
$this->setzeZustand('SollwertGueltig', false);
|
||||
$this->verwerfeSollwert();
|
||||
$this->SetTimerInterval('VorgabeTimeout', 0);
|
||||
}
|
||||
}
|
||||
@@ -528,7 +529,7 @@ class VerbraucherEinStufig extends IPSModule implements VerbraucherSchnittstelle
|
||||
$this->WriteAttributeString('LaufzeitTag', date('Y-m-d', $jetzt));
|
||||
$this->WriteAttributeInteger('LaufzeitStandZeit', $jetzt);
|
||||
$this->setzeZustand('Tageslaufzeit', 0);
|
||||
$this->setzeZustand('SollwertGueltig', false);
|
||||
$this->verwerfeSollwert();
|
||||
$this->setzeZustand('Rueckmeldefehler', false);
|
||||
$this->WriteAttributeBoolean('Initialisiert', true);
|
||||
}
|
||||
|
||||
@@ -132,6 +132,7 @@ class VerbraucherWaermepumpe extends IPSModule implements VerbraucherSchnittstel
|
||||
parent::ApplyChanges();
|
||||
|
||||
$this->aktualisiereVariablen();
|
||||
$this->bereinigeUngueltigenSollwert();
|
||||
$this->registriereMeldungen();
|
||||
try {
|
||||
$this->pruefeKonfiguration();
|
||||
@@ -172,7 +173,7 @@ class VerbraucherWaermepumpe extends IPSModule implements VerbraucherSchnittstel
|
||||
case 'Aktiv':
|
||||
$this->SetValue('Aktiv', (bool) $wert);
|
||||
if (!(bool) $wert) {
|
||||
$this->setzeZustand('SollwertGueltig', false);
|
||||
$this->verwerfeSollwert();
|
||||
$this->SetTimerInterval('VorgabeTimeout', 0);
|
||||
}
|
||||
$this->aktualisiere(true);
|
||||
@@ -230,7 +231,7 @@ class VerbraucherWaermepumpe extends IPSModule implements VerbraucherSchnittstel
|
||||
if ((bool) $this->leseZustand('SollwertGueltig')
|
||||
&& !in_array((int) $this->leseZustand('Sollleistung'), $this->leseLeistungsangebot(), true)
|
||||
) {
|
||||
$this->setzeZustand('SollwertGueltig', false);
|
||||
$this->verwerfeSollwert();
|
||||
}
|
||||
$this->planeMeldung();
|
||||
return;
|
||||
@@ -286,7 +287,7 @@ class VerbraucherWaermepumpe extends IPSModule implements VerbraucherSchnittstel
|
||||
$this->WriteAttributeInteger('Laufbeginn', $laeuft ? $jetzt : 0);
|
||||
$this->schalte(WaermepumpenRegler::STEUERZUSTAND_NORMAL, $jetzt);
|
||||
$steuerzustand = WaermepumpenRegler::STEUERZUSTAND_NORMAL;
|
||||
$this->setzeZustand('SollwertGueltig', false);
|
||||
$this->verwerfeSollwert();
|
||||
}
|
||||
|
||||
$this->aktualisiereSperrerholung($laeuft, $jetzt);
|
||||
@@ -828,7 +829,7 @@ class VerbraucherWaermepumpe extends IPSModule implements VerbraucherSchnittstel
|
||||
$ablauf = $this->ReadAttributeInteger('LetzteVorgabeZeit')
|
||||
+ $this->ReadPropertyInteger('VorgabeTimeout');
|
||||
if ($this->ReadAttributeInteger('LetzteVorgabeZeit') <= 0 || $jetzt >= $ablauf) {
|
||||
$this->setzeZustand('SollwertGueltig', false);
|
||||
$this->verwerfeSollwert();
|
||||
$this->SetTimerInterval('VorgabeTimeout', 0);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -122,6 +122,7 @@ class VerbraucherWarmwassererwaermer extends IPSModule implements VerbraucherSch
|
||||
|
||||
$this->initialisiereTemperaturen();
|
||||
$this->aktualisiereVariablen();
|
||||
$this->bereinigeUngueltigenSollwert();
|
||||
|
||||
try {
|
||||
$this->pruefeKonfiguration();
|
||||
@@ -219,7 +220,7 @@ class VerbraucherWarmwassererwaermer extends IPSModule implements VerbraucherSch
|
||||
if ((bool) $this->leseZustand('SollwertGueltig')
|
||||
&& !in_array((int) $this->leseZustand('Sollleistung'), $angebot, true)
|
||||
) {
|
||||
$this->setzeZustand('SollwertGueltig', false);
|
||||
$this->verwerfeSollwert();
|
||||
$this->regelzyklus(false);
|
||||
}
|
||||
$this->SetTimerInterval('RueckmeldungVerzoegert', 100);
|
||||
@@ -264,7 +265,7 @@ class VerbraucherWarmwassererwaermer extends IPSModule implements VerbraucherSch
|
||||
if ($letzteVorgabe <= 0
|
||||
|| $jetzt - $letzteVorgabe > $this->ReadPropertyInteger('VorgabeTimeout')
|
||||
) {
|
||||
$this->setzeZustand('SollwertGueltig', false);
|
||||
$this->verwerfeSollwert();
|
||||
}
|
||||
|
||||
$ziel = 0;
|
||||
@@ -276,7 +277,7 @@ class VerbraucherWarmwassererwaermer extends IPSModule implements VerbraucherSch
|
||||
} elseif ((bool) $this->leseZustand('SollwertGueltig')) {
|
||||
$ziel = (int) $this->leseZustand('Sollleistung');
|
||||
if (!in_array($ziel, $angebot, true)) {
|
||||
$this->setzeZustand('SollwertGueltig', false);
|
||||
$this->verwerfeSollwert();
|
||||
$ziel = 0;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -41,6 +41,29 @@ berechnet sein Leistungsangebot neu und meldet es zurueck. Eine vorhandene
|
||||
Sollleistung wird dabei nur verworfen, wenn sie im neuen Angebot nicht mehr
|
||||
zulaessig ist.
|
||||
|
||||
### Verworfene Sollwerte und Anzeige
|
||||
|
||||
Beim Verwerfen einer gueltigen Vorgabe setzen alle Verbrauchermodule sowohl
|
||||
`SollwertGueltig=false` als auch den gespeicherten und gegebenenfalls sichtbaren
|
||||
Wert `Sollleistung=0`. An den Manager geht weiterhin `Sollleistung_W=null`;
|
||||
die Anzeige 0 W ist keine neue gueltige Manager-Vorgabe und kein Nachweis einer
|
||||
physisch ausgeschalteten Last.
|
||||
|
||||
Lokale Schutzprogramme, Mindestlaufzeiten und bestehende Lade-Uebergaenge
|
||||
bleiben unveraendert. Berechnet ein Modul danach eine lokale Sollleistung,
|
||||
darf es diese weiterhin anzeigen. Bei Ladestationen bleibt waehrend eines
|
||||
Regeluebergangs insbesondere der letzte Geraetebefehl erhalten, auch wenn die
|
||||
alte Manager-Vorgabe bereits verworfen und ihre Anzeige auf 0 gesetzt wurde.
|
||||
Wiederholte Verwerfungen einer bereits ungueltigen Manager-Vorgabe lassen eine
|
||||
inzwischen neu berechnete lokale Schutzleistung unveraendert.
|
||||
|
||||
Nach einem Modulupdate bereinigt `ApplyChanges` bereits gespeicherte ungueltige
|
||||
Altwerte. Gueltige Vorgaben einschliesslich 0 W und negativer Batterieleistung
|
||||
bleiben erhalten. Keine neuen Properties, Variablen-IDs oder Vertragsversion;
|
||||
es ist keine manuelle Konfigurationsmigration erforderlich. Das Update ist
|
||||
kontrolliert anzuwenden, da die regulaere Instanzinitialisierung wie bisher
|
||||
Geraeteaktionen ausloesen kann.
|
||||
|
||||
## Verbraucher an Manager
|
||||
|
||||
```json
|
||||
|
||||
@@ -5,13 +5,31 @@ declare(strict_types=1);
|
||||
namespace Belevo\EnelixEMS;
|
||||
|
||||
/**
|
||||
* Registriert die gemeinsamen Properties und Variablen aller EMS-Verbraucher.
|
||||
* Gemeinsame Registrierung und Sollwert-Bereinigung aller EMS-Verbraucher.
|
||||
*
|
||||
* Das Trait ist noch keine vollstaendige Steuerungsimplementierung. Die
|
||||
* konkreten Module ergaenzen Geraeteanbindung, Leistungsangebot und Zustand.
|
||||
*/
|
||||
trait VerbraucherBasisTrait
|
||||
{
|
||||
protected function verwerfeSollwert(): void
|
||||
{
|
||||
// Lokale Ersatzleistungen nicht bei jedem weiteren Timeout kurz auf 0 setzen.
|
||||
if (!(bool) $this->leseZustand('SollwertGueltig')) {
|
||||
return;
|
||||
}
|
||||
$this->setzeZustand('SollwertGueltig', false);
|
||||
$this->setzeZustand('Sollleistung', 0);
|
||||
}
|
||||
|
||||
protected function bereinigeUngueltigenSollwert(): void
|
||||
{
|
||||
// Auch vor dem Update gespeicherte, bereits ungueltige Vorgaben bereinigen.
|
||||
if (!(bool) $this->leseZustand('SollwertGueltig')) {
|
||||
$this->setzeZustand('Sollleistung', 0);
|
||||
}
|
||||
}
|
||||
|
||||
protected function registriereVerbraucherBasis(): void
|
||||
{
|
||||
$this->RegisterPropertyInteger('PrioritaetPV', 0);
|
||||
|
||||
@@ -133,6 +133,7 @@ PHP
|
||||
'GoodWe-Entladen verwendet negativen Managerwert und Modus 12',
|
||||
static function (TestContext $test) use (
|
||||
$managerdatenSenden,
|
||||
$batterieID,
|
||||
$modusID,
|
||||
$leistungID
|
||||
): void {
|
||||
@@ -141,6 +142,10 @@ PHP
|
||||
static fn (): bool => (float) GetValue($leistungID) === 843.0
|
||||
&& (int) GetValue($modusID) === 12
|
||||
);
|
||||
$test->assertSame(-843, GetValue($test->objectByIdent('Sollleistung', $batterieID)));
|
||||
IPS_RequestAction($batterieID, 'VorgabeTimeout', 0);
|
||||
$test->assertSame(false, GetValue($test->objectByIdent('SollwertGueltig', $batterieID)));
|
||||
$test->assertSame(0, GetValue($test->objectByIdent('Sollleistung', $batterieID)));
|
||||
}
|
||||
);
|
||||
|
||||
@@ -197,6 +202,7 @@ PHP
|
||||
$leistungID
|
||||
): void {
|
||||
$test->configureInstance($batterieID, ['Batteriemanagement' => 1]);
|
||||
$test->assertSame(0, GetValue($test->objectByIdent('Sollleistung', $batterieID)));
|
||||
$test->waitUntil(
|
||||
static fn (): bool => (float) GetValue($leistungID) === 0.0
|
||||
&& (int) GetValue($managementID) === 1
|
||||
|
||||
@@ -186,7 +186,7 @@ return static function (TestContext $test): void {
|
||||
|
||||
$test->runCase('Solarumschaltung wartet auf die neue Manager-Vorgabe', static function (
|
||||
TestContext $test
|
||||
) use ($station): void {
|
||||
) use ($station, $sendeBeobachtung): void {
|
||||
$managerId = $test->createInstance(
|
||||
'{6F771B18-59D4-4C8A-B951-3B2FE9F6A2C4}',
|
||||
'Hilfsmanager Easee-Uebergang',
|
||||
@@ -221,10 +221,11 @@ return static function (TestContext $test): void {
|
||||
(string) GetValue($test->objectByIdent('LetzterGeraetebefehl', $station))
|
||||
);
|
||||
$test->assertSame(
|
||||
4104,
|
||||
0,
|
||||
GetValue($test->objectByIdent('Sollleistung', $station)),
|
||||
'Die Sollleistung muss bis zur neuen Manager-Vorgabe stabil bleiben.'
|
||||
'Die verworfene Manager-Vorgabe darf nicht als aktuelle Sollleistung stehen bleiben.'
|
||||
);
|
||||
$test->assertSame(false, GetValue($test->objectByIdent('SollwertGueltig', $station)));
|
||||
|
||||
$sendeSollwert(10944);
|
||||
$test->assertTrue(str_contains(
|
||||
@@ -234,6 +235,25 @@ return static function (TestContext $test): void {
|
||||
|
||||
IPS_RequestAction($station, 'Solarladen', true);
|
||||
$sendeSollwert(0);
|
||||
$test->assertSame(true, GetValue($test->objectByIdent('SollwertGueltig', $station)));
|
||||
$test->assertSame(0, GetValue($test->objectByIdent('Sollleistung', $station)));
|
||||
|
||||
$sendeSollwert(10944);
|
||||
$sendeBeobachtung('EH123456', 109, 1);
|
||||
$test->assertSame('[0]', GetValue($test->objectByIdent('LeistungsangebotDiagnose', $station)));
|
||||
$test->assertSame(false, GetValue($test->objectByIdent('SollwertGueltig', $station)));
|
||||
$test->assertSame(0, GetValue($test->objectByIdent('Sollleistung', $station)));
|
||||
$test->assertTrue(str_contains(
|
||||
(string) GetValue($test->objectByIdent('LetzterGeraetebefehl', $station)),
|
||||
'"Ampere":0'
|
||||
));
|
||||
|
||||
$sendeBeobachtung('EH123456', 110, 30);
|
||||
$sendeBeobachtung('EH123456', 109, 3);
|
||||
$sendeSollwert(10944);
|
||||
IPS_RequestAction($station, 'VorgabeTimeout', 0);
|
||||
$test->assertSame(false, GetValue($test->objectByIdent('SollwertGueltig', $station)));
|
||||
$test->assertSame(0, GetValue($test->objectByIdent('Sollleistung', $station)));
|
||||
});
|
||||
|
||||
$test->runCase('SignalR-Abbruch erreicht die Ladestation', static function (
|
||||
|
||||
@@ -387,10 +387,11 @@ return static function (TestContext $test): void {
|
||||
'Die Umschaltung darf vor der neuen Manager-Vorgabe keinen Zwischenwert setzen.'
|
||||
);
|
||||
$test->assertSame(
|
||||
4104,
|
||||
0,
|
||||
GetValue($test->objectByIdent('Sollleistung', $stationId)),
|
||||
'Die Sollleistung muss bis zur neuen Manager-Vorgabe stabil bleiben.'
|
||||
'Die verworfene Manager-Vorgabe darf nicht als aktuelle Sollleistung stehen bleiben.'
|
||||
);
|
||||
$test->assertSame(false, GetValue($test->objectByIdent('SollwertGueltig', $stationId)));
|
||||
$angebot = (string) GetValue($test->objectByIdent('LeistungsangebotDiagnose', $stationId));
|
||||
$test->assertSame('[10944]', $angebot, 'PV ohne Solarladen muss nur das Maximum anbieten.');
|
||||
$abgewiesen = false;
|
||||
@@ -502,6 +503,29 @@ return static function (TestContext $test): void {
|
||||
);
|
||||
});
|
||||
|
||||
$test->runCase('Abziehen und Vorgabe-Timeout hinterlassen keine alte Sollleistung', static function (
|
||||
TestContext $test
|
||||
) use ($stationen, $goEAntwort, $anforderungSenden): void {
|
||||
$stationId = $stationen['go-e alt'];
|
||||
IPS_SetProperty($stationId, 'Testantwort', $goEAntwort(2, 10944, [160, 160, 160]));
|
||||
IPS_ApplyChanges($stationId);
|
||||
IPS_RequestAction($stationId, 'Aktiv', true);
|
||||
IPS_RequestAction($stationId, 'Solarladen', true);
|
||||
$anforderungSenden($stationId, 10944);
|
||||
$test->assertSame(10944, GetValue($test->objectByIdent('Sollleistung', $stationId)));
|
||||
|
||||
IPS_RequestAction($stationId, 'VorgabeTimeout', 0);
|
||||
$test->assertSame(false, GetValue($test->objectByIdent('SollwertGueltig', $stationId)));
|
||||
$test->assertSame(0, GetValue($test->objectByIdent('Sollleistung', $stationId)));
|
||||
|
||||
$anforderungSenden($stationId, 10944);
|
||||
IPS_SetProperty($stationId, 'Testantwort', $goEAntwort(1, 0));
|
||||
IPS_ApplyChanges($stationId);
|
||||
$test->assertSame('[0]', GetValue($test->objectByIdent('LeistungsangebotDiagnose', $stationId)));
|
||||
$test->assertSame(false, GetValue($test->objectByIdent('SollwertGueltig', $stationId)));
|
||||
$test->assertSame(0, GetValue($test->objectByIdent('Sollleistung', $stationId)));
|
||||
});
|
||||
|
||||
$test->runCase('Leistungswerte und Fahrzeugstatus folgen ihrer Sichtbarkeitsgruppe', static function (
|
||||
TestContext $test
|
||||
) use ($stationen): void {
|
||||
|
||||
@@ -105,6 +105,7 @@ return static function (TestContext $test): void {
|
||||
$test->assertSame(false, GetValue($test->objectByIdent('Heizbedarf', $verbraucherId)));
|
||||
|
||||
SetValue($pufferId, 55.0);
|
||||
$test->assertSame(0, GetValue($test->objectByIdent('Sollleistung', $verbraucherId)));
|
||||
IPS_RequestAction($verbraucherId, 'Melden', true);
|
||||
$test->assertSame([false, false], $kontaktzustand());
|
||||
});
|
||||
|
||||
@@ -225,4 +225,18 @@ return static function (TestContext $test): void {
|
||||
) === false);
|
||||
$test->assertInstanceStatus($verbraucherId);
|
||||
});
|
||||
|
||||
$test->runCase('Deaktivierung verwirft eine positive Vorgabe vollstaendig', static function (
|
||||
TestContext $test
|
||||
) use ($verbraucherId, $anforderungSenden): void {
|
||||
IPS_SetProperty($verbraucherId, 'Mindestlaufzeit', 0);
|
||||
IPS_SetProperty($verbraucherId, 'Mindesteinschaltdauer', 0);
|
||||
IPS_SetProperty($verbraucherId, 'Mindestausschaltdauer', 0);
|
||||
IPS_ApplyChanges($verbraucherId);
|
||||
$anforderungSenden(1200);
|
||||
$test->assertSame(1200, GetValue($test->objectByIdent('Sollleistung', $verbraucherId)));
|
||||
IPS_RequestAction($verbraucherId, 'Aktiv', false);
|
||||
$test->assertSame(false, GetValue($test->objectByIdent('SollwertGueltig', $verbraucherId)));
|
||||
$test->assertSame(0, GetValue($test->objectByIdent('Sollleistung', $verbraucherId)));
|
||||
});
|
||||
};
|
||||
|
||||
@@ -121,6 +121,8 @@ return static function (TestContext $test): void {
|
||||
TestContext $test
|
||||
) use ($waermepumpe, $kontakt1, $kontakt2): void {
|
||||
IPS_RequestAction($waermepumpe, 'Aktiv', false);
|
||||
$test->assertSame(false, GetValue($test->objectByIdent('SollwertGueltig', $waermepumpe)));
|
||||
$test->assertSame(0, GetValue($test->objectByIdent('Sollleistung', $waermepumpe)));
|
||||
IPS_RequestAction($waermepumpe, 'Aktiv', true);
|
||||
$test->waitUntil(
|
||||
static fn (): bool => GetValue($kontakt1) === false
|
||||
|
||||
@@ -110,6 +110,33 @@ return static function (TestContext $test): void {
|
||||
$temperaturSetzen(52.0);
|
||||
});
|
||||
|
||||
$test->runCase('Abgelaufene Vorgabe wird auch in der Anzeige verworfen', static function (
|
||||
TestContext $test
|
||||
) use ($verbraucherId, $managerId, $kontakte): void {
|
||||
IPS_SetProperty($verbraucherId, 'VorgabeTimeout', 1);
|
||||
IPS_ApplyChanges($verbraucherId);
|
||||
IPS_RequestAction($verbraucherId, 'Aktiv', true);
|
||||
IPS_RequestAction($verbraucherId, 'ManagerdatenEmpfangen', json_encode([
|
||||
'Kopf' => [
|
||||
'Version' => '4.0',
|
||||
'AbsenderID' => $managerId,
|
||||
'EmpfaengerID' => $verbraucherId,
|
||||
'Zeitpunkt' => time(),
|
||||
],
|
||||
'Betriebsart' => 'PV',
|
||||
'Sollleistung_W' => 1000,
|
||||
], JSON_THROW_ON_ERROR));
|
||||
$test->assertSame(1000, GetValue($test->objectByIdent('Sollleistung', $verbraucherId)));
|
||||
IPS_Sleep(2100);
|
||||
IPS_RequestAction($verbraucherId, 'Melden', true);
|
||||
$test->assertSame(false, GetValue($test->objectByIdent('SollwertGueltig', $verbraucherId)));
|
||||
$test->assertSame(0, GetValue($test->objectByIdent('Sollleistung', $verbraucherId)));
|
||||
$test->waitUntil(static fn (): bool => GetValue($kontakte[0]) === false);
|
||||
IPS_RequestAction($verbraucherId, 'Aktiv', false);
|
||||
IPS_SetProperty($verbraucherId, 'VorgabeTimeout', 120);
|
||||
IPS_ApplyChanges($verbraucherId);
|
||||
});
|
||||
|
||||
if ($lizenzcode === '') {
|
||||
$test->runCase('Manager bleibt ohne Lizenz sicher gesperrt', static function (
|
||||
TestContext $test
|
||||
|
||||
@@ -9,6 +9,86 @@ use PHPUnit\Framework\TestCase;
|
||||
|
||||
final class VerbraucherBasisTraitTest extends TestCase
|
||||
{
|
||||
/** @dataProvider sollwerte */
|
||||
public function testVerwerfenLoeschtGespeicherteUndSichtbareVorgabe(int $leistung, bool $sichtbar): void
|
||||
{
|
||||
$modul = new VerbraucherBasisDummy();
|
||||
$modul->zustand = ['Sollleistung' => $leistung, 'SollwertGueltig' => true];
|
||||
$modul->sichtbareWerte = $sichtbar ? $modul->zustand : [];
|
||||
|
||||
$modul->verwerfen();
|
||||
$modul->verwerfen();
|
||||
|
||||
self::assertSame(['Sollleistung' => 0, 'SollwertGueltig' => false], $modul->zustand);
|
||||
self::assertSame($sichtbar ? $modul->zustand : [], $modul->sichtbareWerte);
|
||||
}
|
||||
|
||||
/** @dataProvider sollwerte */
|
||||
public function testUpdateBereinigtAlteUngueltigeVorgaben(int $leistung, bool $sichtbar): void
|
||||
{
|
||||
$modul = new VerbraucherBasisDummy();
|
||||
$modul->zustand = ['Sollleistung' => $leistung, 'SollwertGueltig' => false];
|
||||
$modul->sichtbareWerte = $sichtbar ? $modul->zustand : [];
|
||||
|
||||
$modul->bereinigen();
|
||||
|
||||
self::assertSame(['Sollleistung' => 0, 'SollwertGueltig' => false], $modul->zustand);
|
||||
self::assertSame($sichtbar ? $modul->zustand : [], $modul->sichtbareWerte);
|
||||
}
|
||||
|
||||
/** @dataProvider sollwerte */
|
||||
public function testUpdateErhaeltGueltigeVorgabenAuchNullUndEntladen(int $leistung, bool $sichtbar): void
|
||||
{
|
||||
$modul = new VerbraucherBasisDummy();
|
||||
$modul->zustand = ['Sollleistung' => $leistung, 'SollwertGueltig' => true];
|
||||
$modul->sichtbareWerte = $sichtbar ? $modul->zustand : [];
|
||||
$vorher = $modul->zustand;
|
||||
|
||||
$modul->bereinigen();
|
||||
|
||||
self::assertSame($vorher, $modul->zustand);
|
||||
self::assertSame($sichtbar ? $vorher : [], $modul->sichtbareWerte);
|
||||
}
|
||||
|
||||
public static function sollwerte(): array
|
||||
{
|
||||
return [[10944, true], [10944, false], [-843, true], [-843, false], [0, true], [0, false]];
|
||||
}
|
||||
|
||||
public function testWiederholtesVerwerfenLaesstNeuBerechneteLokaleSchutzleistungStehen(): void
|
||||
{
|
||||
$modul = new VerbraucherBasisDummy();
|
||||
$modul->zustand = ['Sollleistung' => 3000, 'SollwertGueltig' => false];
|
||||
$modul->sichtbareWerte = $modul->zustand;
|
||||
|
||||
$modul->verwerfen();
|
||||
|
||||
self::assertSame(['Sollleistung' => 3000, 'SollwertGueltig' => false], $modul->zustand);
|
||||
self::assertSame($modul->zustand, $modul->sichtbareWerte);
|
||||
}
|
||||
|
||||
public function testAlleVerbraucherVerwerfenSollwerteUeberDieGemeinsameFunktion(): void
|
||||
{
|
||||
$anzahl = 0;
|
||||
foreach (glob(__DIR__ . '/../*/module.php') as $datei) {
|
||||
$quelle = (string) file_get_contents($datei);
|
||||
if (!str_contains($quelle, 'implements VerbraucherSchnittstelle')) {
|
||||
continue;
|
||||
}
|
||||
++$anzahl;
|
||||
self::assertStringContainsString('use VerbraucherBasisTrait;', $quelle, $datei);
|
||||
self::assertStringContainsString('$this->verwerfeSollwert();', $quelle, $datei);
|
||||
self::assertStringNotContainsString("setzeZustand('SollwertGueltig', false)", $quelle, $datei);
|
||||
self::assertStringNotContainsString("WriteAttributeBoolean('ZustandSollwertGueltig', false)", $quelle, $datei);
|
||||
self::assertStringContainsString(
|
||||
'$this->aktualisiereVariablen();' . "\n " . '$this->bereinigeUngueltigenSollwert();',
|
||||
$quelle,
|
||||
$datei
|
||||
);
|
||||
}
|
||||
self::assertSame(7, $anzahl);
|
||||
}
|
||||
|
||||
public function testGemeinsamePropertiesUndVariablenWerdenRegistriert(): void
|
||||
{
|
||||
$modul = new VerbraucherBasisDummy();
|
||||
@@ -50,6 +130,35 @@ final class VerbraucherBasisDummy
|
||||
{
|
||||
use VerbraucherBasisTrait;
|
||||
|
||||
/** @var array<string, int|bool> */
|
||||
public array $zustand = [];
|
||||
|
||||
/** @var array<string, int|bool> */
|
||||
public array $sichtbareWerte = [];
|
||||
|
||||
public function verwerfen(): void
|
||||
{
|
||||
$this->verwerfeSollwert();
|
||||
}
|
||||
|
||||
public function bereinigen(): void
|
||||
{
|
||||
$this->bereinigeUngueltigenSollwert();
|
||||
}
|
||||
|
||||
private function setzeZustand(string $ident, $wert): void
|
||||
{
|
||||
$this->zustand[$ident] = $wert;
|
||||
if (array_key_exists($ident, $this->sichtbareWerte)) {
|
||||
$this->sichtbareWerte[$ident] = $wert;
|
||||
}
|
||||
}
|
||||
|
||||
private function leseZustand(string $ident)
|
||||
{
|
||||
return $this->zustand[$ident];
|
||||
}
|
||||
|
||||
/** @var array<string, mixed> */
|
||||
public array $properties = [];
|
||||
|
||||
|
||||
Reference in New Issue
Block a user