New ESP32 energy monitoring component

Hello, I made an esphome component for ESP32 to measure electric power through ADC.
It is inspired to the good old Emonlib, which is found in almost all DIY energy monitors.
I kept the power estimation algorithm, but I cut some rough edges, making it sleeker and easier to configure.

Technical details

This component leverages DMA on the ADC peripheral in ESP32 chips. This allows for a much higher sample rate (20kHz), which in turn leads to almost perfectly synchronized samples, thus releasing the need for a phase calibration parameter (_PHASECAL in Emonlib) and making the result in theory more precise (I have not tested its precision, since I do not own precise measurement equipment).
On the other side it requires esp-idf v5.x or newer, which is at the moment not officially supported by the ESPHome project. It apparently works, but still could break something.

It is now in a beta state. There are some open points. Any feedback, help, feature request, performance benchmark or code contribution is highly appreciated.
Here is a sample configuration if you want to give it a try:

...

esp32:
  board: esp32dev
  framework:
    type: esp-idf
    platform_version: https://github.com/platformio/platform-espressif32.git
    version: 5.2.1

external_components:
  - source: github://Petapton/esphome@emon
    components: [ emon ]

sensor:
  - platform: emon
    v_input:
      pin: GPIO34
      attenuation: 2.5dB
      cal: 2.121e-1
    i_input:
      pin: GPIO35
      attenuation: 2.5dB
      cal: 2.8798e-2
    data_interval: 1s
    voltage:
      name: "Emon P1 Voltage"
    current:
      name: "Emon P1 Current"
    active_power:
      name: "Emon P1 Active Power"
    apparent_power:
      name: "Emon P1 Apparent Power"
    power_factor:
      name: "Emon P1 Power Factor"

button:
  # Reboot in safe mode before OTA updates
  - platform: safe_mode
    name: "Safe Mode"

...

Known issues

  • OTA update does not work unless booted in safe mode. This is most likely due to the fact that the ADC peripheral generates frequent interrupts, making the OTA process time out.

Hardware wise, is this only for Emon?

I’m sorry, I think I don’t understand your question.
You can hook it up to virtually any AC voltage-current signal pair and it will spit out power readings. Of course you will need extra circuitry to avoid frying your esp.
If you are interested in building custom hardware, please see the electricity monitoring guide by Openenergymonitor.

I mean, what kind of input your component is expecting? Let’s say if I have some voltage sensor and current transformer… I’m not interested in Emon hardware.

Yep, exactly that. A voltage transformer and a CT clamp.
As long as your signal stays in the ADC boundaries, you are good to go.

Sorry my stupid question, I didn’t notice that arrow to open “Technical details”.

1 Like

I happen to be in possession of a 4 channel PCB, so is it possible to use one channel for the voltage and the other 3 to report 3 different devices?

I think this is not supported at the moment, but should definitely be available in some later iteration. Nevertheless you could try setting up more than one entry in the yaml file and see if it works.
I expect it not to work. In such case, would you mind sending logs?
Thank you.

1 Like

This is very much an “on the bench” project at the moment, it’s kind of ready to go but there’s too many other plates that need attention. I’ll report back…

1 Like

@Petapton Not had a great deal of time to spend on this, but today I started!

Created simple ESPHome entry, successfully compiled and loaded, but it doesn’t run successfully, here’s an extract from the log, there’s more repeated.

