MODBUS - How to read multiple coils in a polling

Hi,

I’m new to HomeAssistant and still in the beginning of the learning curve. I have my home fully automatized with a self developed home control and in total roughly 300 switched circuits, some dimmers controlled by DMX 512 and many sensors like all the switches in the house. The automation also runs on my CPU device, so the system is fully working by itself.

Access from the outside is done via MODBUS/TCP via the ODRID HMI IOS app where I’ve designed some panels.

All this works fine, but I want to enhance all it by a modern Web GUI and Smartphone App which is independent from a single source product like ODRID HMI. I already had two previous apps which both have been not maintained at some part, so I want a backup (which can become the primary solution :wink:) That’s where HASS should be used for.

I already have created a first test setup with three coils. It’s working well as expected:

# Example configuration.yaml entry for a TCP connection
modbus:
  name: hcs
  type: tcp
  host: 10.1.1.1
  port: 502

# Testswitche
switch:
  platform: modbus
  scan_interval: 3
  coils:
    - name: DeckeCouch
      hub: hcs
      slave: 1
      coil: 103
    - name: Decke Esstisch
      hub: hcs
      slave: 1
      coil: 104
    - name: Wandlampe Couch
      hub: hcs
      slave: 1
      coil: 105

I’ve then monitored the communication to my HCS CPU device, and that’s the point where I was shocked:

Normally I’d expect that the software would read as many coils as possible in a single command: Up to 255 consecutive coils are supported in the MODBUS read coil command. That’s also how all the iPhone HMI/SCADA apps are working I had running.

But Wireshark showed me that HASS does three MODBUS pollings, getting only one coil per poll. There is a READ COILS command for address 103 and a number of one(!) coil. Then a READ COILS command for address 104, also asking for only one coil, an finally the same for coil 105.

That’s a massive overhead and a complete show stopper! In my final setup there will be around 200 coils which should be polled every 3 seconds - my CPU is an embedded platform and would be fully flooded by that number of requests, which can easily be done with a single polling.

Did I overlook something? How can I tell HASS to poll dozens of coils with a single READ COIL command?

Sorry in case that’s a noob question and I did not find the proper part in the docs or here … any help is highly appreciated.

Marco

Hi there,

I’ve requested an enhancement about it Add Modbus Sensor support for multiple discrete inputs - Feature Requests - Home Assistant Community (home-assistant.io)
I amended it in the senor.py components and I run it custom so far, it works like a charm please see it under modbus/sensor at 293c24a50ffb0d3339a91c01ee3bb87e02328183 · kurkowskim/modbus (github.com).
So you can use it to template your switch reading the state value from the sensor like:

- platform: template
    switches:
      heat_pump_switch:
        value_template: "{{ states.sensor.heat_pump_all_discrete_inputs.state.split(',')[1]|int == 1 }}"
        icon_template: >-
          {% if is_state("switch.heat_pump_switch", "on") %}
            mdi:power
          {% else %}
            mdi:power-off
          {% endif %}
        turn_on:
          service: modbus.write_coil
          data:
            address: 10
            hub: hub1
            unit: 1
            state: true
        turn_off:
          service: modbus.write_coil
          data:
            address: 10
            hub: hub1
            unit: 1
            state: false

Thanks for the hint!
I pretty quick found this project and it runs like a charm with perfect MODBUS accesses: https://github.com/mbs38/spicierModbus2mqtt

1 Like

Thanks a lot! Nevertheless, I use Hassio Supervised version, hence I’d prefer to keep it within Hassio core. So far, I created my custom component named modbus_extended and I added the functionality to read multiple discrete inputs to sensor on my own while waiting for HA enhancement. It works well.

Long term, I can also consider putting separate Rasp unit as a MQQT dispatcher and move all MODBUS devices there, for that your hint is perfect.

Marcin Kurkowski,
Thanks for you info. I will try to implement it as well. Would you please share the source of your custom component named modbus_extended?

hi,

Pleease copy all files from standard modbus components under your custom extended_modbus directory. Sources are here:
core/homeassistant/components/modbus at dev · home-assistant/core · GitHub

then overwrite sensor.py with my code:
modbus/sensor at 293c24a50ffb0d3339a91c01ee3bb87e02328183 · kurkowskim/modbus · GitHub
Also make sure that in your configuration of this sensor you use right platform:

- platform: modbus_extended
    scan_interval: 10
    registers:
    - name: heat_pump_all_discrete_inputs
      hub: hub1
      slave: 100
      register_type: discrete_input
      register: 0
      count: 2
      data_type: custom
      structure: ">2b"

it should work after this action

1 Like

Don’t worry, Odrid HMI is still maintained. The current production version Odrid HMI 1.5.1 was released 2021-02-24 and there has not been any reported problems or crashes with this version. There is also a version that can be installed on Mac, requires macOS 10.15 or later.

I have HA installed at home (running CORE in a docker container) and reading modbus registers (about 20 every 60 seconds) of my Motorhome inverter over LTE. I found that this generate 5GB/day of traffic. Looking as well into to read multiple registers with a single poll…