ESPHome + Pulscounter with IN-Z61 (Gascounter)

I just don’t get any valid pulse counter values and don’t know what I’m doing wrong. Sometimes pulses are counted, but these cannot be valid values.

Is it the GIPO or the pulse counter settings?

 # -------------------------------------
  # GPIO12: gas meter counter...
  # Pulse transmitter Elster IN-Z61
  # -------------------------------------
  - platform: pulse_counter
    pin:
      number: GPIO12
      mode: INPUT_PULLUP
    unit_of_measurement: "m³"
    name: "Gasverbrauch aktuell"
    id: gas_meter
    update_interval: ${update_interval}
    accuracy_decimals: 3
    icon: "mdi:fire"
    state_topic: ${topic_prefix}/gas_current
    filters:
      - multiply: 0.001
    total:
      unit_of_measurement: "m³"
      name: "Gasverbrauch gesamt"
      id: gas_meter_total
      accuracy_decimals: 3
      filters:
        - multiply: 0.001

The IN-Z61 Pulse Transmitter (reed switch) is connected to a Kom Schroder gas diaphragm meter BK-G2.5 and works.

The remaining sensors (water pressure, water temperature) work properly and provide valid data.

If someone has an idea or a tip what I could do, it would help me a lot.
Thanks

2 Likes

Hallo @petsie
Did you have any success with your setup?

I try to use a slightly different using NodeMCU ESP8266 with a IN-Z65 on the BK-G4

Wbr

Yes. but i do use a binary sensor - not the pulse_counter. The pulse_counter do not work for me.

## ################################################################
## ESP32 DEV  - GAS & WASSER 2021 - SENSOREN
## ESP32 NodeMCU Module WLAN WiFi Development Board mit CP2102
##   - GPIO19: Pulscounter Gaszähler
##   - GPIO34: Druck Kaltwasser
##   - GPIO17: Kaltwasser Temperatur
## ################################################################
substitutions:
  platform: ESP32
  board: esp32dev
  device_name_short: "wasserundgas" # used by esp-home config
  friendly_name: "WUG"
  device_description: "Gaszähler, Kaltwassertemperatur, Kaltwasserdruck"
  update_interval: 60s
  impulsfactor: "0.100"
  appversion: "1.1.4"
  ## all used pins on ESP32
  gipo_pressure_SEN0257: GPIO34   # COLD WATER PRESSURE SENSOR
  gipo_dallas_sensor: GPIO17      # COLD WATER SENSOR
  gipo_puse_counter: GPIO19       # GASCOUNTER ZI-61 REED CONTACT
  


esphome:
  name: ${device_name_short}
  comment: ${device_description}
  platform: ${platform}
  board: ${board}
  arduino_version: recommended
  project:
    name: "OE9psj.esp32WUG"
    version: ${appversion}
  on_boot:
    then:
      - logger.log:
          level: info
          format: "BOOTMESSAGE:${device_name_short} API is connected, Device ready!"
      - globals.set:
          id: boot_counter
          value: !lambda "return id(boot_counter)+=1;"
  on_shutdown:
    then:
      - logger.log: ${device_name_short} is down!


# ----------------------------------------------------------------
# Global variables
# ----------------------------------------------------------------
globals:
  - id: z61count
    type: int
    restore_value: yes
    initial_value: "0"
  - id: z61counter
    type: float
    restore_value: yes
    initial_value: "0.0"
  - id: m3kw
    type: float
    restore_value: yes
    initial_value: "10.94"
  - id: gas_meter_displayvalue
    type: float
    restore_value: yes
    initial_value: "29126.2"
  - id: gas_meter_totalm3
    type: float
    restore_value: yes
    initial_value: "0.0"
  - id: gas_meter_displayinital
    type: float
    restore_value: yes
    initial_value: "29060.6"

# ---------------------------------------
# Base packages wifi, timeserver...
# ---------------------------------------
packages:
  base: !include common/base.yaml

