hoylabs / OpenDTU-OnBattery

Software for ESP32 to talk to Hoymiles/TSUN/Solenso Inverters, VE.Direct devices, battery management systems, and related peripherals
GNU General Public License v2.0
301 stars 63 forks source link

feature: DPL: allow overscaling to compensate for shading #956

Closed AndreasBoehm closed 3 months ago

AndreasBoehm commented 5 months ago

Fixes https://github.com/helgeerbe/OpenDTU-OnBattery/issues/917 based on the discussion https://github.com/helgeerbe/OpenDTU-OnBattery/discussions/819

Notes

Config Scaling result
Screenshot 2024-05-13 at 09 49 23 Screenshot 2024-05-13 at 09 48 46

Console

10:00:54.585 > [DPL::loop] ******************* ENTER **********************
10:00:54.597 > [DPL::calcPowerLimit] battery use prevented, solar power (DC): 10000 W
10:00:54.617 > [DPL::calcPowerLimit] target consumption: -150 W, base load: 100 W, power meter does include inverter output
10:00:54.628 > [DPL::calcPowerLimit] power meter value: -115 W, power meter valid: yes, inverter output: 235 W, solar power (AC): 9219 W
10:00:54.633 > [DPL::calcPowerLimit] limited to solar power: 270 W
10:00:54.640 > [DPL::setNewPowerLimit] input limit: 270 W, min limit: 40 W, max limit: 1600 W, hysteresis: 5 W
10:00:54.666 > [DPL::scalePowerLimit] 2/4 channels are producing less than expected, scaling from 270 to 324 W
10:00:54.671 > [DPL::setNewPowerLimit] inverter max: 1600 W, inverter is producing, requesting: 324 W, reported: 240 W, diff: 84 W
10:00:54.677 > [DPL::updateInverter] sending limit of 20.2 % (324 W respectively), max output is 1600 W
schlimmchen commented 5 months ago

@AndreasBoehm I allowed myself to rebase this onto the current development branch before asking users to review your work.

schlimmchen commented 5 months ago

@greymda @spcqike @hex2647 Please test this feature by flashing the firmware built in this PR's build-run.

greymda commented 5 months ago

i don't have access any more to the partially shaded setup :(

spcqike commented 5 months ago

Kann es sein dass es ein Problem mit HMS wechselrichter und neuer Firmware gab? Oder liegt es am PR? Ich bekomme seit dem Update keine Verbindung mehr zum HMS.

schlimmchen commented 5 months ago

Benutzt du einen Reverse Proxy oder hast sonst irgendein Setup, das verhindert, dass die Websocket-Verbindung zustande kommt? Oder geht es nicht um das LiveView, sondern dass der Inverter nicht gepollt werden kann? Was steht in der Konsole?

spcqike commented 5 months ago

Kein peoxy. Direkt die IP der openDTU. Er empfängt gar nichts vom wechselrichter

Naja. Da steht nicht viel.

All missing
17:03:43.240 > Nothing received, resend whole request
17:03:43.738 > Websocket: [/livedata][6] disconnect
17:03:44.048 > All missing
17:03:44.058 > Nothing received, resend whole request
17:03:44.864 > All missing
17:03:44.907 > Nothing received, resend whole request
17:03:45.566 > All missing
17:03:45.576 > Nothing received, resend count exeeded
17:03:45.888 > All missing
17:03:45.896 > Nothing received, resend whole request
17:03:46.195 > All missing
17:03:46.240 > Nothing received, resend whole request
17:03:46.502 > All missing
17:03:46.544 > Nothing received, resend whole request
17:03:46.714 > All missing
17:03:46.748 > Nothing received, resend whole request
17:03:46.912 > All missing
17:03:46.951 > Nothing received, resend count exeeded
17:03:46.958 > Fetch inverter: 116492305207
17:03:46.965 > Request SystemConfigPara
17:03:46.972 > All missing
17:03:46.980 > Nothing received, resend whole request
17:03:46.988 > All missing
17:03:46.997 > Nothing received, resend whole request
17:03:47.033 > All missing
17:03:47.041 > Nothing received, resend whole request
17:03:47.085 > All missing
17:03:47.093 > Nothing received, resend whole request
17:03:47.101 > All missing
17:03:47.109 > Nothing received, resend count exeeded
17:03:47.707 > All missing
17:03:47.717 > Nothing received, resend whole request
schlimmchen commented 5 months ago

Begreif ich nicht. Hat sich an den Einstellungen des CMT etwas verändert? Ich hab ja ein HMT und keine Probleme...

spcqike commented 5 months ago

Nein. Daran hat sich nichts geändert.

Ich weiß allerdings nicht, wie lange ich kein Update gemacht habe. Wenn irgendwas die Kommunikation zerschossen hat, könnte das auch schon länger her sein. Wobei es dann wohl mehr issues geben würde. Und das letzte war ja wegen dem Proxy, oder?

spcqike commented 5 months ago

Ich weiß nicht hat genau warum, aber es scheint an den DTU Einstellungen zu liegen.

Ich habe in der Vergangenheit, da ich Signal Probleme hatte, die Frequenz und die sendeleistung leicht erhöht.

Damit der DTU den wechselrichter nach einem Update wieder findet oder anspricht, reicht es, in den DtU Einstellungen bspw verbose logging zu aktivieren und zu speichern. Den Rest kann ich so lassen wie es ist. Logging kann danach auch wieder aus gemacht werden. Hauptsache das speichern wird einmal ausgeführt.

Das konnte ich jetzt sowohl mit der Firmware aus dem PR als auch mit dem latest release und einem Release aus dem Februar reproduzieren.

So, es läuft also. Und irgendwie lag es (halb?) an mir. Aber dennoch komisch. Leider ist jetzt die Sonne weg um die Anpassung zu testen :)

Nachtrag; Es reicht einfach so auf speichern zu drücken. Ohne Änderungen. Und auch ein reiner Neustart der DTU genüg für das Problem. Scheinbar.

schlimmchen commented 5 months ago