[10:51:21]
[10:51:21]assert failed: dma_chan_free spi_common.c:353 (spi_dma_chan_enabled & BIT(dma_chan))
[10:51:21]
[10:51:21]
[10:51:21]Backtrace: 0x400261e6:0x3ffd77d0 0x4002c461:0x3ffd77f0 0x40032e99:0x3ffd7810 0x400fc835:0x3ffd7930 0x400fcbb7:0x3ffd7950 0x4009ce85:0x3ffd7970 0x4009cfc3:0x3ffd79a0 0x4008851c:0x3ffd7a00 0x40111979:0x3ffd7a50 0x40111a13:0x3ffd7a70 0x40090705:0x3ffd7a90 0x400928c2:0x3ffd7ad0 0x40088af3:0x3ffd7bb0
[10:51:21]
[10:51:21]
[10:51:21]
[10:51:21]
[10:51:21]ELF file SHA256: 3d5680d72
[10:51:21]
[10:51:21]Rebooting...
[10:51:21]I (30) boot: ESP-IDF 5.2.1 2nd stage bootloader
[10:51:21]I (30) boot: compile time Jul 31 2024 10:29:52
[10:51:21]I (30) boot: chip revision: v0.0
[10:51:21]I (30) boot.esp32s2: SPI Speed      : 80MHz
[10:51:21]I (30) boot.esp32s2: SPI Mode       : DIO
[10:51:21]I (30) boot.esp32s2: SPI Flash Size : 4MB
[10:51:21]I (30) boot: Enabling RNG early entropy source...
[10:51:21]I (31) boot: Partition Table:
[10:51:21]I (31) boot: ## Label            Usage          Type ST Offset   Length
[10:51:21]I (32) boot:  0 otadata          OTA data         01 00 00009000 00002000
[10:51:21]I (33) boot:  1 phy_init         RF data          01 01 0000b000 00001000
[10:51:21]I (34) boot:  2 app0             OTA app          00 10 00010000 001c0000
[10:51:21]I (35) boot:  3 app1             OTA app          00 11 001d0000 001c0000
[10:51:21]I (36) boot:  4 nvs              WiFi data        01 02 00390000 0006d000
[10:51:21]I (38) boot: End of partition table
[10:51:21]I (38) esp_image: segment 0: paddr=00010020 vaddr=3f000020 size=300c8h (196808) map
[10:51:21]I (78) esp_image: segment 1: paddr=000400f0 vaddr=3ffc81b0 size=034ach ( 13484) load
[10:51:21]I (81) esp_image: segment 2: paddr=000435a4 vaddr=40024000 size=0ca74h ( 51828) load
[10:51:21]I (94) esp_image: segment 3: paddr=00050020 vaddr=40080020 size=9b44ch (635980) map
[10:51:21]I (221) esp_image: segment 4: paddr=000eb474 vaddr=40030a74 size=07734h ( 30516) load
[10:51:21]I (240) boot: Loaded app from partition at offset 0x10000
[10:51:21]I (241) boot: Disabling RNG early entropy source...
[10:51:21]I (290) main_task: Started on CPU0
[10:51:21]I (290) main_task: Calling app_main()
[10:51:21][I][logger:156]: Log initialized
[10:51:21][D][esp-idf:000][main]: I (368) main_task: Returned from app_main()
[10:51:21]
[10:51:21][C][safe_mode:079]: There have been 8 suspected unsuccessful boot attempts
[10:51:21][D][esp32.preferences:114]: Saving 1 preferences to flash...
[10:51:21][D][esp32.preferences:142]: Saving 1 preferences to flash: 0 cached, 1 written, 0 failed
[10:51:21][I][app:029]: Running through setup()...
[10:51:21][C][wifi:047]: Setting up WiFi...
[10:51:21][D][esp-idf:000]: I (381) wifi:
[10:51:21][D][esp-idf:000]: wifi driver task: 3fff0c40, prio:23, stack:6656, core=0
[10:51:21][D][esp-idf:000]: 
[10:51:21]
[10:51:21][D][esp-idf:000][wifi]: I (386) wifi:
[10:51:21][D][esp-idf:000][wifi]: wifi firmware version: a9f5b59
[10:51:21][D][esp-idf:000][wifi]: 
[10:51:21]
[10:51:21][D][esp-idf:000][wifi]: I (389) wifi:
[10:51:21][D][esp-idf:000][wifi]: wifi certification version: v7.0
[10:51:21][D][esp-idf:000][wifi]: 
[10:51:21]
[10:51:21][D][esp-idf:000][wifi]: I (391) wifi:
[10:51:21][D][esp-idf:000][wifi]: config NVS flash: enabled
[10:51:21][D][esp-idf:000][wifi]: 
[10:51:21]
[10:51:21][D][esp-idf:000][wifi]: I (393) wifi:
[10:51:22][D][esp-idf:000][wifi]: config nano formating: disabled
[10:51:22][D][esp-idf:000][wifi]: 
[10:51:22]
[10:51:22][D][esp-idf:000][wifi]: I (395) wifi:
[10:51:22][D][esp-idf:000][wifi]: Init data frame dynamic rx buffer num: 32
[10:51:22][D][esp-idf:000][wifi]: 
[10:51:22]
[10:51:22][D][esp-idf:000][wifi]: I (397) wifi:
[10:51:22][D][esp-idf:000][wifi]: Init static rx mgmt buffer num: 5
[10:51:22][D][esp-idf:000][wifi]: 
[10:51:22]
[10:51:22][D][esp-idf:000][wifi]: I (399) wifi:
[10:51:22][D][esp-idf:000][wifi]: Init management short buffer num: 32
[10:51:22][D][esp-idf:000][wifi]: 
[10:51:22]
[10:51:22][D][esp-idf:000][wifi]: I (401) wifi:
[10:51:22][D][esp-idf:000][wifi]: Init dynamic tx buffer num: 32
[10:51:22][D][esp-idf:000][wifi]: 
[10:51:22]
[10:51:22][D][esp-idf:000][wifi]: I (403) wifi:
[10:51:22][D][esp-idf:000][wifi]: Init static rx buffer size: 1600
[10:51:22][D][esp-idf:000][wifi]: 
[10:51:22]
[10:51:22][D][esp-idf:000][wifi]: I (405) wifi:
[10:51:22][D][esp-idf:000][wifi]: Init static rx buffer num: 10
[10:51:22][D][esp-idf:000][wifi]: 
[10:51:22]
[10:51:22][D][esp-idf:000][wifi]: I (407) wifi:
[10:51:22][D][esp-idf:000][wifi]: Init dynamic rx buffer num: 32
[10:51:22][D][esp-idf:000][wifi]: 
[10:51:22]
[10:51:22][D][esp-idf:000]: I (409) wifi_init: rx ba win: 6
[10:51:22]
[10:51:22][D][esp-idf:000]: I (412) wifi_init: tcpip mbox: 32
[10:51:22]
[10:51:22][D][esp-idf:000]: I (414) wifi_init: udp mbox: 6
[10:51:22]
[10:51:22][D][esp-idf:000]: I (416) wifi_init: tcp mbox: 6
[10:51:22]
[10:51:22][D][esp-idf:000]: I (418) wifi_init: tcp tx win: 5760
[10:51:22]
[10:51:22][D][esp-idf:000]: I (420) wifi_init: tcp rx win: 5760
[10:51:22]
[10:51:22][D][esp-idf:000]: I (422) wifi_init: tcp mss: 1440
[10:51:22]
[10:51:22][D][esp-idf:000]: I (424) wifi_init: WiFi IRAM OP enabled
[10:51:22]
[10:51:22][D][esp-idf:000]: I (426) wifi_init: WiFi RX IRAM OP enabled
[10:51:22]
[10:51:22][C][wifi:060]: Starting WiFi...
[10:51:22][C][wifi:061]:   Local MAC: 84:F7:03:EA:F2:4E
[10:51:22][D][esp-idf:000][wifi]: I (429) phy_init: phy_version 2401,2a6dc26,Sep 26 2023,11:22:15
[10:51:22]
[10:51:22][D][esp-idf:000][wifi]: I (470) wifi:
[10:51:22][D][esp-idf:000][wifi]: mode : sta (84:f7:03:ea:f2:4e)
[10:51:22][D][esp-idf:000][wifi]: 
[10:51:22]
[10:51:22][D][esp-idf:000][wifi]: I (473) wifi:
[10:51:22][D][esp-idf:000][wifi]: enable tsf
[10:51:22][D][esp-idf:000][wifi]: 
[10:51:22]
[10:51:22][D][esp-idf:000][wifi]: I (477) wifi:
[10:51:22][D][esp-idf:000][wifi]: Set ps type: 0, coexist: 0
[10:51:22]
[10:51:22][D][esp-idf:000][wifi]: 
[10:51:22]
[10:51:22][D][wifi:481]: Starting scan...
[10:51:22][D][sensor:093]: 'Device Uptime': Sending state 0.01117 hours with 2 decimals of accuracy
[10:51:22][D][esp-idf:000][wifi]: I (485) wifi:
[10:51:22][D][esp-idf:000][wifi]: Set ps type: 0, coexist: 0
[10:51:22]
[10:51:22][D][esp-idf:000][wifi]: 
[10:51:22]
[10:51:22][W][component:157]: Component wifi set Warning flag: scanning for networks
[10:51:25][D][wifi:496]: Found networks:
[10:51:25][I][wifi:539]: - 'dandelion' [redacted]▂▄▆█
[10:51:25][D][wifi:541]:     Channel: 11
[10:51:25][D][wifi:542]:     RSSI: -52 dB
[10:51:25][I][wifi:539]: - 'dandelion' [redacted]▂▄▆█
[10:51:25][D][wifi:541]:     Channel: 11
[10:51:25][D][wifi:542]:     RSSI: -57 dB
[10:51:25][I][wifi:539]: - 'dandelion' [redacted]▂▄▆█
[10:51:25][D][wifi:541]:     Channel: 1
[10:51:25][D][wifi:542]:     RSSI: -80 dB
[10:51:25][D][wifi:544]: - [redacted] [redacted]▂▄▆█
[10:51:25][D][wifi:544]: - [redacted] [redacted]▂▄▆█
[10:51:25][D][wifi:544]: - [redacted] [redacted]▂▄▆█
[10:51:25][D][wifi:544]: - [redacted] [redacted]▂▄▆█
[10:51:25][D][wifi:544]: - [redacted] [redacted]▂▄▆█
[10:51:25][D][wifi:544]: - [redacted] [redacted]▂▄▆█
[10:51:25][D][wifi:544]: - [redacted] [redacted]▂▄▆█
[10:51:25][D][wifi:544]: - [redacted] [redacted]▂▄▆█
[10:51:25][D][wifi:544]: - [redacted] [redacted]▂▄▆█
[10:51:25][D][wifi:544]: - [redacted] [redacted]▂▄▆█
[10:51:25][D][wifi:544]: - [redacted] [redacted]▂▄▆█
[10:51:25][D][wifi:544]: - [redacted] [redacted]▂▄▆█
[10:51:25][D][wifi:544]: - [redacted] [redacted]▂▄▆█
[10:51:25][D][wifi:544]: - [redacted] [redacted]▂▄▆█
[10:51:25][D][wifi:544]: - [redacted] [redacted]▂▄▆█
[10:51:25][D][wifi:544]: - [redacted] [redacted]▂▄▆█
[10:51:25][D][wifi:544]: - [redacted] [redacted]▂▄▆█
[10:51:25][D][wifi:544]: - [redacted] [redacted]▂▄▆█
[10:51:25][D][wifi:544]: - [redacted] [redacted]▂▄▆█
[10:51:25][D][wifi:544]: - [redacted] [redacted]▂▄▆█
[10:51:25][D][wifi:544]: - [redacted] [redacted]▂▄▆█
[10:51:25][D][wifi:544]: - [redacted] [redacted]▂▄▆█
[10:51:25][D][wifi:544]: - [redacted] [redacted]▂▄▆█
[10:51:25][D][wifi:544]: - [redacted] [redacted]▂▄▆█
[10:51:25][D][wifi:544]: - [redacted] [redacted]▂▄▆█
[10:51:25][D][wifi:544]: - [redacted] [redacted]▂▄▆█
[10:51:25][D][wifi:544]: - [redacted] [redacted]▂▄▆█
[10:51:25][I][wifi:312]: WiFi Connecting to 'dandelion'...
[10:51:25][D][esp-idf:000][wifi]: I (3732) wifi:
[10:51:25][D][esp-idf:000][wifi]: new:<11,0>, old:<1,0>, ap:<255,255>, sta:<11,0>, prof:1
[10:51:25][D][esp-idf:000][wifi]: 
[10:51:25]
[10:51:25][D][esp-idf:000][wifi]: I (4281) wifi:
[10:51:25][D][esp-idf:000][wifi]: state: init -> auth (b0)
[10:51:25][D][esp-idf:000][wifi]: 
[10:51:25]
[10:51:25][D][esp-idf:000][wifi]: I (4289) wifi:
[10:51:25][D][esp-idf:000][wifi]: state: auth -> assoc (0)
[10:51:25][D][esp-idf:000][wifi]: 
[10:51:25]
[10:51:25][D][esp-idf:000][wifi]: I (4360) wifi:
[10:51:25][D][esp-idf:000][wifi]: state: assoc -> run (10)
[10:51:25][D][esp-idf:000][wifi]: 
[10:51:25]
[10:51:25][D][esp-idf:000][wifi]: I (4378) wifi:
[10:51:25][D][esp-idf:000][wifi]: connected with dandelion, aid = 10, channel 11, BW20, bssid = d2:21:f9:a2:56:9a
[10:51:25][D][esp-idf:000][wifi]: 
[10:51:25]
[10:51:25][D][esp-idf:000][wifi]: I (4382) wifi:
[10:51:25][D][esp-idf:000][wifi]: security: WPA2-PSK, phy: bgn, rssi: -53
[10:51:25][D][esp-idf:000][wifi]: 
[10:51:25]
[10:51:25][D][esp-idf:000][wifi]: I (4385) wifi:
[10:51:26][D][esp-idf:000][wifi]: pm start, type: 0
[10:51:26]
[10:51:26][D][esp-idf:000][wifi]: 
[10:51:26]
[10:51:26][D][esp-idf:000][wifi]: I (4388) wifi:
[10:51:26][D][esp-idf:000][wifi]: dp: 1, bi: 102400, li: 3, scale listen interval from 307200 us to 307200 us
[10:51:26][D][esp-idf:000][wifi]: 
[10:51:26]
[10:51:26][D][esp-idf:000][wifi]: I (4391) wifi:
[10:51:26][D][esp-idf:000][wifi]: AP's beacon interval = 102400 us, DTIM period = 1
[10:51:26][D][esp-idf:000][wifi]: 
[10:51:26]
[10:51:26][D][esp-idf:000][wifi]: I (4407) wifi:
[10:51:26][D][esp-idf:000][wifi]: <ba-add>idx:0 (ifx:0, d2:21:f9:a2:56:9a), tid:6, ssn:15, winSize:64
[10:51:26][D][esp-idf:000][wifi]: 
[10:51:26]
[10:51:26][D][esp-idf:000][sys_evt]: I (5397) esp_netif_handlers: sta ip: 192.168.20.166, mask: 255.255.255.0, gw: 192.168.20.1
[10:51:26]
[10:51:26][C][wifi:427]:   Local MAC: 84:F7:03:EA:F2:4E
[10:51:26][C][wifi:432]:   SSID: [redacted]
[10:51:26][C][wifi:435]:   IP Address: 192.168.20.166
[10:51:26][C][wifi:438]:   BSSID: [redacted]
[10:51:26][C][wifi:440]:   Hostname: 'current-monitor'
[10:51:26][C][wifi:442]:   Signal strength: -53 dB ▂▄▆█
[10:51:26][C][wifi:446]:   Channel: 11
[10:51:26][C][wifi:447]:   Subnet: 255.255.255.0
[10:51:26][C][wifi:448]:   Gateway: 192.168.20.1
[10:51:26][C][wifi:449]:   DNS1: 1.1.1.1
[10:51:27][C][wifi:450]:   DNS2: 8.8.8.8
[10:51:27][D][wifi:625]: Disabling AP...
[10:51:27][C][api:025]: Setting up Home Assistant API server...
[10:51:27]
[10:51:27]assert failed: dma_chan_free spi_common.c:353 (spi_dma_chan_enabled & BIT(dma_chan))
[10:51:27]
[10:51:27]
[10:51:27]Backtrace: 0x400261e6:0x3ffd77d0 0x4002c461:0x3ffd77f0 0x40032e99:0x3ffd7810 0x400fc835:0x3ffd7930 0x400fcbb7:0x3ffd7950 0x4009ce85:0x3ffd7970 0x4009cfc3:0x3ffd79a0 0x4008851c:0x3ffd7a00 0x40111979:0x3ffd7a50 0x40111a13:0x3ffd7a70 0x40090705:0x3ffd7a90 0x400928c2:0x3ffd7ad0 0x40088af3:0x3ffd7bb0
[10:51:

First pass at YAML

#####################################################
# 
# https://community.home-assistant.io/t/new-esp32-energy-monitoring-component/733269
#
#####################################################

# Device Types
#  SCT013
#   10A, 20A, 30A, 50A, 60A, 100A == 1V
#  100A == 50mA

substitutions:
  name: "current-monitor"
  friendly_name: "Current Monitor"
  ssid: "Current Monitor"
  board: lolin_s2_mini
  main_icon: "power-socket-uk"
  default_state: "RESTORE_DEFAULT_OFF"
  network_LED: GPIO18 # On the PCB
  s2_onboard_button: GPIO00 # On the Lolin S2
  s2_onboard_led: GPIO15 # On the Lolin S2
  channel_1_pin: GPIO01
  channel_1_name: Voltage
  channel_1_type: 10A
  channel_1_threshold: "2"
  channel_2_pin: GPIO02
  channel_2_name: Shower
  channel_2_type: 10A
  channel_2_threshold: "2"
  channel_3_pin: GPIO03
  channel_3_name: Cooker
  channel_3_type: 30A
  channel_3_threshold: "2"
  channel_4_pin: GPIO04
  channel_4_name: Device 4
  channel_4_type: 30A
  channel_4_threshold: "2"
  sample_duration: 500ms # 200ms == 10 cycles
  update_interval: 1000ms
#  update_time: 1s
  decimal_places: "5"

globals:
  - id: initialisation_complete #setupComplete
    type: bool
    restore_value: no
    initial_value: "false"

esphome:
  name: ${name}
  friendly_name: ${friendly_name}

esp32:
  board: ${board}
  framework:
    type: esp-idf
    platform_version: https://github.com/platformio/platform-espressif32.git
    version: 5.2.1

external_components:
  - source: github://Petapton/esphome@emon
    components: [ emon ]

# Enable logging
logger:
  level: DEBUG

# Lolin ESP32 S2 requires WiFi power save mode off
# https://forum.level1techs.com/t/esp32-s2-wemos-based-4-port-power-monitor-open-source-shenanigans/209173
wifi:
  power_save_mode: none

packages:
  common: !include common/common.yaml
  api:    !include common/api.yaml
  ota:    !include common/ota.yaml
  wifi:   !include common/wifi.yaml

time:
  - platform: homeassistant
    id: homeassistant_time

captive_portal:

#################################
sensor:
  - platform: emon
    v_input:
      pin: ${channel_1_pin}
      attenuation: 2.5dB
      cal: 2.121e-1
    i_input:
      pin: ${channel_2_pin}
      attenuation: 2.5dB
      cal: 2.8798e-2
    data_interval: 1s
    voltage:
      name: "Emon P1 Voltage"
    current:
      name: "Emon P1 Current"
    active_power:
      name: "Emon P1 Active Power"
    apparent_power:
      name: "Emon P1 Apparent Power"
    power_factor:
      name: "Emon P1 Power Factor"

button:
  # Reboot in safe mode before OTA updates
  - platform: safe_mode
    name: "Safe Mode"

This was a quick and dirty copy from original CT clamp code so I might have included a few deliberate mistakes…

I wish somebody would make me a dang sandwich instead, geeze!!

Cool project! Thanks for doing it and sharing. I very much appreciate it.

1 Like

So a bit more time today to investigate…

If I remove ALL references to this component from my YAML, everything works as expected. If I add the packages back in, everything continues to work fine.

However, if I add ANY of the related sensor code back in I get this compile error;

...
Compiling .pioenvs/current-monitor/src/esphome/components/esp32/gpio.o
Compiling .pioenvs/current-monitor/src/esphome/components/esp32/preferences.o
src/esphome/components/emon/emon.cpp: In member function 'virtual void esphome::emon::Emon::setup()':
src/esphome/components/emon/emon.cpp:33:3: warning: missing initializer for member 'adc_continuous_handle_cfg_t::flags' [-Wmissing-field-initializers]
   33 |   };
      |   ^
