Update: This has now been edited to use the pypowerwall ‘convenience’ (/pw) endpoints
So after having a play with the OH Powerwall binding, it looks like at this stage it doesn’t support the Powerwall 3. I needed a fairly quick solution to integrate the PW3 into OpenHAB, so I could monitor status and persist key values.
My requirements don’t include controlling the PW3 - Happy to let it do its own thing there, but arguably you could use the same approach for the controllable values, only thing then, is that requires the cloud API connection from the PyPowerwall Proxy
For others who are looking to do the same, this is a rough how-to guide I have collated from various sources, to get PW3 values back into OpenHAB, with the following high-level steps:
- Install/Configure WIFI connection on OH server, as client to PW3 WiFi AP
- Install Docker & Run pypowerwallproxy container
- Add HTTP Things & Items, to retrieve values from pypowerwall proxy
I have done this all on my local openHAB server, running Ubuntu, but arguably the first 3 steps could be done on a separate device such as a PI Zero 2W (with Ethernet HAT), giving you a dedicated proxying device. You may need to do this, if you are already using, or don’t have a WiFi adapter in your OpenHAB server, and don’t want to add another one in there.
Obviously you will need to interpret and apply your own site/device-specific commands/config.
First things first, you are going to need the WIFI SSID and Wifi Password for the TEDAPI access - There is no access via the local LAN ports to the PW3 API, which was taken away in a recent release (25.10). Take a picture of the WiFi sticker in the main PW3 unit (Not the Gateway Unit), while your installer is connecting things up…
1) Setup WiFi Network Adapter
#install network manager (if not already installed)
sudo apt install network-manager
#list wifi interfaces - In my example below, the wlan interface is wlp3s0
sudo nmcli d
#turn on WiFi
sudo nmcli r wifi on
#List Wifi Networks (Just to check its working, however noting the Powerwall 3 Wifi Network is hidden, so you will not see it in the list)
sudo nmcli d wifi list
#replace <ssid> below with SSID from Powerwall 3 - Will be something like TealsaPW_XXXX, and also replace the ifname with the actual wifi interface name on your system
sudo nmcli c add type wifi con-name powerwall ifname wlp3s0 ssid <ssid>
#replace <password> with password from Powerwall 3
sudo nmcli c modify powerwall wifi-sec.key-mgmt wpa-psk wifi-sec.psk <password>
# The following is optional, to set a fixed IP address, as the PW3 will provide a DCHP IP Address
sudo nmcli con mod "powerwall" \
ipv4.addresses "192.168.91.50/24" \
ipv4.gateway "" \
ipv4.dns "" \
ipv4.dns-search "" \
ipv4.method "manual"
#bring up the network
sudo nmcli c up powerwall
#Ping the powerwall - If it responds, you are ready to move onto the next steps
ping 192.168.91.1
2) Install and run pypowerwall proxy in Docker
#If docker is not already installed, execute the following command:
sudo apt install docker.io docker-compose-v2 docker-doc
#'Install' & run the pypowerwall container. Replace the gateway_password, with the one from your PW3, and the timezone with that appropriate to your location
sudo docker run \
-d \
-p 8675:8675 \
-e PW_PORT='8675' \
-e PW_HOST='192.168.91.1' \
-e PW_GW_PWD='Gateway_Password' \
-e PW_TIMEZONE='Pacific/Auckland' \
-e TZ='Pacific/Auckland' \
-e PW_CACHE_EXPIRE='5' \
-e PW_DEBUG='no' \
-e PW_HTTPS='no' \
-e PW_STYLE='clear' \
--name pypowerwall \
--restart unless-stopped \
jasonacox/pypowerwall
The container will restart following reboots. Documentation for the proxy can be found at pypowerwall/proxy at main · jasonacox/pypowerwall · GitHub
Browse to your openhab server, on port 8675 (http://openhabserveraddress:8675/ ), and you should then see a animated graphic similar to the following:
This means you should be ready to move onto the next step, of setting up OpenHAB itself.
- Setup OpenHAB Things
This assumes you have got the HTTP binding installed already, and the baseURL below assumes you are using your OpenHAB server to run the pypowerwall proxy container:
The below is a sample of a few channels
UID: http:url:powerwall3_http
label: Powerwall 3 via pypowerwall proxy
thingTypeUID: http:url
configuration:
authMode: BASIC
ignoreSSLErrors: false
baseURL: http://localhost:8675
delay: 1000
stateMethod: GET
refresh: 10
commandMethod: GET
timeout: 10000
bufferSize: 2048
channels:
- id: last-failure
channelTypeUID: http:request-date-time
label: Last Failure
configuration: {}
- id: last-success
channelTypeUID: http:request-date-time
label: Last Success
configuration: {}
- id: pw3BatteryLevel
channelTypeUID: http:string
label: Powerwall 3 Battery Level
description: Powerwall 3 Battery Level via HTTP pypowerwall proxy
configuration:
mode: READONLY
stateExtension: /pw/level
- id: pw3BatteryPower
channelTypeUID: http:string
label: Powerwall 3 Battery Power
description: Powerwall 3 BatteryPower via HTTP pypowerwall proxy
configuration:
mode: READONLY
stateExtension: /pw/power
- id: pw3SitePower
channelTypeUID: http:string
label: Powerwall 3 Site Power
description: Powerwall 3 Site Power via HTTP pypowerwall proxy
configuration:
mode: READONLY
stateExtension: /pw/power
- id: pw3LoadPower
channelTypeUID: http:string
label: Powerwall 3 Load Power
description: Powerwall 3 Load Power via HTTP pypowerwall proxy
configuration:
mode: READONLY
stateExtension: /pw/power
- id: pw3SolarTotalPower
channelTypeUID: http:string
label: Powerwall 3 Total Solar Power
description: Powerwall 3 Total Solar Power via HTTP pypowerwall proxy
configuration:
mode: READONLY
stateExtension: /pw/power
- id: pw3MPPTAPower
channelTypeUID: http:string
label: Powerwall 3 MPPT A Power
description: Powerwall 3 MPPT A Power via HTTP pypowerwall proxy
configuration:
mode: READONLY
stateExtension: /pw/strings
- id: pw3MPPTBPower
channelTypeUID: http:string
label: Powerwall 3 MPPT B Power
description: Powerwall 3 MPPT B Power via HTTP pypowerwall proxy
configuration:
mode: READONLY
stateExtension: /pw/strings
- id: pw3MPPTCPower
channelTypeUID: http:string
label: Powerwall 3 MPPT C Power
description: Powerwall 3 MPPT C Power via HTTP pypowerwall proxy
configuration:
mode: READONLY
stateExtension: /pw/strings
- id: pw3MPPTDPower
channelTypeUID: http:string
label: Powerwall 3 MPPT D Power
description: Powerwall 3 MPPT D Power via HTTP pypowerwall proxy
configuration:
mode: READONLY
stateExtension: /pw/strings
- id: pw3MPPTEPower
channelTypeUID: http:string
label: Powerwall 3 MPPT E Power
description: Powerwall 3 MPPT E Power via HTTP pypowerwall proxy
configuration:
mode: READONLY
stateExtension: /pw/strings
- id: pw3MPPTFPower
channelTypeUID: http:string
label: Powerwall 3 MPPT F Power
description: Powerwall 3 MPPT F Power via HTTP pypowerwall proxy
configuration:
mode: READONLY
stateExtension: /pw/strings
- id: pw3GridStatus
channelTypeUID: http:string
label: Powerwall 3 Grid Status
description: Powerwall 3 Grid Status via HTTP pypowerwall proxy
configuration:
mode: READONLY
stateExtension: /freq
- id: pw3ProxyStatus
channelTypeUID: http:string
label: Powerwall 3 Proxy connection to PW3
description: Powerwall 3 Proxy connection to PW3 status
configuration:
mode: READONLY
stateExtension: /pw/is_connected
Then from there, you will need link the channels to items, and apply some JSONpath expressions to pull out the specific values related to the items, e.g. for the above channel examples, these would be (Pick whatever names UID’s you want - These are just as examples):
| Description | Channel ID | Item UID | JSONpath | Proxy Source |
|---|---|---|---|---|
| Powerwall 3 Battery Level | pw3BatteryLevel | PW3_Battery_Level | $.level | /pw/level |
| Powerwall 3 Battery Power | pw3BatteryPower | PW3_Battery_Power | $.battery | /pw/power |
| Powerwall 3 Load Power | pw3LoadPower | PW3_Site_Power | $.site | /pw/power |
| Powerwall 3 Total Solar Power | pw3SolarTotalPower | PW3_Total_Solar_Power | $.solar | /pw/power |
| Powerwall 3 MPPT A Power | pw3MPPTAPower | Powerwall_3_MPPT_A_Power | $.*.PVAC_PVMeasuredPower_A | /pw/strings |
| Powerwall 3 MPPT B Power | pw3MPPTBPower | Powerwall_3_MPPT_B_Power | $.*.PVAC_PVMeasuredPower_B | /pw/strings |
| Powerwall 3 MPPT C Power | pw3MPPTCPower | Powerwall_3_MPPT_C_Power | $.*.PVAC_PVMeasuredPower_C | /pw/strings |
| Powerwall 3 MPPT D Power | pw3MPPTDPower | Powerwall_3_MPPT_D_Power | $.*.PVAC_PVMeasuredPower_D | /pw/strings |
| Powerwall 3 MPPT E Power | pw3MPPTEPower | Powerwall_3_MPPT_E_Power | $.*.PVAC_PVMeasuredPower_E | /pw/strings |
| Powerwall 3 MPPT F Power | pw3MPPTFPower | Powerwall_3_MPPT_F_Power | $.*.PVAC_PVMeasuredPower_F | /pw/strings |
| Powerwall 3 Grid Status | pw3GridStatus | Powerwall_3_Grid_Status | config:js:1on0offtransform | /freq |
| Powerwall 3 Grid Status | pw3ProxyStatus | Powerwall_3_Proxy_Status | config:js:PW3_proxy_trueOnfalseOff | /pw/is_connected |
For the grid status the following is the config:js:1on0offtransform contents:
(function(data) {
var returnValue = JSON.parse(input).grid_status
if (returnValue == '0') {
return 'OFF';
} else
if (returnValue == "1") {
return 'ON';
} else
return ""
})(input)
And for the proxy status, the following is the config:js:PW3_proxy_trueOnfalseOff contents:
(function(data) {
var returnValue = JSON.parse(input).is_connected
if (returnValue == false) {
return 'OFF';
} else
if (returnValue == true) {
return 'ON';
} else
return "OFF"
})(input)
Whilst the status of the ‘thing’ will change if the Proxy stops responding, the is_connected channel is useful to inform OpenHAB if the Proxy has lost connection to the Powerwall itself.
Note that the 10000ms timeout is required for the HTTP Thing for this to work however - Most requests complete in subsecond time, but if the Proxy loses connection to the Powerwall, all Proxy responses take longer, (most will return a null), however the is_connected will also take longer, and we want it to return a false, so we can tell OpenHab that the Powerwall network connection is offline, rather than it just timing out.
There are a ton of other stats available via the Proxy, but also refer to the proxy documentation for some cases where data is not available for the PW3 (The proxy also supports predecessor versions).
Note for the MPPT Power Readings, I use a wildcard in the JSONpath - The powerwall unit ID/serial number forms part of the path, and the wildcard works just fine…. if you only have one Powerwall !! I assume this section may be repeated, if you have multiple units on your site, in which case you will just need to replace the wildcard with the specific ID’s for each unit.
A note for those in New Zealand & Australia:
- There are 6 logical string values in the PW3 interface
- For those in North America etc, they can use the 6 string values individually, as this matches the 6 physical MPPT inputs on the PW3
- For those of us at the bottom of the world (NZ/Aus), the PW3 ships with only 3 physical MPPT inputs, but still displays 6 string values in the interface
- In essence, it looks like the inputs are paired (physically jumpered together) to provide higher current capacity, so to get the readings for the 3 physical MPPT inputs, you will need to add A+B, C+D,E+F to get the correct total current and power for each string. Obviously you don’t need to do that for voltage, and can just take that value for A,C,E which will/should be identical to their paired inputs.
"PVAC_PVCurrent_A": 0,
"PVAC_PVCurrent_B": 0,
"PVAC_PVCurrent_C": 0,
"PVAC_PVCurrent_D": 0,
"PVAC_PVCurrent_E": 0,
"PVAC_PVCurrent_F": 0,
"PVAC_PVMeasuredPower_A": 0,
"PVAC_PVMeasuredPower_B": 0,
"PVAC_PVMeasuredPower_C": 0,
"PVAC_PVMeasuredPower_D": 0,
"PVAC_PVMeasuredPower_E": 0,
"PVAC_PVMeasuredPower_F": 0,
"PVAC_PVMeasuredVoltage_A": 2,
"PVAC_PVMeasuredVoltage_B": 2,
"PVAC_PVMeasuredVoltage_C": 6,
"PVAC_PVMeasuredVoltage_D": 6,
"PVAC_PVMeasuredVoltage_E": 22,
"PVAC_PVMeasuredVoltage_F": 22,
I will continue to add to this post (Including my final findings/setup on the string values), as I expand on my usage of the statistics, but really, once you have the above data coming into OpenHAB, you can apply your usual persistence, and presentation approaches, including use of some of the ‘Energy’ widgets others have so kindly created.
Hope this helps