Und auch ein reiner Neustart der DTU genüg für das Problem. Scheinbar.

Sicher?

Es gab da jedenfalls Probleme mit den Einstellungen. Die hatten mit der Frequenzauswahl zu tun. Da musste man dann den Schieber einmal bewegen und speichern, sodass ein gültiger Wert abgespeichert wurde.

spcqike commented 5 months ago

Sicher?

grad nochmal getestet. Ja. Neustart, 30 Sekunden kein Empfang. Einstellungen ->DTU -> Speicher , 3 sek später die live Daten.

hex2647 commented 5 months ago

@greymda @spcqike @hex2647 Please test this feature by flashing the firmware built in this PR's build-run.

Ist installiert und aktiviert... morgen ist bei mir keine Verschattung zu erwarten aber das lässt sich ja simulieren :) bin gespannt.

AndreasBoehm commented 5 months ago

Es sieht so aus als ob ich die Logik nochmal überarbeiten muss, habe zwei Eingänge mit 50W und zwei die bis zu 100w bekommen. Netzbezug ist auf -100W gestellt, trotzdem regelt die Überskalierung effektiv auf -200W.

Konnte jemand von euch ein ähnliches Problem feststellen?

hex2647 commented 5 months ago

Das bisher noch nicht. Was mir vorhin aufgefallen war ist das er total instabil war, also das die Regelung extrem geschwankt hat… ich Versuch das nachher mal festzuhalten und besser darzustellen…

spcqike commented 5 months ago

Hab es auch grad getestet. Schwankt stark. Entweder voll offen (2.000W) oder das normale Limit, welches nicht ausreicht

image

hab zum testen 1 Paneel abgesteckt und das Target grad auf 800W gestellt.

AndreasBoehm commented 4 months ago

Danke fürs testen @spcqike und @hex2647. Ich habe den Fehler für die instabile und schwankende Regelung und auch den Fehler in der Berechnung für das Limit behoben. Vorerst zähle ich einen Eingang der 95% des Limits liefert als nicht limitiert um bei minimalen Schwankungen nicht zu viel zu skalieren, was haltet ihr davon?

@schlimmchen Könntest du den workflow erneut freigeben um neue test builds bereitzustellen? Danke.

schlimmchen commented 4 months ago

Neue Firmware: https://github.com/helgeerbe/OpenDTU-OnBattery/actions/runs/9054654684

spcqike commented 4 months ago

Vorerst zähle ich einen Eingang der 95% des Limits liefert als nicht limitiert um bei minimalen Schwankungen nicht zu viel zu skalieren, was haltet ihr davon?

ich weiß nicht, ob das so hinkommt.

auto expectedPowerPerChannel = (newLimit / dcTotalChnls) * 0.95;

        size_t dcLimitedChnls = 0;
        auto limitedChannelPowerSum = 0.0;

        for (auto& c : dcChnls) {
            auto channelPower = inverter->Statistics()->getChannelFieldValue(TYPE_DC, c, FLD_PDC);

            if (channelPower < expectedPowerPerChannel) {
                dcLimitedChnls++;
                limitedChannelPowerSum += channelPower;
            }
        }

vielleicht verstehe ich auch nur die Variablen falsch, aber sollte man nicht die nicht begrenzten Eingänge zählen? und sollte man nicht gegen das alte Limit vergleichen? Sollte es nicht eher so werden?

auto expectedPowerPerChannel = (currentLimitWatts/ dcTotalChnls) / 0.95;

        size_t dcNotLimitedChnls = 0;
        auto notLimitedChannelPowerSum = 0.0;

        for (auto& c : dcChnls) {
            auto channelPower = inverter->Statistics()->getChannelFieldValue(TYPE_DC, c, FLD_PDC);

            if (channelPower < expectedPowerPerChannel) {
                dcNotLimitedChnls ++;
                notLimitedChannelPowerSum += channelPower;
            }
        }

        if (dcNotLimitedChnls == 0 || dcNotLimitedChnls == dcTotalChnls) { return newLimit; }

        auto overScaled = static_cast<int32_t>((newLimit - notLimitedChannelPowerSum ) /(dcTotalChnls-dcNotLimitedChnls) * dcTotalChnls);

        MessageOutput.printf("[DPL::scalePowerLimit] %d/%d channels are producing less than expected, "
                "scaling from %d to %d W\r\n", dcNotLimitedChnls , dcTotalChnls, newLimit, overScaled);
        return overScaled;

Wie oben geschrieben, müsste 1. anhand des aktuell gültigen Limits verglichen werden. (Wenn das Limit bspw. von 1000W auf 300W fällt, und man die aktuelle DC Leistung gegen das neue Limit vergleicht, liefern alle DC Eingänge zu viel) Dann müsste 2. herausgefunden werden, welche Eingänge NICHT durch das Software-Limit begrenzt sind (sondern durch Verschattung). die Summe der "unter performenden" Eingänge und deren Leistung ist wichtig.

Ob man nun fixe 95% annimmt, oder die aktuelle Effizienz, oder den Wert einfach bei 1 belässt (immerhin wird die erwartete DC Leistung dadurch nur erhöht. DC-seitig liefern die Eingänge immer mehr, als man AC-seitig haben will.), kann man ja einfach ausprobieren.

Was man vielleicht noch einbauen sollte

 if (newLimit < currentLimitWatts) { return newLimit; }

Die Skalierung braucht nicht gemacht zu werden, wenn das Limit sich verkleinert. Die Berechnung

auto overScaled = static_cast<int32_t>((newLimit - limitedChannelPowerSum) / dcNonLimitedChnls * dcTotalChnls);

wird nicht sinnvoll klappen, wenn das neue Limit, durch Verbrauchsreduzierung, wesentlich kleiner wird. im Gegenteil, extrem Beispiel: das alte LImit war 800W, das neue ist 50W. Was passiert da?

AndreasBoehm commented 4 months ago

