Sonnenbatterie with APIv2 / Webhook

Yes just sent off a querie. No reply.

Do you also see an OperatingMode switch, as reported by Uwe?
Can you maybe add this to the previous chart?
Maybe the Sonnen service needs some time to check with the HQ as they are off in Germany right now. I may also try to investigate with the Italian support teamā€¦ maybe Iā€™m luckier than you, even if not easy as Iā€™m not experiencing this behavior (so far Iā€™ve never charged at max power).

I understand you own a SonnenBattery 10 as I do.
The nominal (dis)charge power is 4,6 kW (or 3,4 kW if you have the smaller version).

EDIT: Apologies, Iā€™ve just understood you own the ā€œPerformaceā€ model. So my comment is pointless as the power is what you said.

While replying to Uwe I noticed that the inverter, for a SB 10, has max 95% efficiency. Maybe you could check for your model, do not exceed the resulting value and see if this happens again.

No, my battery is a 5 year old eco 9.43. 10kWh 9 usable and a Fronius Primo 6.0-1 inverter.

Operating mode is managed via REST API.

EM_OperatingMode=1 puts the battery into manual mode that allows POST commands to charge and discharge.
EM_OperatingMode=2 puts the battery into automatic (self consumption) mode

I was wondering if the battery was changing mode by itself when you see the SOC drift but I understand itā€™s not the case.

No donā€™t think so. Automatic mode would either change the output of the battery to match the house consumption or if PV output is available would charge the battery ant available PV output.

Hi, Any chance I can see the code behind the buttons? I donā€™t use node_red.
I take it you donā€™t have a configuration yaml file when you use node_red?
Iā€™m garbage at writing code from scratch but I can usually follow basic code to fudge my way through getting my things workingā€¦ :laughing:

This is what i think worked before I used node red. The below code is an switch.yaml file. I stopped using them as I wanted a dynamic message so I donā€™t know if they still work but its a start for you @whistlebare.
You need your Token from the API and IP address and unique_id if you want.

- platform: command_line
  switches:
    sonnen_automatic_mode:
      unique_id: xxxxxxx
      friendly_name: 'Set Sonnen to Auto'
      command_on: "curl -X PUT -d EM_OperatingMode=2 --header 'Auth-Token: xxxxxxxx' http://192.168.xxx.xxx:80/api/v2/configurations"
      value_template: >
          {{value_json.config.on}}
      icon_template: >
        {% if value_json.config.on == true %} mdi:toggle-switch
        {% else %} mdi:toggle-switch-off
        {% endif %}
    sonnen_tou_mode:
      unique_id: xxxxxxxx
      friendly_name: 'Set Sonnen to TOU'
      command_on: "curl -X PUT -d EM_OperatingMode=10 --header 'Auth-Token: xxxxxxxx' http://192.168.xxx.xxx:80/api/v2/configurations"
      value_template: >
          {{value_json.config.on}}
      icon_template: >
        {% if value_json.config.on == true %} mdi:toggle-switch
        {% else %} mdi:toggle-switch-off
        {% endif %}
    sonnen_manual_mode:
      unique_id: xxxxxxxxx
      friendly_name: 'Set Sonnen to Manual'
      command_on: "curl -X PUT -d EM_OperatingMode=1 --header 'Auth-Token: xxxxxxxxx' http://192.168.xxx.xxx:80/api/v2/configurations"
      value_template: >
          {{value_json.config.on}}
      icon_template: >
        {% if value_json.config.on == true %} mdi:toggle-switch
        {% else %} mdi:toggle-switch-off
        {% endif %}
1 Like

Sure, however Node-Red takes a lot of the coding out. If you are less interested in coding then youā€™re probably a candidate for Node-Red.

I use switch nodes for these buttons. You Need Custom Integration installed in Home Assistant for this node to function. This integration is kind of a feed back into HA from node-red. In this case it allows me to place a switch on my dashboard that has an affect in Node-Red.

These are the switch nodes:


The way I use them is when you activate the dashboard switchs the action triggers a ā€œflowā€ in NR.

For example the automatic mode switch feeds into 6 different lines of nodes.

\

The first is a REST API PUT command that sets the backup buffer of the battery to 0%. The reason for this is because I use 100% backup buffer to put the battery into standby mode and switching back to 0% just makes sure that standby is off.