Compiling .pioenvs/current-monitor/src/esphome/components/esphome/ota/ota_esphome.o
Compiling .pioenvs/current-monitor/src/esphome/components/homeassistant/time/homeassistant_time.o
Compiling .pioenvs/current-monitor/src/esphome/components/logger/logger.o
...

I have cleaned up my code a bit, Clean Build Files and the error persists.

So I’m making a simple assumption that my device works, my simple YAML is ok but I have a problem with this component? Is it ok to use a Lolin S2 mini for this component?

Well, it should be, but I only tested it on plain ESP32 boards. Maybe that’s the cause of your troubles…
Should check whether there is some difference in pin definition (there is for sure, but maybe it is already accounted for in the component)

Sorry spending a lot of time away from home and then lots of “jobs” when we are… So I’m getting the same compile error I mentioned above when I build a new minimal device and has nothing else included, so I’m guessing there’s something in my system that’s causing this?

I’ll have a bit more time in a few days to investigate further and I’ll see if I can build a clean HA/ESPHOME to try it on.

EDIT: Just to be clear by minimal I mean taking your example code and adding enough to make it compile and nothing else.

Hello, im pretty new to HA and esphome but ive really been digging it so far.

Now im trying to build a powermeter with a ZMPT101B (AC sensor module) and the WCS1800 (Current sensor module), i stumbled upon this thread since i was searching for a way to include the emonlib or similar for the calculations so i can get the powermeter up and running but i havnt found a way to do this yet… But this new component sounds promising.