vielleicht verstehe ich auch nur die Variablen falsch, aber sollte man nicht die nicht begrenzten Eingänge zählen? und sollte man nicht gegen das alte Limit vergleichen? Sollte es nicht eher so werden? Ich hab die Variablen umbenannt um deutlich zu machen das in meinem Fall "limited" ein "limited by shading" war und nicht "limited by inverter limit". Eventuell kannst du mit dieser Info meine Berechnungen nachvollziehen.

auto expectedPowerPerChannel = (currentLimitWatts/ dcTotalChnls) / 0.95;
Hast du hier eine Effizienz von 95% angenommen um den AC wert von 'currentLimitWatts' in DC zu wandeln?

        size_t dcNotLimitedChnls = 0;
        auto notLimitedChannelPowerSum = 0.0;

        for (auto& c : dcChnls) {
            auto channelPower = inverter->Statistics()->getChannelFieldValue(TYPE_DC, c, FLD_PDC);

            if (channelPower < expectedPowerPerChannel) {
                dcNotLimitedChnls ++;
                notLimitedChannelPowerSum += channelPower;
            }
        }

        if (dcNotLimitedChnls == 0 || dcNotLimitedChnls == dcTotalChnls) { return newLimit; }

        auto overScaled = static_cast<int32_t>((newLimit - notLimitedChannelPowerSum ) /(dcTotalChnls-dcNotLimitedChnls) * dcTotalChnls);

        MessageOutput.printf("[DPL::scalePowerLimit] %d/%d channels are producing less than expected, "
                "scaling from %d to %d W\r\n", dcNotLimitedChnls , dcTotalChnls, newLimit, overScaled);
        return overScaled;

Wie oben geschrieben, müsste 1. anhand des aktuell gültigen Limits verglichen werden. (Wenn das Limit bspw. von 1000W auf 300W fällt, und man die aktuelle DC Leistung gegen das neue Limit vergleicht, liefern alle DC Eingänge zu viel) Dann müsste 2. herausgefunden werden, welche Eingänge NICHT durch das Software-Limit begrenzt sind (sondern durch Verschattung). die Summe der "unter performenden" Eingänge und deren Leistung ist wichtig.

Du hast recht, da hatte ich einen Fehler in meiner Logik, ich werde den Code anpassen und das aktuelle Limit verwenden um zu ermitteln ob ein Eingang verschattet ist.

Ob man nun fixe 95% annimmt, oder die aktuelle Effizienz, oder den Wert einfach bei 1 belässt (immerhin wird die erwartete DC Leistung dadurch nur erhöht. DC-seitig liefern die Eingänge immer mehr, als man AC-seitig haben will.), kann man ja einfach ausprobieren.

Ich denke du vermischt hier zwei Dinge a) AC <-> DC Umwandlung und die Effizienz davon und b) Threshold der z.b. auch bei 61 Watt bei geforderten 64 Watt den Eingang als non shaded wertet.

a) werde ich sobald die Regelung klappt noch mit einbauen, denn nur dann entspricht das Limit auch wirklich dem was man erwartet. b) sollten wir diskutieren, aktuell nutze ich hier 95%

Was man vielleicht noch einbauen sollte

 if (newLimit < currentLimitWatts) { return newLimit; }

Das kann man pauschal so nicht machen, denn newLimit wird immer kleiner sein als currentLimitWatts wenn wir aktuell im 'Overscaling' sind, auch kann das neue Limit kleiner sein aber es trotzdem bedarf geben eine Verschattung auszugleichen.

Die Skalierung braucht nicht gemacht zu werden, wenn das Limit sich verkleinert. Die Berechnung

auto overScaled = static_cast<int32_t>((newLimit - limitedChannelPowerSum) / dcNonLimitedChnls * dcTotalChnls);

wird nicht sinnvoll klappen, wenn das neue Limit, durch Verbrauchsreduzierung, wesentlich kleiner wird. im Gegenteil, extrem Beispiel: das alte LImit war 800W, das neue ist 50W. Was passiert da?

Dafür gibt es eine extra Abfrage die einfach newLimit zurück gibt wenn alle Eingänge die Erwartungen erfüllen. Gibt dann ja keinen 'shaded channel'.

AndreasBoehm commented 4 months ago

Was man vielleicht noch einbauen sollte

 if (newLimit < currentLimitWatts) { return newLimit; }

Die Skalierung braucht nicht gemacht zu werden, wenn das Limit sich verkleinert.

Da wir nun 'currentLimitWatts' zur Berechnung nutzen habe ich verstanden warum du diesen Vorschlag bringst. Ich würde vorschlagen das wir in dem fall aber dann einfach mit 'newLimit' prüfen ob wir einen verschatteten Eingang haben um gleich korrekt zu skalieren. Was denkst du?

spcqike commented 4 months ago

Hast du hier eine Effizienz von 95% angenommen um den AC wert von 'currentLimitWatts' in DC zu wandeln?

naja, die 95% habe ich von dir übernommen, aber ja 😄 dazu habe ich ja noch folgende Gedanken gehabt

Ob man nun fixe 95% annimmt, oder die aktuelle Effizienz, oder den Wert einfach bei 1 belässt (immerhin wird die erwartete DC Leistung dadurch nur erhöht. DC-seitig liefern die Eingänge immer mehr, als man AC-seitig haben will.), kann man ja einfach ausprobieren.

Muss man halt mal gucken, ob und wie 95%, die tatsächliche Effizienz oder aber auch ne "1" sich auswirken. die DC Leistung ist definitiv immer höher als die AC Leistung. Es wäre also falsch, das (lastLimit / dcTotalChnls)*factor anzunehmen, da der Erwartungswert damit immer kleiner wird und Eingänge als "gesättigt" bzw. durch den Software-Limiter begrenzt interpretiert werden, obwohl sie es nicht sind.

Ich denke du vermischt hier zwei Dinge a) AC <-> DC Umwandlung und die Effizienz davon und b) Threshold der z.b. auch bei 61 Watt bei geforderten 64 Watt den Eingang als non shaded wertet.

a) werde ich sobald die Regelung klappt noch mit einbauen, denn nur dann entspricht das Limit auch wirklich dem was man erwartet. b) sollten wir diskutieren, aktuell nutze ich hier 95%