This PUT command is carried out using first a function node:

This is the guts of the 0% Backup Buffer function node. Its very simple. All its doing is create a message array with the variables you can see (iā€™ve blanked out the Auth-Token as thatā€™s private).

This message array ā€˜msgā€™ is then passed to the next node which is a http request node. It has no setting except the PUT method as all the details have been passed using the msg array from the previous function node.

After that I pass the returned responce from the subject server (the battery) to some error hadleing steps.


This simply tests that the return responce was an error and if so write it and some other info like timestamp and the contents of the origin PUT command etc.

So here is the entire flow for EMHASS


The details of all this is in that document I mentioned above and in fact the entire flow is there as well so you can import it into your node-red instant and with a little bit of adjustment use the same setup. Thats the EMHASS.JSON file. Itā€™s all the code in this RN flow.

I canā€™t explane it all here as thatā€™s what the document does and its 37 pages long.

There is no code other than these nodes and whatā€™s explained in the doco. Node-red does away with most coding and automations. I donā€™t use automations any more as Iā€™ve translated them all into node-red.

2 Likes

Thanks for thatā€¦I might have a play with the code and see how I get on. I have automations working for various triggers to do with my Intelligent Octopus set up, it would be nice to have some visual indications and buttons to go along with it

Damn looks like iā€™ve got to install Node Red on my docker and learn yet another program :laughing: Thanks for the in depth explanationā€¦ :+1:

Iā€™ll bet youā€™ll eventually migrate all your automations to node-red if you do install it.

Hi!
This might me a little bit off topic, but maybe a good place to ask:
I read the values from api/v2/status and discovered some time ago, that ā€œSystemStatusā€ changes sometimes to ā€œCriticalErrorā€ for 5 or 15 minutes. Sometimes means between once per week and 24 times a day (which means about 2h no operation of the battery!).
Iā€™m curious, if Iā€™m the only one with this behaviour or if this happens also to others. Usually this value is not watched regularly, but maybe some of you could take a look on your recorded values and give a response, if this happens also to you.

Hello
Thank you for the great work here.
My English is not that perfect, so everything with a translator! Sorry!
Iā€™m not that familiar with Node-red yet, Iā€™m still at the beginning.
I also have a solar battery and would like to minimize its high consumption.
When there is no more production and the battery supplies the house, I still have a power supply of 50 - 100 watts.
I can already send charging commands or change the work mode.
Maybe not correct, Iā€™m definitely using the wrong nodes.
What I canā€™t do is send a variable value (consumption is constantly changing).
As you can see in the pictures, I send 50 watts to unload with the URL.
But I would like to send a value that is consumption + grid consumption. It also has a sensor for that.
For example, the house consumes 400 watts and the power supply is 50 watts, so I would like to send 450 watts to discharge.
Maybe someone can give me some food for thought.
This is what it looks like at the moment.
Canā€™t attach images!
URL - http://192.168.1.70/api/v2/setpoint/discharge/50

Thank you in advance
greeting

sonnen battery is manageable via RESTful API. So you can use the Home Assistant RESTful Command to send commands to the battery to charge or discharge at whatever rate you want.

Alternatively you can do the same thing with Node-Red by using the http request node.

In either case to change the battery charge/discharge rate requires a PUT command after the battery has been put in manual mode (which can also be done with a RESTful command).

Example:


These two flows put the battery into manual mode and then pass a number in Watts to charge the battery.
Hereā€™s the JSON code for these two flows:

[{"id":"f8c8624c7c9dca94","type":"http request","z":"65840aa926d9c567","name":"POST","method":"POST","ret":"obj","paytoqs":"ignore","url":"","tls":"","persist":false,"proxy":"","insecureHTTPParser":false,"authType":"bearer","senderr":false,"headers":[],"x":1250,"y":340,"wires":[["0e3f0373d7e81e09","7e7a97b8e68d3389"]]},{"id":"858d53f8ca9abe53","type":"function","z":"65840aa926d9c567","name":"Charge Setup","func":"var pospayload = 0.0\npospayload = Math.abs(msg.payload)\n// Increase pospayload by 100 if it is between 200 and 2500\nif (pospayload >= 200 && pospayload <= 2500) \n{\n    pospayload += 100;\n}\nmsg.headers = {}\nmsg.headers['Auth-Token'] = 'YOUR-SONNEN-AUTH-TOKEN'\nmsg.headers [\"Content-Type\"] = \"application/x-www-form-urlencoded\"\nmsg.url = \"http://192.168.1.70:80/api/v2/setpoint/charge/\" + pospayload.toString()\nreturn msg;","outputs":1,"timeout":"","noerr":0,"initialize":"","finalize":"","libs":[],"x":1080,"y":340,"wires":[["f8c8624c7c9dca94"]]},{"id":"0e3f0373d7e81e09","type":"debug","z":"65840aa926d9c567","name":"debug Charge","active":false,"tosidebar":true,"console":false,"tostatus":false,"complete":"true","targetType":"full","statusVal":"","statusType":"auto","x":1440,"y":340,"wires":[]},{"id":"402679171d35e0d2","type":"http request","z":"65840aa926d9c567","name":"PUT","method":"PUT","ret":"obj","paytoqs":"ignore","url":"","tls":"","persist":false,"proxy":"","insecureHTTPParser":false,"authType":"bearer","senderr":false,"headers":[],"x":1250,"y":280,"wires":[["5bd08bcd972153bc","81532e458a6da3d1"]]},{"id":"9efde64dbc00c864","type":"function","z":"65840aa926d9c567","name":"Manual Mode","func":"msg.payload = \"EM_OperatingMode=1\"\nmsg.headers = {}\nmsg.headers['Auth-Token'] = 'YOUR-SONNEN-AUTH-TOKEN'\nmsg.headers [\"Content-Type\"] = \"application/x-www-form-urlencoded\"\nmsg.url = \"http://192.168.1.70:80/api/v2/configurations\" \nreturn msg;","outputs":1,"noerr":0,"initialize":"","finalize":"","libs":[],"x":1080,"y":280,"wires":[["402679171d35e0d2"]]},{"id":"5bd08bcd972153bc","type":"debug","z":"65840aa926d9c567","name":"debug Manual Mode","active":false,"tosidebar":true,"console":false,"tostatus":false,"complete":"true","targetType":"full","statusVal":"","statusType":"auto","x":1460,"y":280,"wires":[]},{"id":"4b6455180cf0d210","type":"delay","z":"65840aa926d9c567","name":"4 sec","pauseType":"delay","timeout":"4","timeoutUnits":"seconds","rate":"1","nbRateUnits":"1","rateUnits":"second","randomFirst":"1","randomLast":"5","randomUnits":"seconds","drop":false,"allowrate":false,"outputs":1,"x":930,"y":340,"wires":[["858d53f8ca9abe53"]]},{"id":"93beed478696134e","type":"link in","z":"65840aa926d9c567","name":"link in Charge Setup","links":["8f6da85cea51a6c2","63ba9e6850f7361b","95976ebe7f6655d3","cc0a6d9606abe439","cba7fee3cee79393","b42b8c412b6200e7"],"x":835,"y":340,"wires":[["4b6455180cf0d210"]]},{"id":"2608790487e879c8","type":"link in","z":"65840aa926d9c567","name":"link in Manual Mode Setup","links":["8f6da85cea51a6c2","c4a70f29ecac9603","767baa7b0d82b4ca","d9ba6153cfb88bbb","63ba9e6850f7361b","95976ebe7f6655d3","cc0a6d9606abe439","87b07b541bba63f6","cba7fee3cee79393","b42b8c412b6200e7"],"x":835,"y":280,"wires":[["e8a2ee908ef64a78"]]},{"id":"e8a2ee908ef64a78","type":"delay","z":"65840aa926d9c567","name":"2 sec","pauseType":"delay","timeout":"2","timeoutUnits":"seconds","rate":"1","nbRateUnits":"1","rateUnits":"second","randomFirst":"1","randomLast":"5","randomUnits":"seconds","drop":false,"allowrate":false,"outputs":1,"x":930,"y":280,"wires":[["9efde64dbc00c864"]]}]

