how to add APSystems ECU-3 solar inverter monitor

Topics (not sure which fora)
when not sure where to post, post here and mods will move it to right forum.

Moderators: leecollings, remb0

Post Reply
User avatar
FireWizard
Posts: 1745
Joined: Tuesday 25 December 2018 12:11
Target OS: Raspberry Pi / ODroid
Domoticz version: Beta
Location: Voorthuizen (NL)
Contact:

Re: how to add APSystems ECU-3 solar inverter monitor

Post by FireWizard »

Hi Bernhard,

Thanks for the feedback.
Later I will post the complete flow, so that others can make their own application.

Thanks for the co-operation and have a nice weekend,

Regards
Benneton
Posts: 111
Joined: Thursday 08 December 2016 9:46
Target OS: Raspberry Pi / ODroid
Domoticz version:
Contact:

Re: how to add APSystems ECU-3 solar inverter monitor

Post by Benneton »

Hi FireWizard,

It was a pleasure to work with you!

Thank you for all!
You too a lovely weekend.

Bernard
User avatar
FireWizard
Posts: 1745
Joined: Tuesday 25 December 2018 12:11
Target OS: Raspberry Pi / ODroid
Domoticz version: Beta
Location: Voorthuizen (NL)
Contact:

Re: how to add APSystems ECU-3 solar inverter monitor

Post by FireWizard »

Hi all,

Please find below the final Node Red flow in order to scrape data from AP Systems ECU-3 Home page and the realtimedata page.

This flow is made for 6 inverters, each containing 2 solar panels. So 12 solar panels.
In case you have more or less inverters and/or panels you should modify the function node marked "Solar Production Inverters to Domoticz".
Each block of code contains the sensors available from one inverter.

In all cases, you should modify the following nodes to your need:

1. Node marked : "5 Min Tick":
- Tick de box, before "Inject once after".
- Select "Repeat" as "Interval".
- Select the interval, you want to poll the ECU-3 (The ECU-3 is updated every 5 minutes, so a faster time is useless).

2. Node marked: "Day Time switch":
- Insert your own "Latitude"and "Longitude" co-ordinates.

3. Node marked: "HTTP AP Systems Overview Request":
- Insert your own ECU-3 URL: http://<IP Address>/index.php/home.

4. Node marked: "HTTP AP Systems Production Request":
- Insert your own ECU-3 URL: http://<IP Address>/index.php/realtimedata.

5. Node marked: "Solar Overview to Domoticz":
- Insert your own Domoticz IDX for the applicable sensors.

6. Node marked: "Solar Environmental to Domoticz":
- Insert your own Domoticz IDX for the applicable sensors.