Tue ich das? Hier ein Auszug meines HMS-2000 grafik

Das Limit ist 600W, jeder Eingang kann also 150W, die Effizienz ist aktuell ~ 95%.

auto expectedPowerPerChannel = (currentLimitWatts/ dcTotalChnls) / 0.95; liefert also 157.9W zurück. Jeder Eingang liefert (leicht) mehr, ist also rein durch den Limiter begrenzt.

auto expectedPowerPerChannel = (currentLimitWatts/ dcTotalChnls); würde halt rein 150W zurück geben, auch da liegt jeder Eingang drüber.

welchen Threshold wir annehmen können, sollten wir testen. Sauberer wäre wahrscheinlich der erste, da ein EIngang, der in diesem Fall "nur" 155W liefert, tatsächlich nicht sein Maximum erreicht 😄 aber ob die fehlenden ~2W pro Eingang am Ende ins Gewicht fallen? (wobei 5% Abweichung bei angenommenen 1500W Limit bereits 75W ausmachen können ..... 🤔)

Das kann man pauschal so nicht machen, denn newLimit wird immer kleiner sein als currentLimitWatts wenn wir aktuell im 'Overscaling' sind

da hast du natürlich recht.

Ich würde vorschlagen das wir in dem fall aber dann einfach mit 'newLimit' prüfen ob wir einen verschatteten Eingang haben um gleich korrekt zu skalieren. Was denkst du?

klingt sinnig. aber wie du auch korrekt feststellst newLimit wird immer kleiner sein als currentLimitWatts wenn wir aktuell im 'Overscaling' sind damit trifft es ja wieder immer zu, oder? 😞

ach, ärgerlich. ich habe meinen Branch leider bereits gelöscht, hatte doch aber genau solch eine Regelung bereits laufen 😄 inkl. der Probleme des Überschwingens und der Beseitigung derer https://github.com/helgeerbe/OpenDTU-OnBattery/pull/241

spcqike commented 4 months ago

Nachtrag:

Was ich in meinem ehemaligen PR noch sehe: ich hatte ne Abfrage, ob die tatsächliche AC Ausgangsleistung < dem newLimit ist

maxPower >= _lastRequestedPowerLimit / dcTotalChnls && inverter->Statistics()->getChannelFieldValue(TYPE_AC, (ChannelNum_t)config.PowerLimiter_InverterChannelId, FLD_PAC) < newPowerLimit

Nicht schön, aber die Abfrage ist ja quasi "maxPower (irgendeines Eingangs) >= durch den Limiter begrenzte Leistung (hier ohne Berücksichtigung der Effizienz) UND AC Leistung des Inverters < newPowerLimit". Wenn also mindestens 1 Eingang durch den Limiter begrenzt ist, also mehr liefern könnte, und das AC Limit dennoch nicht erreicht wird.

spcqike commented 4 months ago

Ich nochmal:

Ich hab mir die Anpassungen nochmal angeguckt, vielleichts liegts ja an mir / meinem Verständnis, aber ist das nicht doch falsch=

auto expectedAcPowerPerChannel = (newLimit / dcTotalChnls) * 0.95;

und später

            auto channelPowerDC = inverter->Statistics()->getChannelFieldValue(TYPE_DC, c, FLD_PDC);

            if (channelPowerDC < expectedAcPowerPerChannel) {
                //shaded channel

Du berechnest einen zu erwartenden AC Leistungswert pro Eingang und vergleichst diesen später mit der DC Eingangsleistung?

Wäre es nicht besser, den DC Anteil pro Eingang zu berechnen und dann DC mit DC zu vergleichen?

Wenn ich deine Berechnung richtig verstehe, unter der Annahme eines HM-600 und 300W limit. Jeder Eingang muss, nach deiner berechnung 300/2*0.95 -> 142.5W DC liefern. alles unter 142.5W wird als verschattet angenommen.

Wenn wir also 158W und 145W annehmen, ist das System stabil und nicht verschattet, auch wenn uns 13W AC-seitig fehlen (158+145 -> 303W DC; 95% Effizienz -> ~287W AC output) bei höheren Leistungen driftet es noch weiter auseinander, ohne dass das System skalieren würde. (bspw. der HMS-2000, mit 1500W Limit. bei deiner Berechnung wären 356W ok und nicht verschattet. in Wahrheit misst er aber 403W pro Eingang, immerhin knapp 50W pro Eingang mehr)

Wäre es nicht besser direkt in DC zu rechnen?

auto expectedDcPowerPerChannel = (currentLimitWatts/ dcTotalChnls) / 0.95;

gäbe 158W DC pro nicht verschatteten Eingang, bzw. für einen rein durch das Softwarelimit begrenzten Eingang.

Wenn ich so drüber nachdenke, glaube ich, dass der Punkt

maxPower >= _lastRequestedPowerLimit / dcTotalChnls && inverter->Statistics()->getChannelFieldValue(TYPE_AC, (ChannelNum_t)config.PowerLimiter_InverterChannelId, FLD_PAC) < newPowerLimit doch recht wichtig ist bzw. damals war. Dass die Skalierung stattfindet, wenn wenigstens 1 Eingang durch den Wechselrichter limitiert ist und die aktuelle AC Leistung dem neuen Limit nicht gerecht wird.

AndreasBoehm commented 4 months ago

@spcqike Danke für deine Infos und Gedanken.

Ich habe jetzt alles umgestellt auf AC, damit lässt sich sinnvoller mit dem aktuellen Limit vergleichen und auch besser das neue Limit berechnen.

Habe auch noch ein paar mehr Regeln hinzugefügt um sicherzugehen das wir weiter hochskalieren wenn das Limit noch nicht ausreicht um die gewünschte Energie zu liefern und auch um das Limit wieder zu senken falls gefordert, ohne das uns die skalierung dazwischen kommt.

Ich würde mich freuen wenn du nochmal drüber schaust und probierst ob jetzt alles funktioniert.

@schlimmchen Könntest du den workflow bitte erneut freigeben? Danke.

AndreasBoehm commented 4 months ago

@greymda @spcqike @hex2647 Please test the latest changes by flashing the firmware built in this PR's build-run.

hex2647 commented 4 months ago

Install stops at 5%? IMG_1404

spcqike commented 4 months ago

Bei mir ist es durchgelaufen. Hab es leider zu spät gemacht. Heute wird es nichts mehr mit testen :)