# ----------------------------------------------------------------
# Native API Component
# ----------------------------------------------------------------
api:
  id: espapi
  port: 6053
  reboot_timeout: 5min
  services:
    - service: set_gasmeterdisplay
      variables:
        my_newdisplayvalue: float
      then:
        - logger.log:
            format: "Setting Gasmeter Display value: %.1f"
            args: [my_newdisplayvalue]
        - globals.set:
            id: gas_meter_displayvalue
            value: !lambda 'return (my_newdisplayvalue);'
        - globals.set:
            id: z61counter
            value: !lambda 'return (my_newdisplayvalue);'
        - globals.set:
            id: gas_meter_totalm3
            value: !lambda 'return ((my_newdisplayvalue) - id(gas_meter_displayinital));'
        - globals.set:
            id: z61count
            value: !lambda 'return ( ((my_newdisplayvalue) - id(gas_meter_displayinital))/${impulsfactor} );'
        - logger.log:
            format: "Gasmeter Display value: %.1f"
            args: [id(gas_meter_displayvalue)]

# ----------------------------------------------------------------
# GPIO02: used for temperatur sensors data wired
# ----------------------------------------------------------------
dallas:
  pin: ${gipo_dallas_sensor}
  update_interval: ${update_interval}

# ----------------------------------------------------------------
# Switch to restart, reset all, reset bootcounter
# ----------------------------------------------------------------
switch:
  - platform: restart
    name: ${friendly_name} restart
  - platform: template
    name: ${friendly_name} reset all
    turn_on_action:
      then:
        - lambda: |-
            id(boot_counter) = 0;
            id(z61counter) = 0.0;
            id(z61count) = 0;
            id(gas_meter_totalm3)= 0.0;
            id(gas_meter_displayvalue)= 0.0;
            id(daily_value)= 0.0;
            id(bootcounter).update();
            id(gas_meter_display).update();
            id(gas_meter_total_m3).update();
            id(gas_meter_total_kw).update();
            id(gas_meter_total_kw_day).update();
        - logger.log: ${device_name_short} all values reset!

# ----------------------------------------------------------------
# GASCOUNTER ZI-61 REED CONTACT
# GPIO19 <-- o-RC-o <--- GND
#            o-10k ----> +5V
# +++++++++++++++++++++++++++++++
# Gasmeter: Krom Schröder BK-G,25
# ++++++++++++++++++++++++++++++++
# Q_max: 4 m³/h
# Q_min: 0.025 m³/h
# V: 1.2 dm³
# p_max: 0.5 bar
# 1 imp = 0.1 m³
# ----------------------------------------------------------------
binary_sensor:
  - platform: gpio
    pin:
      number: GPIO19
      mode: INPUT_PULLUP  ## set ESP32 pin to input pull-up mode
      inverted: false
    name: ${friendly_name} Gaszähler Z-61 Impuls
    id: gassensor_state
    device_class: window
    filters:
      - delayed_off: 10ms
    ## This automation will be triggered when a button press ends,
    ## or in other words on the falling edge of the signal.
    on_release:
      then:
        - lambda: |-
            ESP_LOGI("main", " -------  Z-61 SET NEW VALUES !!!!!");
            id(z61count) += 1;
            id(z61counter) += ${impulsfactor};
            id(gas_meter_displayvalue) += ${impulsfactor};
            id(gas_meter_totalm3) += ${impulsfactor};
            id(daily_value) += ${impulsfactor};
            id(gas_meter_display).update();
            id(gas_meter_total_m3).update();
            id(gas_meter_total_kw).update();
            id(gas_meter_total_kw_day).update();
            id(gas_meter_m3_today).publish_state(${impulsfactor});