7. Node marked: "Solar Production Inverters to Domoticz":
- Insert your own InverterID (after "case")
- Insert your own Domoticz IDX for the applicable sensors.
- if you have more than 6 inverters, copy line 6 and insert as many as needed. Number them accordingly. 7, 8, etc.
- if you have more than 6 inverters, copy line 9 - 17 and paste them in line 63. Repeat it as much as you need.
- if you have more than 6 inverters, insert msg7, msg8, etc in line 65 (straight after msg6, seperated by comma's).
- if you have less than 6 inverters, delete line 6, 5 etc.
- if you have less than 6 inverters, delete line 54-62, etc. As much as you need.
- if you have less than 6 inverters, delete msg 6, msg5, etc in line 65.

8. Node marked: "Domoticz In":
- Insert your own desired "Server name"
- Configure the node (Pencil right side of Server)
- In the Connection Tab configure the IP address of the MQTT Broker. If it runs on the same device as Node Red you can use "localhost".
- In the Security Tab configure Username/Password (if you have your MQTT broker protected with a username and password. (Recommended).

All used nodes are core Node Red nodes, except the "Day Time Switch". this node has to be installed, using the palette or from the command line;
Node name: node-red-contrib-time-switch. From the cli install the node with "npm install node-red-contrib-time-switch".

The complete flow you will find below:

Code: Select all

[{"id":"d243b84a.4ac438","type":"tab","label":"AP Systems","disabled":false,"info":""},{"id":"63bcbc31.eb708c","type":"http request","z":"d243b84a.4ac438","name":"HTTP AP Systems Production Request","method":"GET","ret":"txt","paytoqs":false,"url":"http://192.168.1.50/index.php/realtimedata","tls":"","proxy":"","x":420,"y":440,"wires":[["c3df4a05.c383"]]},{"id":"d5e45a3a.244e5","type":"debug","z":"d243b84a.4ac438","name":"HTML Output","active":false,"tosidebar":true,"console":false,"tostatus":false,"complete":"payload","targetType":"msg","x":720,"y":500,"wires":[]},{"id":"8501a12b.61eb4","type":"inject","z":"d243b84a.4ac438","name":"5 Min Tick","topic":"","payload":"","payloadType":"date","repeat":"","crontab":"","once":false,"onceDelay":"","x":140,"y":360,"wires":[["d1c96d07.95888"]]},{"id":"c3df4a05.c383","type":"html","z":"d243b84a.4ac438","name":"Scrape inverter","property":"payload","outproperty":"payload","tag":"td","ret":"html","as":"single","x":720,"y":440,"wires":[["d5e45a3a.244e5","80391cd8.5820d8"]]},{"id":"80391cd8.5820d8","type":"function","z":"d243b84a.4ac438","name":"Create Inverter Array","func":"var i;\nfor (i = 0; i < msg.payload.length/9; i++) {\nvar InverterIDA = msg.payload[9*i+0];\nvar CurrentPowerA = msg.payload[9*i+1];\nvar GridFreq = msg.payload[9*i+2];\nvar GridVoltageA = msg.payload[9*i+3];\nvar GridTemp = msg.payload[9*i+4];\nvar GridReportTime = msg.payload[9*i+5];\nvar InverterIDB = msg.payload[9*i+6];\nvar CurrentPowerB = msg.payload[9*i+7];\nvar GridVoltageB = msg.payload[9*i+8];\nnewMsg = {payload: ([InverterIDA.substr(0,12),CurrentPowerA.slice(0,-2),GridVoltageA.slice(0,-2),CurrentPowerB.slice(0,-2),GridVoltageB.slice(0,-2),GridFreq.slice(0,-3),GridTemp.slice(0,-8)])}\nnode.send(newMsg);\n}","outputs":1,"noerr":0,"x":960,"y":440,"wires":[["7d148fd5.6837a8","752a8421.e09cf4"]]},{"id":"7d148fd5.6837a8","type":"debug","z":"d243b84a.4ac438","name":"Output APS Array","active":false,"tosidebar":true,"console":false,"tostatus":false,"complete":"payload","targetType":"msg","x":1310,"y":440,"wires":[]},{"id":"752a8421.e09cf4","type":"function","z":"d243b84a.4ac438","name":"Solar Production Inverters to Domoticz","func":"var msg1 = {};\nvar msg2 = {};\nvar msg3 = {};\nvar msg4 = {};\nvar msg5 = {};\nvar msg6 = {};\n\nswitch (msg.payload[0]) {\n\n    case \"404000191265\": //Inverter 1\n    msg1.payload = {\"command\":\"udevice\",\"idx\":1001,\"nvalue\":0,\"svalue\":(msg.payload[1] + \";0\")}; //Current Power A\n    msg2.payload = {\"command\":\"udevice\",\"idx\":1002,\"nvalue\":0,\"svalue\":(msg.payload[2])}; //Voltage A\n    msg3.payload = {\"command\":\"udevice\",\"idx\":1003,\"nvalue\":0,\"svalue\":(msg.payload[3] + \";0\")}; //Current Power B\n    msg4.payload = {\"command\":\"udevice\",\"idx\":1004,\"nvalue\":0,\"svalue\":(msg.payload[4])}; //Voltage B\n    msg5.payload = {\"command\":\"udevice\",\"idx\":1005,\"nvalue\":0,\"svalue\":(msg.payload[5])}; //Frequency\n    msg6.payload = {\"command\":\"udevice\",\"idx\":1006,\"nvalue\":0,\"svalue\":(msg.payload[6])}; //Temperature\n    break;\n\n    case \"404000191123\": //Inverter 2\n    msg1.payload = {\"command\":\"udevice\",\"idx\":2001,\"nvalue\":0,\"svalue\":(msg.payload[1] + \";0\")}; //Current Power A\n    msg2.payload = {\"command\":\"udevice\",\"idx\":2002,\"nvalue\":0,\"svalue\":(msg.payload[2])}; //Voltage A\n    msg3.payload = {\"command\":\"udevice\",\"idx\":2003,\"nvalue\":0,\"svalue\":(msg.payload[3] + \";0\")}; //Current Power B\n    msg4.payload = {\"command\":\"udevice\",\"idx\":2004,\"nvalue\":0,\"svalue\":(msg.payload[4])}; //Voltage B\n    msg5.payload = {\"command\":\"udevice\",\"idx\":2005,\"nvalue\":0,\"svalue\":(msg.payload[5])}; //Frequency\n    msg6.payload = {\"command\":\"udevice\",\"idx\":2006,\"nvalue\":0,\"svalue\":(msg.payload[6])}; //Temperature\n    break;\n\n    case \"404000193004\": //Inverter 3\n    msg1.payload = {\"command\":\"udevice\",\"idx\":3001,\"nvalue\":0,\"svalue\":(msg.payload[1] + \";0\")}; //Current Power A\n    msg2.payload = {\"command\":\"udevice\",\"idx\":3002,\"nvalue\":0,\"svalue\":(msg.payload[2])}; //Voltage A\n    msg3.payload = {\"command\":\"udevice\",\"idx\":3003,\"nvalue\":0,\"svalue\":(msg.payload[3] + \";0\")}; //Current Power B\n    msg4.payload = {\"command\":\"udevice\",\"idx\":3004,\"nvalue\":0,\"svalue\":(msg.payload[4])}; //Voltage B\n    msg5.payload = {\"command\":\"udevice\",\"idx\":3005,\"nvalue\":0,\"svalue\":(msg.payload[5])}; //Frequency\n    msg6.payload = {\"command\":\"udevice\",\"idx\":3006,\"nvalue\":0,\"svalue\":(msg.payload[6])}; //Temperature\n    break;\n\n    case \"404000191257\": //Inverter 4\n    msg1.payload = {\"command\":\"udevice\",\"idx\":4001,\"nvalue\":0,\"svalue\":(msg.payload[1] + \";0\")}; //Current Power A\n    msg2.payload = {\"command\":\"udevice\",\"idx\":4002,\"nvalue\":0,\"svalue\":(msg.payload[2])}; //Voltage A\n    msg3.payload = {\"command\":\"udevice\",\"idx\":4003,\"nvalue\":0,\"svalue\":(msg.payload[3] + \";0\")}; //Current Power B\n    msg4.payload = {\"command\":\"udevice\",\"idx\":4004,\"nvalue\":0,\"svalue\":(msg.payload[4])}; //Voltage B\n    msg5.payload = {\"command\":\"udevice\",\"idx\":4005,\"nvalue\":0,\"svalue\":(msg.payload[5])}; //Frequency\n    msg6.payload = {\"command\":\"udevice\",\"idx\":4006,\"nvalue\":0,\"svalue\":(msg.payload[6])}; //Temperature\n    break;\n\n    case \"404000192992\": //Inverter 5\n    msg1.payload = {\"command\":\"udevice\",\"idx\":5001,\"nvalue\":0,\"svalue\":(msg.payload[1] + \";0\")}; //Current Power A\n    msg2.payload = {\"command\":\"udevice\",\"idx\":5002,\"nvalue\":0,\"svalue\":(msg.payload[2])}; //Voltage A\n    msg3.payload = {\"command\":\"udevice\",\"idx\":5003,\"nvalue\":0,\"svalue\":(msg.payload[3] + \";0\")}; //Current Power B\n    msg4.payload = {\"command\":\"udevice\",\"idx\":5004,\"nvalue\":0,\"svalue\":(msg.payload[4])}; //Voltage B\n    msg5.payload = {\"command\":\"udevice\",\"idx\":5005,\"nvalue\":0,\"svalue\":(msg.payload[5])}; //Frequency\n    msg6.payload = {\"command\":\"udevice\",\"idx\":5006,\"nvalue\":0,\"svalue\":(msg.payload[6])}; //Temperature\n    break;\n\n    case \"404000191779\": //Inverter 6\n    msg1.payload = {\"command\":\"udevice\",\"idx\":6001,\"nvalue\":0,\"svalue\":(msg.payload[1] + \";0\")}; //Current Power A\n    msg2.payload = {\"command\":\"udevice\",\"idx\":6002,\"nvalue\":0,\"svalue\":(msg.payload[2])}; //Voltage A\n    msg3.payload = {\"command\":\"udevice\",\"idx\":6003,\"nvalue\":0,\"svalue\":(msg.payload[3] + \";0\")}; //Current Power B\n    msg4.payload = {\"command\":\"udevice\",\"idx\":6004,\"nvalue\":0,\"svalue\":(msg.payload[4])}; //Voltage B\n    msg5.payload = {\"command\":\"udevice\",\"idx\":6005,\"nvalue\":0,\"svalue\":(msg.payload[5])}; //Frequency\n    msg6.payload = {\"command\":\"udevice\",\"idx\":6006,\"nvalue\":0,\"svalue\":(msg.payload[6])}; //Temperature\n    break;\n\n}\nreturn [[msg1,msg2,msg3,msg4,msg5,msg6]];","outputs":1,"noerr":0,"x":1020,"y":500,"wires":[["5bea947.a4ba1ec","fdfef99c.3962f8"]]},{"id":"5bea947.a4ba1ec","type":"debug","z":"d243b84a.4ac438","name":"Domoticz In","active":false,"tosidebar":true,"console":false,"tostatus":false,"complete":"payload","targetType":"msg","x":1310,"y":500,"wires":[]},{"id":"fdfef99c.3962f8","type":"mqtt out","z":"d243b84a.4ac438","name":"Domoticz In","topic":"domoticz/in","qos":"2","retain":"false","broker":"f9f13036.e28b58","x":1530,"y":360,"wires":[]},{"id":"a1776ce7.3be728","type":"http request","z":"d243b84a.4ac438","name":"HTTP AP Systems Overview Request","method":"GET","ret":"txt","paytoqs":false,"url":"http://192.168.2.88/index.php/home","tls":"","proxy":"","x":420,"y":280,"wires":[["f9cd660b.5528c","9da26ffb.4f20e"]]},{"id":"f9cd660b.5528c","type":"html","z":"d243b84a.4ac438","name":"Scrape overview","property":"payload","outproperty":"payload","tag":"td","ret":"html","as":"single","x":730,"y":260,"wires":[["f3c1c3d6.06c7b"]]},{"id":"4f709cae.43ea9c","type":"debug","z":"d243b84a.4ac438","name":"Output Overview Array","active":false,"tosidebar":true,"console":false,"tostatus":false,"complete":"payload","targetType":"msg","x":1270,"y":260,"wires":[]},{"id":"d1c96d07.95888","type":"time-switch","z":"d243b84a.4ac438","name":"Day Time switch","lat":"52.000000","lon":"5.000000","startTime":"sunrise","endTime":"sunset","startOffset":"-30","endOffset":"+30","x":350,"y":360,"wires":[["63bcbc31.eb708c","a1776ce7.3be728"],[]]},{"id":"f3c1c3d6.06c7b","type":"function","z":"d243b84a.4ac438","name":"Create Overview Array","func":"var LifeTimeGen = msg.payload[1];\nvar LastSystemPower = msg.payload[2];\nvar CurDayGen = msg.payload[3];\nnewMsg = {payload: ([LifeTimeGen.slice(0,-4),LastSystemPower.slice(0,-2),CurDayGen.slice(0,-4)])};\nreturn newMsg;\n","outputs":1,"noerr":0,"x":970,"y":260,"wires":[["364dfbb1.e2d524","4f709cae.43ea9c"]]},{"id":"9da26ffb.4f20e","type":"html","z":"d243b84a.4ac438","name":"Scrape environment","property":"payload","outproperty":"payload","tag":"center","ret":"html","as":"single","x":740,"y":300,"wires":[["dadfb540.a207a"]]},{"id":"fed6502.196f5b","type":"debug","z":"d243b84a.4ac438","name":"Output Environmental Array","active":false,"tosidebar":true,"console":false,"tostatus":false,"complete":"payload","targetType":"msg","x":1260,"y":300,"wires":[]},{"id":"364dfbb1.e2d524","type":"function","z":"d243b84a.4ac438","name":"Solar Overview to Domoticz","func":"var msg1 = {};\nvar msg2 = {};\nvar msg3 = {};\n\nmsg1.payload = {\"command\":\"udevice\",\"idx\":7001,\"nvalue\":0,\"svalue\":(msg.payload[0])}; //Lifetime generation\nmsg2.payload = {\"command\":\"udevice\",\"idx\":7002,\"nvalue\":0,\"svalue\":(msg.payload[1] + \";0\")}; //Last System Power\nmsg3.payload = {\"command\":\"udevice\",\"idx\":7003,\"nvalue\":0,\"svalue\":(msg.payload[2])}; //Generation of Current Day\n\nreturn [[msg1,msg2,msg3]];","outputs":1,"noerr":0,"x":980,"y":200,"wires":[["d97e6cb5.c7c25","fdfef99c.3962f8"]]},{"id":"d97e6cb5.c7c25","type":"debug","z":"d243b84a.4ac438","name":"Domoticz In","active":false,"tosidebar":true,"console":false,"tostatus":false,"complete":"payload","targetType":"msg","x":1310,"y":160,"wires":[]},{"id":"8321d666.fac028","type":"function","z":"d243b84a.4ac438","name":"Solar Environmental to Domoticz","func":"var msg1 = {};\nvar msg2 = {};\nvar msg3 = {};\n\nmsg1.payload = {\"command\":\"udevice\",\"idx\":8001,\"nvalue\":0,\"svalue\":parseFloat((msg.payload[0]) * 3.78541178).toFixed(1)}; //CO2 Car (L)\nmsg2.payload = {\"command\":\"udevice\",\"idx\":8002,\"nvalue\":0,\"svalue\":(msg.payload[1])}; //CO2 Tree\nmsg3.payload = {\"command\":\"udevice\",\"idx\":8003,\"nvalue\":0,\"svalue\":(msg.payload[2])}; //CO2 Factory (Kg)\n\nreturn [[msg1,msg2,msg3]];","outputs":1,"noerr":0,"x":1000,"y":360,"wires":[["93b122ab.4b1ae","fdfef99c.3962f8"]]},{"id":"dadfb540.a207a","type":"function","z":"d243b84a.4ac438","name":"Create Environmental Array","func":"var CO2Car = msg.payload[0];\nvar CO2Tree = msg.payload[1];\nvar CO2Factory = msg.payload[2];\nnewMsg = {payload: ([CO2Car.slice(0,-12),CO2Tree.slice(0,-10),CO2Factory.slice(0,-7)])};\nreturn newMsg;\n","outputs":1,"noerr":0,"x":980,"y":300,"wires":[["8321d666.fac028","fed6502.196f5b"]]},{"id":"93b122ab.4b1ae","type":"debug","z":"d243b84a.4ac438","name":"Domoticz In","active":false,"tosidebar":true,"console":false,"tostatus":false,"complete":"payload","targetType":"msg","x":1290,"y":400,"wires":[]},{"id":"b0d7a44d.92a2b8","type":"comment","z":"d243b84a.4ac438","name":"Poll Home Page","info":"This node polls http://<ip address>/index.php/home","x":340,"y":220,"wires":[]},{"id":"bce11b22.56815","type":"comment","z":"d243b84a.4ac438","name":"Poll Inverter Page","info":"This node polls http://<ip address>/index.php/realtimedata","x":350,"y":500,"wires":[]},{"id":"f9f13036.e28b58","type":"mqtt-broker","z":"","name":"RPI1_ MQTT_Broker","broker":"192.168.1.10","port":"1883","clientid":"","usetls":false,"compatmode":true,"keepalive":"60","cleansession":true,"birthTopic":"","birthQos":"0","birthRetain":"false","birthPayload":"","closeTopic":"","closeQos":"0","closePayload":"","willTopic":"","willQos":"0","willPayload":""}]
Success with your implementations.
In case of problems or questions, do not hesitate to ask.

Credits are also going to Bernhard (Benneton), because without his help in providing screenshots, access to the web page and the support in debugging by giving valuable feedback, the development of this flow, would not have been possible.

Best Regards,
FireWizard
Macguyver
Posts: 14
Joined: Wednesday 26 February 2020 14:07
Target OS: OS X
Domoticz version: Latest
Location: Zeeland
Contact:

Re: how to add APSystems ECU-3 solar inverter monitor

Post by Macguyver »

Great tutorial, have worked my way through it but keep running into some problems. I think it has something to do with the fact that the URL' s look different. (eg: i do get some output but can't get it to look the same as what the posts show)

my 'home' url looks like: http://192.168.2.13/cgi-bin/home

it creates an error and no data output
Schermafbeelding 2020-03-12 om 17.12.23.png
Schermafbeelding 2020-03-12 om 17.12.23.png (62.22 KiB) Viewed 2631 times
my 'realtimedata' url looks like: http://192.168.2.13/cgi-bin/parameters

it does give some output but it does not compare with the examples
Schermafbeelding 2020-03-12 om 17.15.05.png
Schermafbeelding 2020-03-12 om 17.15.05.png (131.99 KiB) Viewed 2631 times
Schermafbeelding 2020-03-12 om 17.32.03.png
Schermafbeelding 2020-03-12 om 17.32.03.png (46.9 KiB) Viewed 2631 times
any suggestions on how to get this working? soo i can continue to work my way through the other nodes in the script.

*soo far is tried and altered the given settings (incl. the dummie devices in domoticz) of the script on p3 and the complete script on p5

groeten,
Macguyver
Benneton
Posts: 111
Joined: Thursday 08 December 2016 9:46
Target OS: Raspberry Pi / ODroid
Domoticz version:
Contact:

Re: how to add APSystems ECU-3 solar inverter monitor

Post by Benneton »

Hi Macguyver,

I noticed that you are running your ECU on software version 3.11.4
The version this tutorial works with is version 4.1. In this version the URL changed.

I have been looking on the web to see if there are any updates that can be downloaded for security and or bug fixes.
I havent found any .

So I have no idea how the ECU software can be upgraded and if this version is related to the hardware.

I know there are other options to get this done, which did not work for me as I run V4.1, but were made for version 3.x

Hope this helps a bit.

Bernard
User avatar
FireWizard
Posts: 1745
Joined: Tuesday 25 December 2018 12:11
Target OS: Raspberry Pi / ODroid
Domoticz version: Beta
Location: Voorthuizen (NL)
Contact:

Re: how to add APSystems ECU-3 solar inverter monitor

Post by FireWizard »

Hello @Macguyver,

As @Benneton already noted, you are running ECU software 3.11.4 and he is running 4.1.
The easiest solution would be to update your version to v4.1, but this is obviously not an option.
So we don't spend time on that.

When the flow has been created, I already took into account that at a certain moment the web interface may change, because of an upgrade.
For that reason I created two "Function" nodes, while it would have been possible to do it in one (larger) node.

The first one handles the creation of the different arrays, while the second one handles the preparation of the MQTT message.
As you might have noticed, there exist a difference between the webpage in your version and @Benneton version. It means, that we have to modify the first "Function" node. As @Benneton has 6 inverters and 12 solar panels and you have 9 inverters with 18 solar panels, we have to modify the second "Function" node as well.

1. The overview page.

There is a difference between to two versions and also the URL is different.
Your URL: http://<IP Address>/cgi-bin/home, @Benneton URL: http://<IP Address>/index.php/home
You wrote:
it creates an error and no data output
I can imagine. Did you change the URL to the overview page?
But as there exist a significant difference between the versions, I suggest we handle that later.

2. The inverter page

Your real time data is available at http://<IP Address>/cgi-bin/parameters. I see that you have changed the URL, because you receive real time data.
In version 4.1 the URL is: http://<IP Address>/index.php/realtimedata

In your second screenshot I see that the received data is more or less the same as, what @Benneton receives.

If we look at the table in the second screenshot, you will see it consists of 19 rows and 6 columns
The rows includes the header and 18 solar panel data.
You see also that it is nicely saved in an array with contains 19 x 6 = 114 elements (See your third screenshot)
You see also the data. This means that the "Selector" in the html node, marked "Scrape inverter" is OK.

Before we modify the first "Function node", you have to decide, which sensors should be sent to Domoticz.

Each Row contains the following in their respective columns:
- Inverter ID: 2 Solar panels, marked A and B. They will be used as the key.
- Current Power for each panel; that is obvious and has to be sent to Domoticz
- Grid Frequency; it is indicated for each panel, but in version 4.1 it is only indicated per inverter.
It is identical for the A and B panel. So indication per inverter is probably sufficient.
- Grid Voltage; it is indicated per panel, but is it needed per panel? We kept it in v4.1
- Temperature, See the comment for Grid frequency.
- Date is not used as this is created in Domoticz.

Of course it is possible to modify the first "Function" node for all possibilities, but I suggest that you indicate, which sensor you want to have presented in Domoticz. Of course the Current Power per solar panel, but do you want the Grid frequency, Grid Voltage and Temperature per panel or per inverter?
efarmer1
Posts: 15
Joined: Sunday 15 December 2019 15:26
Target OS: Linux
Domoticz version:
Contact:

Re: how to add APSystems ECU-3 solar inverter monitor

Post by efarmer1 »

Any one did this for APS ecu-R?
or will this method work also for ecu-r

thank you
User avatar
FireWizard
Posts: 1745
Joined: Tuesday 25 December 2018 12:11
Target OS: Raspberry Pi / ODroid
Domoticz version: Beta
Location: Voorthuizen (NL)
Contact:

Re: how to add APSystems ECU-3 solar inverter monitor

Post by FireWizard »

Hello,

@efarmer1

Basically scraping data from a website is not specific for APSystems, so if there is data, you can access in an APS ECU-R webpage, it should be possible.
But probably the lay-out of the page, tables, row, columns, etc are different, so it will require an individual approach.

It has been made for version v4.1 and will be made for this version v3.11.4. Every version might be different, and maybe someone else made it for some other version.

How it works, you can find at:
http://noderedguide.com/node-red-lectur ... 6e24l0vq0l
https://stackoverflow.com/questions/556 ... n-node-red

Regards
Last edited by FireWizard on Sunday 13 September 2020 23:27, edited 1 time in total.
Macguyver
Posts: 14
Joined: Wednesday 26 February 2020 14:07
Target OS: OS X
Domoticz version: Latest
Location: Zeeland
Contact:

Re: how to add APSystems ECU-3 solar inverter monitor

Post by Macguyver »

Hi Bernard,

Already see an asnwer from Firewizard below but what version is your ECU labelled?
mine says on the sticker 203XXXXXXXXX that is on the ecu.

Regards, Macguyver
Benneton wrote: Friday 13 March 2020 9:36 Hi Macguyver,

I noticed that you are running your ECU on software version 3.11.4
The version this tutorial works with is version 4.1. In this version the URL changed.

I have been looking on the web to see if there are any updates that can be downloaded for security and or bug fixes.
I havent found any .

So I have no idea how the ECU software can be upgraded and if this version is related to the hardware.

I know there are other options to get this done, which did not work for me as I run V4.1, but were made for version 3.x

Hope this helps a bit.

Bernard
Macguyver
Posts: 14
Joined: Wednesday 26 February 2020 14:07
Target OS: OS X
Domoticz version: Latest
Location: Zeeland
Contact:

Re: how to add APSystems ECU-3 solar inverter monitor

Post by Macguyver »

Hello Firewizard,

Thank you for your quick reply!

I would also like to have the whole works, as @Benneton,

Regards, Macguyver

FireWizard wrote: Friday 13 March 2020 14:18 Hello @Macguyver,

As @Benneton already noted, you are running ECU software 3.11.4 and he is running 4.1.
The easiest solution would be to update your version to v4.1, but this is obviously not an option.
So we don't spend time on that.

When the flow has been created, I already took into account that at a certain moment the web interface may change, because of an upgrade.
For that reason I created two "Function" nodes, while it would have been possible to do it in one (larger) node.

The first one handles the creation of the different arrays, while the second one handles the preparation of the MQTT message.
As you might have noticed, there exist a difference between the webpage in your version and @Benneton version. It means, that we have to modify the first "Function" node. As @Benneton has 6 inverters and 12 solar panels and you have 9 inverters with 18 solar panels, we have to modify the second "Function" node as well.

1. The overview page.

There is a difference between to two versions and also the URL is different.
Your URL: http://<IP Address>/cgi-bin/home, @Benneton URL: http://<IP Address>/index.php/home
You wrote:
it creates an error and no data output
I can imagine. Did you change the URL to the overview page?
But as there exist a significant difference between the versions, I suggest we handle that later.

2. The inverter page

Your real time data is available at http://<IP Address>/cgi-bin/parameters. I see that you have changed the URL, because you receive real time data.
In version 4.1 the URL is: http://<IP Address>/index.php/realtimedata

In your second screenshot I see that the received data is more or less the same as, what @Benneton receives.

If we look at the table in the second screenshot, you will see it consists of 19 rows and 6 columns
The rows includes the header and 18 solar panel data.
You see also that it is nicely saved in an array with contains 19 x 6 = 114 elements (See your third screenshot)
You see also the data. This means that the "Selector" in the html node, marked "Scrape inverter" is OK.

Before we modify the first "Function node", you have to decide, which sensors should be sent to Domoticz.

Each Row contains the following in their respective columns:
- Inverter ID: 2 Solar panels, marked A and B. They will be used as the key.
- Current Power for each panel; that is obvious and has to be sent to Domoticz
- Grid Frequency; it is indicated for each panel, but in version 4.1 it is only indicated per inverter.
It is identical for the A and B panel. So indication per inverter is probably sufficient.
- Grid Voltage; it is indicated per panel, but is it needed per panel? We kept it in v4.1
- Temperature, See the comment for Grid frequency.
- Date is not used as this is created in Domoticz.

Of course it is possible to modify the first "Function" node for all possibilities, but I suggest that you indicate, which sensor you want to have presented in Domoticz. Of course the Current Power per solar panel, but do you want the Grid frequency, Grid Voltage and Temperature per panel or per inverter?
User avatar
FireWizard
Posts: 1745
Joined: Tuesday 25 December 2018 12:11
Target OS: Raspberry Pi / ODroid
Domoticz version: Beta
Location: Voorthuizen (NL)
Contact:

Re: how to add APSystems ECU-3 solar inverter monitor

Post by FireWizard »

Hello,

@Macguyver

This means that you will have to create 18 Virtual Sensors for the Current Power, 9 virtual sensors for the Frequency, 18 virtual sensors for the Voltage and 9 for the Temperature.

This is all described earlier in this thread.

Can you replace the contents of the "Function" node, called "Create Inverter Array", with the text below and post the output of a debug node, connected to that "Function" node?

Code: Select all

var i;
for (i = 0; i < (msg.payload.length-6)/12; i++) {
var InverterIDA = msg.payload[12*i+6];
var CurrentPowerA = msg.payload[12*i+7];
var GridFreqA = msg.payload[12*i+8];
var GridVoltageA = msg.payload[12*i+9];
var TempA = msg.payload[12*i+10];
var DateA = msg.payload[12*i+11];
var InverterIDB = msg.payload[12*i+12];
var CurrentPowerB = msg.payload[12*i+13];
var GridFreqB = msg.payload[12*i+14];
var GridVoltageB = msg.payload[12*i+15];
var TempB = msg.payload[12*i+16];
var DateB = msg.payload[12*i+17];
newMsg = {payload: ([InverterIDA.substr(0,12),CurrentPowerA.slice(0,-2),GridVoltageA.slice(0,-2),CurrentPowerB.slice(0,-2),GridVoltageB.slice(0,-2),GridFreqA.slice(0,-3),TempA.slice(0,-8)])}
node.send(newMsg);
}
I expect 9 objects, each containing an array of 7 elements.

If that is successful, then we can modify the second "Function" node.

Regards
Last edited by FireWizard on Friday 13 March 2020 19:27, edited 1 time in total.
Macguyver
Posts: 14
Joined: Wednesday 26 February 2020 14:07
Target OS: OS X
Domoticz version: Latest
Location: Zeeland
Contact:

Re: how to add APSystems ECU-3 solar inverter monitor

Post by Macguyver »

@Firewizard

I made a clean flow with the data for the complete flow.
- changed the url's to match mine
- replaced the script with the given

screenshot of the outcome:
The only output is on the debug: HTML Output
the: Output APS Array comes up empty =====> "SyntaxError: Unexpected token ')'"
Schermafbeelding 2020-03-13 om 18.03.01.png
Schermafbeelding 2020-03-13 om 18.03.01.png (257.82 KiB) Viewed 2614 times
User avatar
FireWizard
Posts: 1745
Joined: Tuesday 25 December 2018 12:11
Target OS: Raspberry Pi / ODroid
Domoticz version: Beta
Location: Voorthuizen (NL)
Contact:

Re: how to add APSystems ECU-3 solar inverter monitor

Post by FireWizard »

@ Macguyver

In your flow, I see a few things

1. For this moment, could you delete the connecting line between "Day Time switch" node and "HTTP AP Systems Overview Request".
This save at least the 3 error messages in the debug at the bottom.

2. Indeed I see that there is an error "Create Inverter Array" Function node (Red Triangle)
I found, that something had disappeared in my post. I corrected it in my previous post. Try to copy/paste it once more.

3. You did not "Deploy" the latest changes, as I see a blue circle above "HTML Output" debug node.

Regards
Macguyver
Posts: 14
Joined: Wednesday 26 February 2020 14:07
Target OS: OS X
Domoticz version: Latest
Location: Zeeland
Contact:

Re: how to add APSystems ECU-3 solar inverter monitor

Post by Macguyver »

Schermafbeelding 2020-03-13 om 20.01.48.png
Schermafbeelding 2020-03-13 om 20.01.48.png (98.74 KiB) Viewed 2610 times
@Firewizard

Yes this looks more like it.

guess the empty lines are because its dark and they are '0' now?
Schermafbeelding 2020-03-13 om 20.01.48.png
Schermafbeelding 2020-03-13 om 20.01.48.png (98.74 KiB) Viewed 2610 times
User avatar
FireWizard
Posts: 1745
Joined: Tuesday 25 December 2018 12:11
Target OS: Raspberry Pi / ODroid
Domoticz version: Beta
Location: Voorthuizen (NL)
Contact:

Re: how to add APSystems ECU-3 solar inverter monitor

Post by FireWizard »

Hello,

@Macguyver,

You wrote:
Yes this looks more like it.

guess the empty lines are because its dark and they are '0' now?
I see at least 9 arrays, each with 7 elements. They corresponds with the ID's (serialno's) in the webpage table.