Gebe morgen Bescheid

schlimmchen commented 4 months ago

Install stops at 5%?

That's a weird error situation that I observe myself regularly. Need to restart the DTU, then try again.

spcqike commented 4 months ago

mit aktivem DPL bekomme ich weider ganz viele Timeouts, der WEchselrichter ist nicht erreichbar. Hat jemand von euch ähnliche Probleme?

ich habe den HMS-2000. Mir kommt es so vor, als wenn zu viele und zu häufige Abfragen/Anfragen irgendwie Probleme verursachen...

AndreasBoehm commented 4 months ago

mit aktivem DPL bekomme ich weider ganz viele Timeouts, der WEchselrichter ist nicht erreichbar. Hat jemand von euch ähnliche Probleme?

ich habe den HMS-2000.

Mir kommt es so vor, als wenn zu viele und zu häufige Abfragen/Anfragen irgendwie Probleme verursachen...

Hab den HMS-1600 und anfangs ähnliche Probleme. Hab die DTU dann in einen anderen Raum gestellt, näher an den WR, seitdem habe ich keine Probleme mehr.

spcqike commented 4 months ago

naja, da ich an der DTU und den Positionen nichts geändert habe und es bis dato gut und stabil lief (also nur das Abfragen der Daten, kein DPL aktiv), und es auch wieder gut läuft, wenn der DPL aus ist, denke ich nicht, dass es an der Aufstellung liegt.

es gibt auch im Upstream mehrere Issues, weil die HMS die Verbindung wohl des öfteren verlieren in letzter Zeit. bspw.: https://github.com/tbnobody/OpenDTU/issues/1921

Das, was ich jetzt getestet habe, sah gut aus. grafik

rot die PV Erzeugung, orange der Gesamtbezug (bzw. Einspeisung). Target: -1000W (sonst greift die Skalierung grad nicht, da jeder Eingang > 250W liefert :D)

Ab und zu bekommt er die -1000W nicht hin, aber da scheint auch kein neuer Wert von der DTU zu kommen, also wird auch der neue Limit nicht durchgehen... Was auch immer den Empfang da beeinträchtigt...

jetzt, wo der DPL wieder aus ist, ist die Aufzeichnung der PV-Leistung auch wieder konsistent. Die Abfrage klappt im 5s DTU Intervall aller 5-10s.

hex2647 commented 4 months ago

Install stops at 5%?

That's a weird error situation that I observe myself regularly. Need to restart the DTU, then try again.

That Solved it… its installed

hex2647 commented 4 months ago

Hab es auch grad getestet. Schwankt stark. Entweder voll offen (2.000W) oder das normale Limit, welches nicht ausreicht

image

hab zum testen 1 Paneel abgesteckt und das Target grad auf 800W gestellt.

@spcqike: Wie bekomm ich denn die schicken Charts? Dadurch würde vermutlcih das Fehler beschreiebn deutlich leichter werden :)

hex2647 commented 4 months ago

@greymda @spcqike @hex2647 Please test the latest changes by flashing the firmware built in this PR's build-run.

Ich konnte heute nochmal etwas genauer draufschauen. Grundsätzlich würde ich sagen sieht das ganze ganz gut aus aber heute ist nochmal ein Spannender Fall aufgetreten (tatsächlich mehrfach)...

Ausgewirkt hat es sich darin das die DTU sich auf einem viel zu niedrigen Wert "festgeschossen hat"... Resulatat waren die 104,7 Watt aus dem Inverter obwohl genug Sonne und auch genug Leistung aus dem Netz abgerufen wurden: IMG_1435

Auch im Log zu sehen: Aus irgend einem Grund behält er die 240W obwohl er eigentlich mehr machen sollte... Auf welcher Datenbasis entscheidet er hier das alle Strings weniger machen als erwartet?

Websocket: [/livedata][14] disconnect 13:12:50.963 > [DPL::loop] *** ENTER ** 13:12:51.584 > [DPL::calcPowerLimit] battery use prevented, solar power (DC): 10000 W 13:12:51.615 > [DPL::calcPowerLimit] target consumption: 0 W, base load: 70 W, power meter does include inverter output 13:12:51.892 > [DPL::calcPowerLimit] power meter value: 2979 W, power meter valid: yes, inverter output: 104 W, solar power (AC): 9215 W 13:12:51.909 > [DPL::calcPowerLimit] limited to solar power: 3083 W 13:12:51.924 > [DPL::setNewPowerLimit] input limit: 3083 W, min limit: 10 W, max limit: 1000 W, hysteresis: 5 W 13:12:51.953 > [DPL::scalePowerLimit] all channels are producing less than expected, keeping the current limit of 240 W instead of 1000 W by 13:12:51.970 > [DPL::setNewPowerLimit] inverter max: 2000 W, inverter is producing, requesting: 240 W, reported: 240 W, diff: 0 W 13:12:52.016 > [DPL::announceStatus] the system is stable, the last power limit is still valid

spcqike commented 4 months ago

@hex2647 in meinem Fall mit NodeRed (Processing), influxdb (Datenbank) und grafana (Frontend für Graphen und Dashboards)

Aus irgend einem Grund behält er die 240W obwohl er eigentlich mehr machen sollte... Auf welcher Datenbasis entscheidet er hier das alle Strings weniger machen als erwartet?

er berechnet es. Wenn dein Limit zu der Zeit 240W waren, sollte er ja 60W pro Eingang liefern. Scheinbar liefert er insgesamt nur 104W und auf jedem Eingang < 58W. Daher gibt es noch keinen Grund das Limit zu ändern, da auch ein höheres Limit nicht mehr Output liefern würde.