You should be able to import this JSON into you Node-Red instance and work with it. Remember to replace the AUTH-TOKEN with your battery AUTH-TOKEN which can be found here on your battery (assume itā€™s IP address is 192.168.1.70.

Now to decide what rate to charge or discharge I use EMHASS. My config for EMHASS is located here.

1 Like

Hi and thanks for all the effort here!

Iā€™m trying to setup the rest integration for my battery. I want to do as much use as possible of the restful integration, instead of using the sensor integration, because this allows to reduce the number of requests.

In the case of the powermeter endpoint, I want to get both kwh_imported sensors from this query:

[
  {
    "a_l1": 0,
    "a_l2": 0,
    "a_l3": 0,
    "a_total": 0,
    "channel": 1,
    "deviceid": 0,
    "direction": "production",
    "error": 0,
    "frequency": 0,
    "kwh_exported": 0,
    "kwh_imported": 17.5,
    "v_l1_l2": 0,
    "v_l1_n": 237.8000030517578,
    "v_l2_l3": 0,
    "v_l2_n": 0,
    "v_l3_l1": 0,
    "v_l3_n": 0,
    "va_total": 0,
    "var_total": 0,
    "w_l1": 0,
    "w_l2": 0,
    "w_l3": 0,
    "w_total": 0
  },
  {
    "a_l1": 1.6030000448226929,
    "a_l2": 0,
    "a_l3": 0,
    "a_total": 0,
    "channel": 2,
    "deviceid": 1,
    "direction": "consumption",
    "error": 0,
    "frequency": 0,
    "kwh_exported": 0,
    "kwh_imported": 12.300000190734863,
    "v_l1_l2": 0,
    "v_l1_n": 237.8000030517578,
    "v_l2_l3": 0,
    "v_l2_n": 0,
    "v_l3_l1": 0,
    "v_l3_n": 0,
    "va_total": 379.7999877929687,
    "var_total": -379.7999877929687,
    "w_l1": -17.100000381469727,
    "w_l2": 0,
    "w_l3": 0,
    "w_total": 7.5
  }
]

However, this configuration fails.

rest:
  - resource: http://BATTERY_IP:80/api/v2/powermeter
    headers:
      Auth-Token: !secret sonnen_api_token
    scan_interval: 15
    sensor:
      - name: Sonnen Solar production Wh
        unique_id: sonnen_powermeter_solar_production
        json_attributes_path: "$.[0]"
        json_attributes:
          - "kwh_imported"
        unit_of_measurement: Wh
        device_class: energy
        state_class: measurement

In the logs I get these errors:

 Template variable warning: 'list object' has no attribute 'kwh_imported' when rendering '{{ value_json.kwh_imported }}' 

and

Failed to set state for sensor.sonnen_solar_production_kwh, fall back to unknown

Traceback (most recent call last):
  File "/usr/src/homeassistant/homeassistant/helpers/entity.py", line 1209, in _async_write_ha_state
    hass.states.async_set_internal(
  File "/usr/src/homeassistant/homeassistant/core.py", line 2332, in async_set_internal
    state = State(
            ^^^^^^
  File "/usr/src/homeassistant/homeassistant/core.py", line 1776, in __init__
    validate_state(state)
  File "/usr/src/homeassistant/homeassistant/core.py", line 240, in validate_state
    raise InvalidStateError(
homeassistant.exceptions.InvalidStateError: Invalid state with length 856. State max length is 255 characters.

Thanks for any help!

Try this, let me know how it goes:

rest:
  - resource: http://BATTERY_IP:80/api/v2/powermeter
    headers:
      Auth-Token: !secret sonnen_api_token
    scan_interval: 15
    sensor:
      - name: "Sonnen Solar Production Wh"
        unique_id: "sonnen_powermeter_solar_production"
        value_template: "{{ value_json[0].kwh_imported }}"
        unit_of_measurement: "Wh"
        device_class: energy
        state_class: measurement

      - name: "Sonnen Consumption Wh"
        unique_id: "sonnen_powermeter_consumption"
        value_template: "{{ value_json[1].kwh_imported }}"
        unit_of_measurement: "Wh"
        device_class: energy
        state_class: measurement

Wooow! It works!

I donā€™t understand why it doesnā€™t work with the path (which seems like the intended way of doing it), but I can live with that!

Thank you very much

PS: I corrected the paths removing the points, which made the list conversion errors disapear, but still no numeric result.