- Micro-inverter ID (without A or B)
- Current Power A (currently 0 W, because it is dark)
- Grid Voltage A: 230V
- Current Power B (currently 0 W, because it is dark)
- Grid Voltage B (identical with Grid Voltage A): 230V
- Frequency (50Hz)
- Temperature Empty. A little strange, that if it is dark, no temperature is given.

Except 2 arrays, all other arrays are empty.
You can check that, if you see that the corresponding cells in the webpage are also empty. I expect that.
I expect that tomorrow, and hopefully we have some sun, all the arrays are filled.

The error message (Cannot read property 'slice' of undefined) is probably also caused by missing values.

In v4.1 I did not noticed that.

I believe that the first "Function" node is correct now and you can continue with the second one.
Check this node and do not forget to fill in your own IDX numbers (Total 9 x 6 = 54 indexes!)

Code: Select all

var msg1 = {};
var msg2 = {};
var msg3 = {};
var msg4 = {};
var msg5 = {};
var msg6 = {};

switch (msg.payload[0]) {

    case "404000191493": //Inverter 1
    msg1.payload = {"command":"udevice","idx":1001,"nvalue":0,"svalue":(msg.payload[1] + ";0")}; //Current Power A
    msg2.payload = {"command":"udevice","idx":1002,"nvalue":0,"svalue":(msg.payload[2])}; //Voltage A
    msg3.payload = {"command":"udevice","idx":1003,"nvalue":0,"svalue":(msg.payload[3] + ";0")}; //Current Power B
    msg4.payload = {"command":"udevice","idx":1004,"nvalue":0,"svalue":(msg.payload[4])}; //Voltage B
    msg5.payload = {"command":"udevice","idx":1005,"nvalue":0,"svalue":(msg.payload[5])}; //Frequency
    msg6.payload = {"command":"udevice","idx":1006,"nvalue":0,"svalue":(msg.payload[6])}; //Temperature
    break;

    case "404000191548": //Inverter 2
    msg1.payload = {"command":"udevice","idx":2001,"nvalue":0,"svalue":(msg.payload[1] + ";0")}; //Current Power A
    msg2.payload = {"command":"udevice","idx":2002,"nvalue":0,"svalue":(msg.payload[2])}; //Voltage A
    msg3.payload = {"command":"udevice","idx":2003,"nvalue":0,"svalue":(msg.payload[3] + ";0")}; //Current Power B
    msg4.payload = {"command":"udevice","idx":2004,"nvalue":0,"svalue":(msg.payload[4])}; //Voltage B
    msg5.payload = {"command":"udevice","idx":2005,"nvalue":0,"svalue":(msg.payload[5])}; //Frequency
    msg6.payload = {"command":"udevice","idx":2006,"nvalue":0,"svalue":(msg.payload[6])}; //Temperature
    break;

    case "404000191569": //Inverter 3
    msg1.payload = {"command":"udevice","idx":3001,"nvalue":0,"svalue":(msg.payload[1] + ";0")}; //Current Power A
    msg2.payload = {"command":"udevice","idx":3002,"nvalue":0,"svalue":(msg.payload[2])}; //Voltage A
    msg3.payload = {"command":"udevice","idx":3003,"nvalue":0,"svalue":(msg.payload[3] + ";0")}; //Current Power B
    msg4.payload = {"command":"udevice","idx":3004,"nvalue":0,"svalue":(msg.payload[4])}; //Voltage B
    msg5.payload = {"command":"udevice","idx":3005,"nvalue":0,"svalue":(msg.payload[5])}; //Frequency
    msg6.payload = {"command":"udevice","idx":3006,"nvalue":0,"svalue":(msg.payload[6])}; //Temperature
    break;

    case "404000191570": //Inverter 4
    msg1.payload = {"command":"udevice","idx":4001,"nvalue":0,"svalue":(msg.payload[1] + ";0")}; //Current Power A
    msg2.payload = {"command":"udevice","idx":4002,"nvalue":0,"svalue":(msg.payload[2])}; //Voltage A
    msg3.payload = {"command":"udevice","idx":4003,"nvalue":0,"svalue":(msg.payload[3] + ";0")}; //Current Power B
    msg4.payload = {"command":"udevice","idx":4004,"nvalue":0,"svalue":(msg.payload[4])}; //Voltage B
    msg5.payload = {"command":"udevice","idx":4005,"nvalue":0,"svalue":(msg.payload[5])}; //Frequency
    msg6.payload = {"command":"udevice","idx":4006,"nvalue":0,"svalue":(msg.payload[6])}; //Temperature
    break;

    case "404000191590": //Inverter 5
    msg1.payload = {"command":"udevice","idx":5001,"nvalue":0,"svalue":(msg.payload[1] + ";0")}; //Current Power A
    msg2.payload = {"command":"udevice","idx":5002,"nvalue":0,"svalue":(msg.payload[2])}; //Voltage A
    msg3.payload = {"command":"udevice","idx":5003,"nvalue":0,"svalue":(msg.payload[3] + ";0")}; //Current Power B
    msg4.payload = {"command":"udevice","idx":5004,"nvalue":0,"svalue":(msg.payload[4])}; //Voltage B
    msg5.payload = {"command":"udevice","idx":5005,"nvalue":0,"svalue":(msg.payload[5])}; //Frequency
    msg6.payload = {"command":"udevice","idx":5006,"nvalue":0,"svalue":(msg.payload[6])}; //Temperature
    break;

    case "404000191631": //Inverter 6
    msg1.payload = {"command":"udevice","idx":6001,"nvalue":0,"svalue":(msg.payload[1] + ";0")}; //Current Power A
    msg2.payload = {"command":"udevice","idx":6002,"nvalue":0,"svalue":(msg.payload[2])}; //Voltage A
    msg3.payload = {"command":"udevice","idx":6003,"nvalue":0,"svalue":(msg.payload[3] + ";0")}; //Current Power B
    msg4.payload = {"command":"udevice","idx":6004,"nvalue":0,"svalue":(msg.payload[4])}; //Voltage B
    msg5.payload = {"command":"udevice","idx":6005,"nvalue":0,"svalue":(msg.payload[5])}; //Frequency
    msg6.payload = {"command":"udevice","idx":6006,"nvalue":0,"svalue":(msg.payload[6])}; //Temperature
    break;

    case "404000191703": //Inverter 7
    msg1.payload = {"command":"udevice","idx":7001,"nvalue":0,"svalue":(msg.payload[1] + ";0")}; //Current Power A
    msg2.payload = {"command":"udevice","idx":7002,"nvalue":0,"svalue":(msg.payload[2])}; //Voltage A
    msg3.payload = {"command":"udevice","idx":7003,"nvalue":0,"svalue":(msg.payload[3] + ";0")}; //Current Power B
    msg4.payload = {"command":"udevice","idx":7004,"nvalue":0,"svalue":(msg.payload[4])}; //Voltage B
    msg5.payload = {"command":"udevice","idx":7005,"nvalue":0,"svalue":(msg.payload[5])}; //Frequency
    msg6.payload = {"command":"udevice","idx":7006,"nvalue":0,"svalue":(msg.payload[6])}; //Temperature
    break;

    case "404000191735": //Inverter 8
    msg1.payload = {"command":"udevice","idx":8001,"nvalue":0,"svalue":(msg.payload[1] + ";0")}; //Current Power A
    msg2.payload = {"command":"udevice","idx":8002,"nvalue":0,"svalue":(msg.payload[2])}; //Voltage A
    msg3.payload = {"command":"udevice","idx":8003,"nvalue":0,"svalue":(msg.payload[3] + ";0")}; //Current Power B
    msg4.payload = {"command":"udevice","idx":8004,"nvalue":0,"svalue":(msg.payload[4])}; //Voltage B
    msg5.payload = {"command":"udevice","idx":8005,"nvalue":0,"svalue":(msg.payload[5])}; //Frequency
    msg6.payload = {"command":"udevice","idx":8006,"nvalue":0,"svalue":(msg.payload[6])}; //Temperature
    break;

    case "404000192391": //Inverter 9
    msg1.payload = {"command":"udevice","idx":9001,"nvalue":0,"svalue":(msg.payload[1] + ";0")}; //Current Power A
    msg2.payload = {"command":"udevice","idx":9002,"nvalue":0,"svalue":(msg.payload[2])}; //Voltage A
    msg3.payload = {"command":"udevice","idx":9003,"nvalue":0,"svalue":(msg.payload[3] + ";0")}; //Current Power B
    msg4.payload = {"command":"udevice","idx":9004,"nvalue":0,"svalue":(msg.payload[4])}; //Voltage B
    msg5.payload = {"command":"udevice","idx":9005,"nvalue":0,"svalue":(msg.payload[5])}; //Frequency
    msg6.payload = {"command":"udevice","idx":9006,"nvalue":0,"svalue":(msg.payload[6])}; //Temperature
    break;
}
return [[msg1,msg2,msg3,msg4,msg5,msg6]];
[Edit] A check between v4.1. and v3.11.4 turned out that a difference between the two tables exists, so the error message (Cannot read property 'slice' of undefined) is probably also caused by this difference.