Kannst du, sollte sowas wieder passieren, auch Screenshots der wechselrichter Daten(Gesamtleistung, Effizienz,…) und der einzelnen Eingänge beistellen? Dass man besser nachvollziehen kann, was genau grade passiert?

AndreasBoehm commented 4 months ago

... das die DTU sich auf einem viel zu niedrigen Wert "festgeschossen hat"... Resulatat waren die 104,7 Watt aus dem Inverter obwohl genug Sonne und auch genug Leistung aus dem Netz abgerufen wurden

Vielen Dank fürs testen und berichten.

Ich habe einen ähnlichen Fall beobachtet, dachte aber es liegt an meinem Anker Solarspeicher.

Um uns das lösen des Problems einfacher zu machen werde ich nachher die Konsolen Ausgabe um einige Daten erweitern die uns helfen sollten zu verstehen warum die Berechnung auf einem niedrigen Wert "hängen bleibt".

AndreasBoehm commented 4 months ago

Ich habe die Konsolen Ausgabe erweitert, 90% der Ausgaben fliegen raus wenn die Berechnungen berichtig sind, sieht nun wie folgt aus: (Aktuell ist die Sonne hinter den schwarzen Wolken versteckt)

08:41:51.248 > [DPL::calcPowerLimit] battery use prevented, solar power (DC): 10000 W
08:41:51.253 > [DPL::calcPowerLimit] target consumption: -150 W, base load: 100 W, power meter does include inverter output
08:41:51.258 > [DPL::calcPowerLimit] power meter value: 164 W, power meter valid: yes, inverter output: 72 W, solar power (AC): 9231 W
08:41:51.268 > [DPL::calcPowerLimit] limited to solar power: 386 W
08:41:51.290 > [DPL::setNewPowerLimit] input limit: 386 W, min limit: 40 W, max limit: 1600 W, hysteresis: 5 W
08:41:51.304 > [DPL::scalePowerLimit::debug] checking for shading, inverterInputDC 76.599998 W, inverterOutputAC 72.900002 W, inverterEfficiencyFactor 0.951697, expectedAcPowerPerChannel 90.160000 W, currentLimitWatts 368 W, newLimit 386 W
08:41:51.306 > [DPL::scalePowerLimit::debug] channel 0 is producing less than expected, channelPowerAC 3.901958 W, channelPowerDC 4.100000 W
08:41:51.314 > [DPL::scalePowerLimit::debug] channel 1 is producing less than expected, channelPowerAC 3.806789 W, channelPowerDC 4.000000 W
08:41:51.319 > [DPL::scalePowerLimit::debug] channel 2 is producing less than expected, channelPowerAC 31.025326 W, channelPowerDC 32.599998 W
08:41:51.339 > [DPL::scalePowerLimit::debug] channel 3 is producing less than expected, channelPowerAC 34.165932 W, channelPowerDC 35.900002 W
08:41:51.346 > [DPL::scalePowerLimit] 4/4 channels are producing less than expected, shadedChannelACPowerSum 71 W
08:41:51.353 > [DPL::scalePowerLimit] all channels are producing less than expected, keeping the current limit of 368 W instead of 386 W
08:41:51.359 > [DPL::setNewPowerLimit] inverter max: 1600 W, inverter is producing, requesting: 368 W, reported: 368 W, diff: 0 W

@schlimmchen Könntest du den workflow erneut freigeben? Danke.

AndreasBoehm commented 4 months ago

Wenn ich so drüber nachdenke, glaube ich, dass der Punkt

maxPower >= _lastRequestedPowerLimit / dcTotalChnls && inverter->Statistics()->getChannelFieldValue(TYPE_AC, (ChannelNum_t)config.PowerLimiter_InverterChannelId, FLD_PAC) < newPowerLimit doch recht wichtig ist bzw. damals war. Dass die Skalierung stattfindet, wenn wenigstens 1 Eingang durch den Wechselrichter limitiert ist und die aktuelle AC Leistung dem neuen Limit nicht gerecht wird.

@spcqike Kannst du mir eventuell noch erläutern welchen Fall du mit diesem if sicherstellst bzw welche action anschließend ausgeführt wurde? Ich bin mir aktuell nicht sicher ob wir das so brauchen oder nicht.

spcqike commented 4 months ago

könntest du die Ausgabe abrunden? auf eine, oder gar keine Nachkommastelle? ich denke 72.123456 W macht wenig Sinn. Ganze Watt sollten ausreichen, oder?

In der Vergangenheit gab es Probleme, wenn die Nachrichten zu lang wurden, dann wurden Daten einfach abgeschnitten oder nicht angezeigt, oder es kam zu anderen komischen Verhalten.

auch finde ich

08:41:51.304 > [DPL::scalePowerLimit::debug] checking for shading, inverterInputDC 76.599998 W, inverterOutputAC 72.900002 W, inverterEfficiencyFactor 0.951697, expectedAcPowerPerChannel 90.160000 W, currentLimitWatts 368 W, newLimit 386 W

echt lang.

Ich persönlich würd Debug-nachrichten kürzer halten, ja fast kryptisch, und ggf. n Kommentar an der Stelle im Code lassen, was was genau ist.

08:41:51.314 > [DPL::scalePowerLimit::debug] channel 1 is producing less than expected, channelPowerAC 3.806789 W, channelPowerDC 4.000000 W

ebenfalls, reicht nicht "ch0: shaded, 4W", bzw. "chx: not shaded, 32W"?

AC und DC sind redundant, da beides mit der gleichen Effizienz von ein paar Zeilen vorher berechnet wird, oder?

Ich find den Umgang mit AC/DC noch immer verwirrend, aber das mag an mir und meinem Verständnis liegen :) aber, reicht es nicht, sich auf einen Wert festzulegen? AC oder DC?

Ich würde die ganzen Berechnungen und Vergleiche anhand der DC Werte machen. Ja, wir möchten ein AC Limit setzen, dafür bedarf es aber einer DC Gesamt-Leistung, die, nachdem sie einmal berechnet wurde, 1 zu 1 mit den DC Eingängen weiter berechnet/verglichen werden kann. oder ?

