-
After upgrading from version v23.10.9 to v24.3.22 my enclosed attached script is no longer Shelley Pro EM3 firmware: Details: Do I have to modify the script to be compatible with releases after v23.10.9? Any feedback is welcome .🙏 Screenshot: SCRIPT: #!/usr/bin/env python3
import requests, time, sys
from requests.auth import HTTPBasicAuth
# Diese Daten müssen angepasst werden:
serial = "xxxxxxxxxx" # Seriennummer des Hoymiles Wechselrichters
maximum_wr = 450 # Maximale Ausgabe des Wechselrichters
minimum_wr = 70 # Minimale Ausgabe des Wechselrichters
dtu_ip = '192.168.X.X' # IP Adresse von OpenDTU
dtu_nutzer = 'xxxxx' # OpenDTU Nutzername
dtu_passwort = 'xxxxxxxxx' # OpenDTU Passwort
shelly_ip = '192.168.X.X' # IP Adresse von Shelly Pro 3EM
while True:
try:
# Nimmt Daten von der openDTU Rest-API und übersetzt sie in ein json-Format
r = requests.get(url = f'http://{dtu_ip}/api/livedata/status/inverters' ).json()
# Selektiert spezifische Daten aus der json response
reachable = r['inverters'][0]['reachable'] # Ist DTU erreichbar?
producing = int(r['inverters'][0]['producing']) # Produziert der Wechselrichter etwas?
altes_limit = int(r['inverters'][0]['limit_absolute']) # Altes Limit
power_dc = r['inverters'][0]['AC']['0']['Power DC']['v'] # Lieferung DC vom Panel
power = r['inverters'][0]['AC']['0']['Power']['v'] # Abgabe BKW AC in Watt
except:
print('Fehler beim Abrufen der Daten von CMO-openDTU')
try:
# Nimmt Daten von der Shelly 3EM pro Rest-API und übersetzt sie in ein json-Format
grid_sum = requests.get(f'http://{shelly_ip}/rpc/EM.GetStatus?id=0', headers={'Content-Type': 'application/json'}).json()['total_act_power'] # Aktueller Bezug
except:
print('Fehler beim Abrufen der Daten von CMO Shelly Pro 3EM')
# Werte setzen
print(f'\nBezug: {round(grid_sum, 0)} W, Produktion: {round(power, 0)} W, Verbrauch: {round(grid_sum + power, 0)} W')
if reachable:
setpoint = grid_sum + altes_limit - 5 # Neues Limit in Watt
print(f'neuer Setpoint: {setpoint} W')
# Fange oberes Limit ab
if setpoint > maximum_wr:
setpoint = maximum_wr
print(f'Setpoint auf Maximum: {maximum_wr} W')
# Fange unteres Limit ab
elif setpoint < minimum_wr:
setpoint = minimum_wr
print(f'Setpoint auf Minimum: {minimum_wr} W')
else:
print(f'Setpoint berechnet: {round(grid_sum, 0)} W + {round(altes_limit, 0)} W - 5 W = {round(setpoint, 0)} W')
if round(setpoint/50,0) != round(altes_limit/50,0):
#if setpoint != altes_limit:
print(f'Setze Inverterlimit von {round(altes_limit, 0)} W auf {round(setpoint, 0)} W... ', end='')
# Neues Limit setzen
try:
r = requests.post(
url = f'http://{dtu_ip}/api/limit/config',
data = f'data={{"serial":"{serial}", "limit_type":0, "limit_value":{setpoint}}}',
auth = HTTPBasicAuth(dtu_nutzer, dtu_passwort),
headers = {'Content-Type': 'application/x-www-form-urlencoded'}
)
print(f'Konfiguration gesendet ({r.json()["type"]})')
except:
print('Fehler beim Senden der Konfiguration')
sys.stdout.flush() # write out cached messages to stdout
time.sleep(15) # wait |
Beta Was this translation helpful? Give feedback.
Replies: 10 comments 2 replies
-
Die API hat sich ein wenig geändert. Beispiel: Dann müßte es wieder laufen |
Beta Was this translation helpful? Give feedback.
-
Warum auch immer, funktioniert die gestern gemachte Änderung heute nicht mehr mit Version 24.3.22 Warum es gestern funktioniert hat, kann ich nicht mehr nachvollziehen. Es scheint so als muss noch an andere Stelle etwas geändert werden. Wäre echt super wenn sich das jemand noch mal anschauen könnte: SCRIPT: #!/usr/bin/env python3
import requests, time, sys
from requests.auth import HTTPBasicAuth
Diese Daten müssen angepasst werden:
serial = "xxxxxxxxxx" # Seriennummer des Hoymiles Wechselrichters
maximum_wr = 450 # Maximale Ausgabe des Wechselrichters
minimum_wr = 70 # Minimale Ausgabe des Wechselrichters
dtu_ip = '192.168.X.X' # IP Adresse von OpenDTU
dtu_nutzer = 'xxxxx' # OpenDTU Nutzername
dtu_passwort = 'xxxxxxxxx' # OpenDTU Passwort
shelly_ip = '192.168.X.X' # IP Adresse von Shelly Pro 3EM
while True:
try:
# Nimmt Daten von der openDTU Rest-API und übersetzt sie in ein json-Format
r = requests.get(url = f'http://{dtu_ip}/api/livedata/status?inv={serial}' ).json()
# Selektiert spezifische Daten aus der json response
reachable = r['inverters'][0]['reachable'] # Ist DTU erreichbar?
producing = int(r['inverters'][0]['producing']) # Produziert der Wechselrichter etwas?
altes_limit = int(r['inverters'][0]['limit_absolute']) # Altes Limit
power_dc = r['inverters'][0]['AC']['0']['Power DC']['v'] # Lieferung DC vom Panel
power = r['inverters'][0]['AC']['0']['Power']['v'] # Abgabe BKW AC in Watt
except:
print('Fehler beim Abrufen der Daten von CMO-openDTU')
try:
# Nimmt Daten von der Shelly 3EM pro Rest-API und übersetzt sie in ein json-Format
grid_sum = requests.get(f'http://{shelly_ip}/rpc/EM.GetStatus?id=0', headers={'Content-Type': 'application/json'}).json()['total_act_power'] # Aktueller Bezug
except:
print('Fehler beim Abrufen der Daten von CMO Shelly Pro 3EM')
# Werte setzen
print(f'\nBezug: {round(grid_sum, 0)} W, Produktion: {round(power, 0)} W, Verbrauch: {round(grid_sum + power, 0)} W')
if reachable:
setpoint = grid_sum + altes_limit - 5 # Neues Limit in Watt
print(f'neuer Setpoint: {setpoint} W')
# Fange oberes Limit ab
if setpoint > maximum_wr:
setpoint = maximum_wr
print(f'Setpoint auf Maximum: {maximum_wr} W')
# Fange unteres Limit ab
elif setpoint < minimum_wr:
setpoint = minimum_wr
print(f'Setpoint auf Minimum: {minimum_wr} W')
else:
print(f'Setpoint berechnet: {round(grid_sum, 0)} W + {round(altes_limit, 0)} W - 5 W = {round(setpoint, 0)} W')
if round(setpoint/50,0) != round(altes_limit/50,0):
#if setpoint != altes_limit:
print(f'Setze Inverterlimit von {round(altes_limit, 0)} W auf {round(setpoint, 0)} W... ', end='')
# Neues Limit setzen
try:
r = requests.post(
url = f'http://{dtu_ip}/api/limit/config',
data = f'data={{"serial":"{serial}", "limit_type":0, "limit_value":{setpoint}}}',
auth = HTTPBasicAuth(dtu_nutzer, dtu_passwort),
headers = {'Content-Type': 'application/x-www-form-urlencoded'}
)
print(f'Konfiguration gesendet ({r.json()["type"]})')
except:
print('Fehler beim Senden der Konfiguration')
sys.stdout.flush() # write out cached messages to stdout
time.sleep(15) # wait |
Beta Was this translation helpful? Give feedback.
-
Setze doch source code einfach in die passenden tags dann wirds auch lesbar :) Ohne mich genauer mit dem algorithmus beschäftigt zu haben.... Das hier: power_dc = r['inverters'][0]['AC']['0']['Power DC']['v'] # Lieferung DC vom Panel Sollte eher das hier sein: power_dc = r['inverters'][0]['INV']['0']['Power DC']['v'] # Lieferung DC vom Panel Siehe hier: e156478 |
Beta Was this translation helpful? Give feedback.
-
hmm was muss ich tun um den Index zu setzten? sorry ich bin nicht so tief in der Materie drin, als ich etwas damit anfangen könnte. |
Beta Was this translation helpful? Give feedback.
-
Die Zuordnung gibt es nicht, daher gibt es den Fehler. |
Beta Was this translation helpful? Give feedback.
-
Ich stehe da auf dem Schlauch. Wenn ich die Änderung von AC auf INV wie oben vorgeschlagen mache, bleibt das Script stehen. Vor der API Änderung hat alles wunderbar funktioniert. Kannst Du mir bitte zeigen, wo ich was im Code anpassen muss. Besten Dank im Voraus |
Beta Was this translation helpful? Give feedback.
-
So ist das nur stochern.... Ersetze doch mal die Zeile except:
print('Fehler beim Abrufen der Daten von CMO-openDTU') durch except Exception as err:
print('Fehler beim Abrufen der Daten von CMO-openDTU')
print(f"Unexpected {err=}, {type(err)=}")
raise |
Beta Was this translation helpful? Give feedback.
-
Das hat geholfen. Typo gefunden. Musste zudem das NAS mal neu starten , damit das Script wieder ordentlich durchläuft. Ich beobachte das jetzt mal ein paar Tage. Gestern hat es ja auch den ganzen Tag funktioniert und dann heute morgen nicht mehr. Auf jeden Fall vielen Dank :-) |
Beta Was this translation helpful? Give feedback.
-
This discussion has been automatically locked since there has not been any recent activity after it was closed. Please open a new discussion for related concerns. |
Beta Was this translation helpful? Give feedback.
Besten Dank, dass war es. :-)
Ich habe es via Variable umgesetzt:
"r = requests.get(url = f'http://{dtu_ip}/api/livedata/status?inv={serial}' ).json()"
Damit nimmt er automatisch die Serial No, die in Zeile 5 angegeben wurde.