In the first function node replace:

Code: Select all

newMsg = {payload: ([InverterIDA.substr(0,12),CurrentPowerA.slice(0,-2),GridVoltageA.slice(0,-2),CurrentPowerB.slice(0,-2),GridVoltageB.slice(0,-2),GridFreqA.slice(0,-3),TempA.slice(0,-8)])}
with

Code: Select all

newMsg = {payload: ([InverterIDA.substr(0,12),CurrentPowerA.slice(0,-7),GridVoltageA.slice(0,-7),CurrentPowerB.slice(0,-7),GridVoltageB.slice(0,-7),GridFreqA.slice(0,-8),TempA.slice(0,-8)])}
Let me know what the result is, when the sun shines.

Regards
Macguyver
Posts: 14
Joined: Wednesday 26 February 2020 14:07
Target OS: OS X
Domoticz version: Latest
Location: Zeeland
Contact:

Re: how to add APSystems ECU-3 solar inverter monitor

Post by Macguyver »

Goodmorning @Firewizard

Yes the sun is up and i have data coming in!
*that being the case with your original script, the edit you wrote makes all data go blank
*no temperature data.

WITH EDITED CODE
Schermafbeelding 2020-03-14 om 09.34.42.png
Schermafbeelding 2020-03-14 om 09.34.42.png (95.17 KiB) Viewed 2591 times
WITH ORIGINAL CODE
Schermafbeelding 2020-03-14 om 09.35.28.png
Schermafbeelding 2020-03-14 om 09.35.28.png (109.22 KiB) Viewed 2591 times
Macguyver
User avatar
FireWizard
Posts: 1745
Joined: Tuesday 25 December 2018 12:11
Target OS: Raspberry Pi / ODroid
Domoticz version: Beta
Location: Voorthuizen (NL)
Contact:

Re: how to add APSystems ECU-3 solar inverter monitor

Post by FireWizard »

Hello,

@Macguyver

It is difficult to make a flow that you can not test.
It has been based on the several screenshots, provided by you.
However they do not match each other.

Therefore,

Can you provide a (new) screenshot from
1. The webpage showing the table, with the individual inverters/solar panels
2. The output of the debug node, marked HTML output, which is attached to the html node, marked "Scrape inverter".
3. Output of debug node, called "Output APS Array" connected to the Function node, called "Create Inverter Array".

The size of that post is quite big, you may put it in a ZIP file.

Best Regards
Macguyver
Posts: 14
Joined: Wednesday 26 February 2020 14:07
Target OS: OS X
Domoticz version: Latest
Location: Zeeland
Contact:

Re: how to add APSystems ECU-3 solar inverter monitor

Post by Macguyver »

@FireWizard

See attached.

gr,
Macguyver
Attachments
Archief.zip
(298.36 KiB) Downloaded 66 times
Macguyver
Posts: 14
Joined: Wednesday 26 February 2020 14:07
Target OS: OS X
Domoticz version: Latest
Location: Zeeland
Contact:

Re: how to add APSystems ECU-3 solar inverter monitor

Post by Macguyver »

@FireWizard

Think i got it... no clue how it works, but looking at the alternative scriptedline you send i started altering the last digit from your scriptline.