AndreasBoehm commented 4 months ago

@spcqike Die meisten Nachrichten werfe ich wieder raus sobald wir wissen das der Algorithmus funktioniert. Ich gebe jeweils AC und DC aus um euch mehr Infos zu geben über die Daten mit denen ich arbeite. Falls die Skalierung nicht wie erwartet arbeitet sehe ich dann alle Werte und kann direkt prüfen ob es irgendwo einen Rechenfehler gibt. AC zu nutzen schien mir am elegantesten, da ich am Schluss auch die Summe der Shaded-Inputs in AC vom newLimit (AC) abziehen muss, und auch das aktuelle Limit in AC vorliegt. Natürlich können wir das auch alles in DC machen, ich sehe keinen Vor- oder Nachteil mit AC oder DC. Kann ich für das nächste Test build gerne umstellen wenn es dir hilft um mich zu unterstützen

AndreasBoehm commented 4 months ago

@greymda @spcqike @hex2647 Please test the latest changes by flashing the firmware built in this PR's build-run.

It will now output more information about the values used to calculate overscaling/shading and should help us to fix any remaining issues.

spcqike commented 4 months ago

Kannst du mir eventuell noch erläutern welchen Fall du mit diesem if sicherstellst bzw welche action anschließend ausgeführt wurde?

So ganz nachvollziehen kann ich das auch nicht mehr. Dafür hat sich auch der Code in Gänze zu stark geändert (also auch die Punkte vor den Skalierungen)

Sinn war aber, dass nur skaliert wird, wenn nötig. also dann, wenn:

Heißt: mindestens ein Kanal könnte mehr liefern um das bisher nicht erreichte Ziel zu erreichen.

Sonst hab ich keine Skalierung gemacht gehabt. wenn nichts durch Software limitiert ist (sondern alles durch durch Verschattung), oder wenn das Ziel erreicht wird (also bspw. alle durch Software limitiert).

Ich glaube, diese Umstände hast du bereits abgefangen, aber eben später im Code und teilweise umfangreicher.

Eine Skalierung wie "wir haben grad 500W, wollen runter auf 300W, Eingang 1 liefert aber nur 100W also brauchen wir ein Limit von 400W um 300W AC seitig zu erreichen" (wieder für ein 2-MPPT Modell) hatte ich damals noch nicht drin.

hex2647 commented 4 months ago

... das die DTU sich auf einem viel zu niedrigen Wert "festgeschossen hat"... Resulatat waren die 104,7 Watt aus dem Inverter obwohl genug Sonne und auch genug Leistung aus dem Netz abgerufen wurden

Vielen Dank fürs testen und berichten.

Ich habe einen ähnlichen Fall beobachtet, dachte aber es liegt an meinem Anker Solarspeicher.

Um uns das lösen des Problems einfacher zu machen werde ich nachher die Konsolen Ausgabe um einige Daten erweitern die uns helfen sollten zu verstehen warum die Berechnung auf einem niedrigen Wert "hängen bleibt".

Jetzt mit mehr Daten :) 14:32:07.371 > [DPL::calcPowerLimit] battery use prevented, solar power (DC): 10000 W 14:32:07.542 > [DPL::calcPowerLimit] target consumption: 0 W, base load: 70 W, power meter does include inverter output 14:32:07.585 > [DPL::calcPowerLimit] power meter value: 137 W, power meter valid: yes, inverter output: 105 W, solar power (AC): 9212 W 14:32:07.633 > [DPL::calcPowerLimit] limited to solar power: 242 W 14:32:07.696 > [DPL::setNewPowerLimit] input limit: 242 W, min limit: 10 W, max limit: 2000 W, hysteresis: 5 W 14:32:07.748 > [DPL::scalePowerLimit::debug] checking for shading, inverterInputDC 111.500000 W, inverterOutputAC 105.900002 W, inverterEfficiencyFactor 0.949776, expectedAcPowerPerChannel 58.800000 W, currentLimitWatts 242 W, newLimit 242 W 14:32:07.801 > [DPL::scalePowerLimit::debug] channel 0 is producing less than expected, channelPowerAC 0.000000 W, channelPowerDC 0.000000 W 14:32:07.844 > [DPL::scalePowerLimit::debug] channel 1 is producing less than expected, channelPowerAC 0.000000 W, channelPowerDC 0.000000 W 14:32:07.886 > [DPL::scalePowerLimit::debug] channel 2 is producing less than expected, channelPowerAC 51.857761 W, channelPowerDC 54.599998 W 14:32:07.929 > [DPL::scalePowerLimit::debug] channel 3 is producing less than expected, channelPowerAC 54.042248 W, channelPowerDC 56.900002 W 14:32:07.968 > [DPL::scalePowerLimit] 4/4 channels are producing less than expected, shadedChannelACPowerSum 105.900009 W 14:32:08.008 > [DPL::scalePowerLimit] all channels are producing less than expected, keeping the current limit of 242 W instead of 242 W 14:32:08.054 > [DPL::setNewPowerLimit] inverter max: 2000 W, inverter is producing, requesting: 242 W, reported: 242 W, diff: 0 W 14:32:08.104 > [DPL::announceStatus] the system is stable, the last power limit is still valid 14:32:08.146 > Websocket: [/livedata][10] disconnect 14:32:08.465 > PowerMeterClass: TotalPower: 138.10

spcqike commented 4 months ago

Ok.

Vor dem skalieren aus diesem PR gab es ja noch das skalieren, welches berücksichtigt, wie viele Eingänge belegt sind. Damit wurde bei dir das Limit wohl immer verdoppelt, da du nur 2 Eingänge belegt hast.

Das skalieren aus diesem PR berücksichtigt das aber (noch?) nicht.

hex2647 commented 4 months ago

Hab jetzt nochmal umgebaut sodass alle 4 Eingänge belegt sind… er skaliert aber trotzdem nicht hoch. Obwohl er eigentlich selbst sagt das die Module verschattet sind?