# ----------------------------------------------------------------
# ALL SENSORS
# ----------------------------------------------------------------
sensor:
  - platform: template
    name: ${friendly_name} Gaszähler Anzeige
    id: gas_meter_display
    accuracy_decimals: 1
    unit_of_measurement: "m³"
    icon: "mdi:counter"
    device_class: gas
    lambda: |-
      return id(gas_meter_displayvalue);

  - platform: template
    name: ${friendly_name} Gaszähler aktuell
    id: gas_meter_m3_today
    state_class: measurement
    device_class: gas
    unit_of_measurement: "m³"
    accuracy_decimals: 2

  - platform: template
    name: ${friendly_name} Gaszähler Impulse
    id: gas_meter_impulse_count
    state_class: measurement
    accuracy_decimals: 0
    lambda: |-
      return (id(z61count));

  - platform: template
    name: ${friendly_name} Gasverbrauch gesamt
    id: gas_meter_total_m3
    accuracy_decimals: 1
    unit_of_measurement: "m³"
    device_class: gas
    state_class: total_increasing
    lambda: |-
      return id(gas_meter_totalm3);

  - platform: template
    name: ${friendly_name} Gasverbrauch heute
    id: gas_meter_total_m3_day
    unit_of_measurement: "m³"
    state_class: total_increasing
    accuracy_decimals: 1
    icon: mdi:gauge
    lambda: |-
      return (id(daily_value));

  - platform: template
    name: ${friendly_name} Kilowattstunde Gas gesamt
    id: gas_meter_total_kw
    accuracy_decimals: 2
    device_class: power
    state_class: total_increasing
    unit_of_measurement: "kW"
    lambda: |-
      return (id(gas_meter_totalm3) * id(m3kw));

  - platform: template
    name: ${friendly_name} Kilowattstunde Gas heute
    id: gas_meter_total_kw_day
    unit_of_measurement: "kW"
    state_class: total_increasing
    device_class: gas
    accuracy_decimals: 2
    lambda: |-
      return (id(daily_value) * id(m3kw));

  # -----------------------------------------------------
  # DFRobot SEN0257 water pressure sensor 1 GPIO 34
  # -----------------------------------------------------
  - platform: adc
    name: ${friendly_name} Kaltwasser Wasserdruck
    pin: ${gipo_pressure_SEN0257}
    id: coldwater_pressure
    update_interval: 10s
    unit_of_measurement: "bar"
    accuracy_decimals: 2
    device_class: pressure
    state_class: measurement
    attenuation: 11db
    filters:
      - lambda: |-
          ESP_LOGI("main", "adc volt: %f", id(coldwater_pressure).raw_state);
          if(x-0.41<0) return 0.00;
          return ((x) * 2.00) - 0.82;

  # ------------------------------------------------------------------------------
  # PIN GIPO17: DS18B20 Digital temperature sensor 1
  # Unique ID: 'dallas-7900000C8579C728'
  # ------------------------------------------------------------------------------
  - platform: dallas
    # index: 0
    address: 0x7900000C8579C728
    accuracy_decimals: 2
    unit_of_measurement: "°C"
    name: ${friendly_name} Kaltwasser Temperatur
    id: coldwater_temperature
    device_class: temperature
    state_class: measurement
    icon: mdi:thermometer-lines

logger:
  level: INFO
  # baud_rate: 9600
  # baud_rate: 0

Hi petsie,

I’m trying to achieve something similar: I bought an ELV ES-GAS-2 module for my ELSTER gas meter. I don’t have proper results with pulse_counter either and stumbled across your post.

I think your setup is very “creative” (= advanced) - I did not know you could do this sort of thing with ESPHOME. I’m trying to adapt your code, but it seems there is something missing, e.g. variables

boot_counter,
daily_value,
bootcounter

are those defined in common/base.yaml ? Would you make that file available, too?

Thanks in advance,

@socrates

You can try this:

@petsie - Perfect, thank you!

Hi @petsie,

if you don’t mind my asking, I have two more questions:

  1. I discovered, that you have implemented a service in ESPHome to “reset” the Displayvalue and re-calculating related values. Under which circumstances do you use this? Currently I have a delta of about 0.5 to 0.9 m3 per day between the calculated value and the value displayed on the gas meter. Do you have a similar experience or do those values match in your setup?

  2. I couldn’t figure out how the daily values are reset. There seems to be nothing in the ESPHome .yaml file capable of reseting the values and I don’t see a corresponding service from HomeAssistant (like for the display value adjustment.)

Thanks in advance!

Hi,

I couldn’t figure out how the daily values are reset.

See: base.yaml → SNTP Time server

time:
  - platform: sntp
    id: sntp_time
    timezone: Europe/Berlin
    servers:
      - 0.at.pool.ntp.org
      - 0.pool.ntp.org
      - 1.pool.ntp.org
    on_time:
      - seconds: 0
        minutes: 0
        hours: 0
        then:
          - lambda: |-
              if(id(daily_value)){
                 id(daily_value)=0.00;
              }
      - seconds: 0
        minutes: 0
        then:
          - lambda: |-
              if(id(hour_value)){
                 id(hour_value)=0.00;
              }
    on_time_sync:
      then:
        - logger.log: "Synchronized sntp clock"

I discovered, that you have implemented a service in ESPHome to “reset” the Displayvalue and…

Do you have a similar experience or do those values match in your setup?

Negativ, i use only “reset” the Displayvalue when I have the device offline or use a new one.
I would check filters: - delayed_off: 10ms, maybe this is too short?