I copied @Petapton first sample config but it wont compile due to mismatch between the toolchain version and the expected version :confused:

Would it be possible to skip the DMA option? im guessing its that feature thats in the core of this issue?

Any suggestions?

INFO ESPHome 2024.8.1
INFO Reading configuration /config/esphome/powermeter.yaml...
INFO Generating C++ source...
INFO Compiling app...
Processing powermeter (board: esp32dev; framework: espidf; platform: https://github.com/platformio/platform-espressif32.git)
--------------------------------------------------------------------------------
HARDWARE: ESP32 240MHz, 320KB RAM, 4MB Flash
 - framework-espidf @ 3.40407.240606 (4.4.7) 
 - tool-cmake @ 3.16.9 
 - tool-ninja @ 1.10.2 
 - tool-riscv32-esp-elf-gdb @ 12.1.0+20221002 
 - tool-xtensa-esp-elf-gdb @ 12.1.0+20221002 
 - toolchain-esp32ulp @ 2.35.0-20220830 
 - toolchain-xtensa-esp-elf @ 13.2.0+20240530
Reading CMake configuration...
-- Building ESP-IDF components for target esp32
-- Project sdkconfig file /data/build/powermeter/sdkconfig.powermeter
-- Configuring incomplete, errors occurred!
See also "/data/build/powermeter/.pioenvs/powermeter/CMakeFiles/CMakeOutput.log".

fatal: not a git repository (or any parent up to mount point /)
Stopping at filesystem boundary (GIT_DISCOVERY_ACROSS_FILESYSTEM not set).
CMake Warning at /data/cache/platformio/packages/[email protected]/tools/cmake/crosstool_version_check.cmake:8 (message):
  Toolchain
  /data/cache/platformio/packages/toolchain-xtensa-esp-elf/bin/xtensa-esp32-elf-gcc
  version 13.2.0 is not the supported version 8.4.0.  Check Getting Started
  documentation or proceed at own risk.

Call Stack (most recent call first):
  /data/cache/platformio/packages/[email protected]/components/esp_common/project_include.cmake:6 (gcc_version_check)
  /data/cache/platformio/packages/[email protected]/tools/cmake/build.cmake:334 (include)
  /data/cache/platformio/packages/[email protected]/tools/cmake/build.cmake:543 (__build_process_project_includes)
  /data/cache/platformio/packages/[email protected]/tools/cmake/project.cmake:476 (idf_build_process)
  CMakeLists.txt:3 (project)


CMake Error at /data/cache/platformio/packages/[email protected]/tools/cmake/crosstool_version_check.cmake:37 (message):
  

  Toolchain:
  /data/cache/platformio/packages/toolchain-xtensa-esp-elf/bin/xtensa-esp32-elf-gcc,
  crosstool-ng version esp-13.2.0_20240530 doesn't match supported version
  esp-2021r2-patch5

  Please try to run 'idf.py fullclean' to solve it quickly.

  Check Getting Started documentation if the error continues.

  You can override this error and proceed with build by defining the
  IDF_MAINTAINER environment variable.

Call Stack (most recent call first):
  /data/cache/platformio/packages/[email protected]/components/esp_common/project_include.cmake:7 (crosstool_version_check)
  /data/cache/platformio/packages/[email protected]/tools/cmake/build.cmake:334 (include)
  /data/cache/platformio/packages/[email protected]/tools/cmake/build.cmake:543 (__build_process_project_includes)
  /data/cache/platformio/packages/[email protected]/tools/cmake/project.cmake:476 (idf_build_process)
  CMakeLists.txt:3 (project)



========================= [FAILED] Took 21.29 seconds =========================

Unfortunately it is not possible, since the DMA is needed to accurately synchronize voltage and current signals (see the Technical details spoiler in the first post).
If you skipped it, you would basically have the good old plain Emonlib, in which you’d have to tune the extra _PHASECAL parameter, which I did not want to. In such case, there’s no point in using this extension, since you could use one of the countless examples of Emonlib/esphome you can find online.

Can I ask you why don’t you want to use DMA or esp-idf 5?