15:35:33.778 > [DPL::loop] *** ENTER ** 15:35:33.807 > [DPL::calcPowerLimit] battery use prevented, solar power (DC): 10000 W 15:35:33.838 > [DPL::calcPowerLimit] target consumption: 0 W, base load: 70 W, power meter does include inverter output 15:35:33.865 > [DPL::calcPowerLimit] power meter value: 287 W, power meter valid: yes, inverter output: 108 W, solar power (AC): 9224 W 15:35:33.897 > [DPL::calcPowerLimit] limited to solar power: 395 W 15:35:33.931 > [DPL::setNewPowerLimit] input limit: 395 W, min limit: 10 W, max limit: 2000 W, hysteresis: 5 W 15:35:33.964 > [DPL::scalePowerLimit::debug] checking for shading, inverterInputDC 114.200005 W, inverterOutputAC 108.599998 W, inverterEfficiencyFactor 0.950963, expectedAcPowerPerChannel 61.740000 W, currentLimitWatts 252 W, newLimit 395 W 15:35:34.001 > [DPL::scalePowerLimit::debug] channel 0 is producing less than expected, channelPowerAC 20.635902 W, channelPowerDC 21.700001 W 15:35:34.035 > [DPL::scalePowerLimit::debug] channel 1 is producing less than expected, channelPowerAC 1.521541 W, channelPowerDC 1.600000 W 15:35:34.063 > [DPL::scalePowerLimit::debug] channel 2 is producing less than expected, channelPowerAC 52.302975 W, channelPowerDC 55.000000 W 15:35:34.091 > [DPL::scalePowerLimit::debug] channel 3 is producing less than expected, channelPowerAC 34.139580 W, channelPowerDC 35.900002 W 15:35:34.118 > [DPL::scalePowerLimit] 4/4 channels are producing less than expected, shadedChannelACPowerSum 108.599998 W 15:35:34.152 > [DPL::scalePowerLimit] all channels are producing less than expected, keeping the current limit of 252 W instead of 395 W 15:35:34.188 > [DPL::setNewPowerLimit] inverter max: 2000 W, inverter is producing, requesting: 252 W, reported: 252 W, diff: 0 W

AndreasBoehm commented 4 months ago

@hex2647 Das Problem ist das alle Eingänge verschattet sind und (laut den Zahlen in deinem Log) keiner der Eingänge durch das Limit begrenzt ist sondern rein durch die verschattung. Selbst Channel 3 liefert nur 52 W anstelle der erwarteten 61W beim aktuellen Limit.

Hast du denn tatsächlich so viel verschattung oder wie kommen deine doch sehr unterschiedlichen Werte an den Eingängen zustande?

Das simple verdoppeln des Limits wie es bisher aktiv war ist durch meinen Algorithmus nicht mehr erforderlich und deshalb auch nicht implementiert.

spcqike commented 4 months ago

Selbst Channel 3 liefert nur 52 W

CH1 liefert sogar nur 1.6W. Also quasi nichts. So wenig auf einem Eingang hab ich nur zur Dämmerung

AndreasBoehm commented 4 months ago

@hex2647 @spcqike

15:35:34.152 > [DPL::scalePowerLimit] all channels are producing less than expected, keeping the current limit of 252 W instead of 395 W

Ich könnte noch einen check einbauen der das neue Limit setzt wenn alle Eingänge verschattet sind und das aktuelle Limit kleiner ist als das neue Limit, aber das wird unterm Strich dem WR auch nicht mehr Leistung entlocken wenn alle Eingänge verschattet sind.

@hex2647 Könntest du dein Szenario mal mit der "alten" Skalierung gegentesten? Also den Haken für das ausgleichen von Verschattung rausnehmen und dann Vergleichen ob du tatsächlich mehr Leistung aus deinem WR bekommst?

spcqike commented 4 months ago

Ich könnte noch einen check einbauen der das neue Limit setzt wenn alle Eingänge verschattet sind und das aktuelle Limit kleiner ist als das neue Limit, aber das wird unterm Strich dem WR auch nicht mehr Leistung entlocken wenn alle Eingänge verschattet sind.

daran hab ich auch schon gedacht. früher war das ja so, und in der Aufzeichnung in Grafana konnte man dann relativ gut nachvollziehen, was berechnet wurde und was das Limit war. Das passiert aktuell ja nicht 😄 dafür reduziert man mit deiner jetzigen Lösung aber den Overhead und unnötige Übertragungen. Wozu aller 10 Sekunden ein Limit übertragen, wenn ne dicke Wolke da ist und eh nichts passieren würde 😄 (man hat nur jetzt halt das kurzzeitige Risiko, dass man, sollte die Sonne doch schlagartig kommen, zu viel produziert. Aber das ist ja generell so, wenn überskaliert wird, und für mich ok)

also nein: aktuell sehe ich keinen Bedarf daran, ein kleineres, nicht erreichtes Limit neu zu setzen.

@hex2647 Könntest du dein Szenario mal mit der "alten" Skalierung gegentesten? Also den Haken für das ausgleichen von Verschattung rausnehmen und dann Vergleichen ob du tatsächlich mehr Leistung aus deinem WR bekommst?

alternativ könnte er den DPL komplett deaktivieren und den Wechselrichter mal manuell auf 100% stellen. nur, um zu sehen, was aktuell wirklich an Solarleistung zur verfügung steht. Ich find es immer noch komisch, dass sein Ch1 so gar nichts beiträgt

15:35:34.035 > [DPL::scalePowerLimit::debug] channel 1 is producing less than expected, channelPowerAC 1.521541 W, channelPowerDC 1.600000 W

wie gesagt, 1.5W kenne ich nur aus der Dämmerung. das sind Frühs und Abends jeweils wenige Minuten, wo das so ist. selbst ne Nordseite liefert mehr, egal ob bewölkt oder nicht.

AndreasBoehm commented 4 months ago

@greymda Did you have a chance to test this feature? Asking because you made the effort to create the issue on github.