Oh dear … THERE I did not look :upside_down_face:

I will have a look at the filter section – thanks a lot!

You can also enable the logger:

and be shure that you use a pulldown resistor.
Another could be the power supply, there are some that cause interference.

I changed to binary_sensor as well. The pulses where count in HA using history_stats.
From that I use template sensor to calculate gas consumption in m³. This sensor I add to the energy dashboard.
Works good for now

cheers

- platform: history_stats
  name: GasVerbrauchPulser
  entity_id: binary_sensor.gasverbrauch_pulser
  state: "on"
  type: count
  start: "{{ now().replace(hour=0, minute=0, second=0) }}"
  end: "{{ now() }}"
template:
  - sensor:
      - name: "gasverbrauchaktuell_m3"
        unit_of_measurement: "m³"
        state: "{{ states('sensor.GasVerbrauchPulser')|float(0) * 0.01 }}"
        device_class: gas
        state_class: total_increasing

Are you shure ?

Bildschirmfoto 2022-03-03 um 07.47.10

I use:

{{ states('sensor.GasVerbrauchPulser')|float(0) * 0.1 }}

I have an BK-G4M and for me 1 imp is 0.01m3.
It looks like the counters are different.

Yes, they are different, my BK-G4 has

1 imp ≙ 0.01m³

I would like to use this, too. I also use an ESP32 but with the IN-Z65. I would like to know how to install this in Home Assistant? Or do i just have to copy the files and folders to the /config/esphome-directory?

My current code works, but the recorded values and the real value on the meter are more and more different while it records.

This is my current Yaml-Code in ESPhome:

esphome:
  name: gassensor

esp32:
  board: esp32dev
  framework:
    type: arduino

# Enable logging
logger:

# Enable Home Assistant API
api:

ota:
  password: "<OTA_password>"

wifi:
  ssid: !secret wifi_ssid
  password: !secret wifi_password

  # Enable fallback hotspot (captive portal) in case wifi connection fails
  ap:
    ssid: "Gassensor Fallback Hotspot"
    password: "<Fallback_Password>"

captive_portal:

sensor:  
  - platform: pulse_counter
    pin:
      number: GPIO19
      mode: INPUT_PULLDOWN
      inverted: false
    name: "Gasverbrauch"
    update_interval : 15s
    filters:
      - lambda: |-
          static float total_value = 6258.56;
          total_value += x * 0.01;
          return total_value;
    unit_of_measurement: m³
    state_class: total_increasing
    device_class: gas
    accuracy_decimals: 2
    icon: 'mdi:fire'

Wirering:
ESP32 → GPIO19 → IN-Z65 → GND → ESP32
i do not use an hardware-resistor, cause i read that the ESP32 has build-in resistors…right?

This is my first experience with ESPhome and any help would be appreciated. Thank you.

I had no success with the pulse_counter, so use the binary sensor.

See: ESPHome - Home Assistant
Go to integration and add ESPHome

Bildschirmfoto 2022-03-10 um 19.18.56

Bildschirmfoto 2022-03-10 um 19.19.04

Thank you for your answer. i had installed esphome via settings > esphome. it is up and running and i was able to flash my esp32 with the yaml-code i posted.

My Question was how i could install this for my sensor?

Just copy the files and folders to the /config/esphome-directory…

/config/esphome
|-- _static
|   |-- webserver-v1.min.css
|   `-- webserver-v1.min.js
|-- common
|   |-- base.yaml
|   |-- base_global.yaml
|   |-- base_webserver.yaml
|   `-- secrets.yaml
`-- gasmeter.yaml

starte esp-home dashboard

esphome-dashboard=‘cd ~/ && esphome dashboard ./’

Compile and install the app to the ESP

i will try it and give feedback if it works. Thank you so much!

i have an Gasmeter with imp = 0.01 m³ so i will have to change this

substitutions:
  platform: ESP32
  board: esp32dev
  device_name_short: "gasmeter" # used by esp-home config
  friendly_name: "GM2021"
  device_description: "Gasmeter"
  update_interval: 60s
  impulsfactor: "0.100"
  appversion: "1.1.7"

to this

substitutions:
  platform: ESP32
  board: esp32dev
  device_name_short: "gasmeter" # used by esp-home config
  friendly_name: "GM2021"
  device_description: "Gasmeter"
  update_interval: 60s
  impulsfactor: "0.010"
  appversion: "1.1.7"

right?