Code: Select all

newMsg = {payload: ([InverterIDA.substr(0,12),CurrentPowerA.slice(0,-2),GridVoltageA.slice(0,-2),CurrentPowerB.slice(0,-2),GridVoltageB.slice(0,-2),GridFreqA.slice(0,-3),TempA.slice(0,-3)])}
Changed that digit for TempA.slice(0,-X) to a : -3 and now Temperature is showing.

The error remains though.
Schermafbeelding 2020-03-14 om 13.20.35.png
Schermafbeelding 2020-03-14 om 13.20.35.png (37.58 KiB) Viewed 2587 times
gr,
User avatar
FireWizard
Posts: 1745
Joined: Tuesday 25 December 2018 12:11
Target OS: Raspberry Pi / ODroid
Domoticz version: Beta
Location: Voorthuizen (NL)
Contact:

Re: how to add APSystems ECU-3 solar inverter monitor

Post by FireWizard »

Hello,

@Macguyver

This screenshots helps a lot.
One of your first screenshots, dated "Schermafbeelding 2020-03-12 om 17.32.03.png (46.9 KiB) Viewed 49 times" caused the trouble.
The first one is much better.
I will study it and come back to you.

You also wrote:
Think i got it... no clue how it works, but looking at the alternative scriptedline you send i started altering the last digit from your scriptline.
I will explain:

As an example I will use the temperature.
The variable has got the name TempA (which is equal to TempB) en therefore we will use only one, so TempA.

The output from the HTML node (debug node, "HTML Output") gives for all temperatures the following: " 23 oC"
That is not what I want. I only want the figure " 23" and so I want to get writ off a space (between 3 and o), o and C.
This is totally 3 characters.
Slice does that exactly.
See e.g. https://www.w3schools.com/jsref/jsref_slice_string.asp
In this case TempA.slice (0,-3), chops the last 3 characters of from the right.
So, if TempA is equal to " 23 oC", then TempA.slice(0,-3) will be " 23" and that is what we need
The unit oC is added in Domoticz.

Regards
Post Reply

Who is online

Users browsing this forum: No registered users and 1 guest