Home Assistant + Tasmota (Wemos mini R1) + Battery meter KG140F

Hi, sorry i cant answer your question… Really need the SOC myself too, as thats the main reason i want to try this…
But, do you have the display plugged in, or use a TTL<->RS485 converter? How have you set it up? Are you using a d1 mini?
The display arrived today, will have a go at it tomorrow…

I am using an ESP32s and I connect TX, RX, and GND direct to KG140F. The display is plugged in and “on”.

1 Like

I have SCO working, at least matches what they have on the app. SOC = Ah remaining / Battery capacity (Amp) * 100

Anyone can help in reducing the frequency of the serial log from 10s to 30s or 60s? This may be one of the reasons HA is freezing for some people.

1 Like

Hi, i have gotten a d1 mini reading the data from the shunt, but when i add the lines:

mqtt:

  • name: D1_mini_1
    topic: tele/D1_mini_1/RESULT

To my config yaml file, i get this error when checking the config yaml file before i boot: (the topic name in my tasmota config is D1_mini_1). Do i need a ‘full topic’?

Invalid config for [mqtt]: expected dictionary for dictionary value @ data[‘mqtt’]. Got [OrderedDict([(‘name’, ‘D1_mini_1’), (‘topic’, ‘tele/D1_mini_1/RESULT’)])]. (See /config/configuration.yaml, line 198).

Any ideas? (sorry, im new to HA etc)

Hi, i have gotten a d1 mini reading the data from the shunt, but when i add the lines:

mqtt:

  • name: D1_mini_1
    topic: tele/D1_mini_1/RESULT

To my config yaml file, i get this error when checking the config yaml file before i boot: (the topic name in my tasmota config is D1_mini_1). Do i need a ‘full topic’?

Invalid config for [mqtt]: expected dictionary for dictionary value @ data[‘mqtt’]. Got [OrderedDict([(‘name’, ‘D1_mini_1’), (‘topic’, ‘tele/D1_mini_1/RESULT’)])]. (See /config/configuration.yaml, line 198).

Any ideas?

For example, i have the lines in tasmota console:

18:10:31.823 MQT: tele/D1_mini_1/RESULT = {“SerialReceived”:":R50=1,\n:r50=1,87,2669,200,268391,98603,387360,0,129,0,99,0,8420,1000,\r\n:R51=1,\n:r51=1,143,0,0,0,0,0,100,0,0,2800,100,100,100,0,1,1,\r\n"}

Mine is done differently. Try this.

template:
  - trigger:
      - platform: mqtt
        topic: tele/D1_mini_1/RESULT
    sensor:
      - name: Freezer Battery Temperature
        unit_of_measurement: "°C"
        state: "{{ (trigger.payload.split(',')[9] | float-100) }}"

Thanks, trying how you say, unfortunately nothing shows up, and i now get this in the logs:

Logger: homeassistant.config
Source: config.py:982
First occurred: 8:21:48 PM (3 occurrences)
Last logged: 8:23:50 PM

Invalid config for [template]: [trigger] is an invalid option for [template]. Check: template->sensor->3->trigger. (See /config/configuration.yaml, line 183).
Invalid config for [template]: [trigger] is an invalid option for [template]. Check: template->sensor->3->trigger. (See /config/configuration.yaml, line 180).

Any ideas whay? Thanks again :+1::+1:

Post your yaml config. I am not an expert but let me see if I can help

Hi, thanks for offering your time :blush: (scroll to the bottom, the rest of the yaml it for my inverter, that all works fine…)

default_config:

# Load frontend themes from the themes folder
frontend:
  themes: !include_dir_merge_named themes

# Text to speech
tts:
  - platform: google_translate

automation: !include automations.yaml
script: !include scripts.yaml
scene: !include scenes.yaml

http:
  use_x_forwarded_for: true
  trusted_proxies:
    - 172.30.33.0/24
    


modbus:
  - name: epever
    type: rtuovertcp
    host: 192.168.0.188
    port: 8088
    delay: 5
    timeout: 10
    close_comm_on_error: false
    retry_on_empty: true
    retries: 20
    sensors:
      # Utility
      - name: "Grid Voltage"
        unit_of_measurement: V
        slave: 10
        address: 0x3500
        input_type: input
        scale: 0.01
        precision: 2      
      - name: "Grid Current"
        unit_of_measurement: A
        slave: 10
        address: 0x3501
        input_type: input
        scale: 0.01
        precision: 2  
      - name: "Grid State"
        # 0:Normal, 1:Low input; 2:High input, 3: No connected
        slave: 10
        address: 0x3511
        input_type: input
      - name: "Grid Total"
        unit_of_measurement: kWh
        slave: 10
        address: 0x350F
        input_type: input
        scale: 0.01
        precision: 2
        data_type: int32
        swap: word
        count: 2
      # PV Array
      - name: "PV Voltage"
        unit_of_measurement: V
        slave: 10
        address: 0x3549
        input_type: input
        scale: 0.01
        precision: 2   
      - name: "PV Current"
        unit_of_measurement: A
        slave: 10
        address: 0x354A
        input_type: input
        scale: 0.01
        precision: 2
      - name: "PV Power"
        unit_of_measurement: W
        slave: 10
        address: 0x354B
        input_type: input
        scale: 0.01
        precision: 2
        data_type: int32
        swap: word
        count: 2
      - name: "PV Total"
        unit_of_measurement: kWh
        slave: 10
        address: 0x3557
        input_type: input
        scale: 0.01
        precision: 2
        data_type: int32
        swap: word
        count: 2
      # Load
      - name: "Load Voltage"
        unit_of_measurement: V
        slave: 10
        address: 0x3521
        input_type: input
        scale: 0.01
        precision: 2      
      - name: "Load Current"
        unit_of_measurement: A
        slave: 10
        address: 0x3522
        input_type: input
        scale: 0.01
        precision: 2   
      - name: "Load Total"
        unit_of_measurement: kWh
        slave: 10
        address: 0x3530
        input_type: input
        scale: 0.01
        precision: 2
        data_type: int32
        swap: word
        count: 2
      # Battery
      - name: "Battery Voltage"
        unit_of_measurement: V
        slave: 10
        address: 0x3580
        input_type: input
        scale: 0.01
        precision: 2      
      - name: "Battery Current"
        unit_of_measurement: A
        slave: 10
        address: 0x3581
        input_type: input
        scale: 0.01
        precision: 2   
      - name: "Battery Capacity"
        unit_of_measurement: "%"
        slave: 10
        address: 0x3586
        input_type: input
        scale: 1
      - name: "Battery Temp"
        #ElectricChrgBatteryTemp 
        unit_of_measurement: "°C"
        slave: 10
        address: 0x3512
        input_type: input
        scale: 0.01
      - name: "Battery State"
        # 0:Normal, 1:Overvoltage, 2:Undervoltage, 3:Undervoltage Disconnect, 4:Fault 
        slave: 10
        address: 0x3589
        input_type: input
      - name: "Charging Mode"
        # 1:Solar Priority, 2:Utility & Solar, 3:Solar
        slave: 10
        address: 0x9607
        input_type: holding
      - name: "Inverter Mode"
        # 0:Inverter priority, 1:Utility Priority
        slave: 10
        address: 0x9608
        input_type: holding
      - name: "Inverter Temp"
        #LoadHeatSink2Temp 
        unit_of_measurement: "°C"
        slave: 10
        address: 0x3533
        input_type: input
        scale: 0.01
       
       
        
        
        
template:
  sensor:
    - name: "Grid Power"
      unit_of_measurement: W
      device_class: power
      state: "{{((states('sensor.grid_current')| float(0) * states('sensor.grid_voltage')| float(0))) | round(2) }}"
      
    - name: "Power into batt"
      state: "{{ states('sensor.grid_power') | float + states('sensor.pv_power') | float }}"
      unit_of_measurement: W
      device_class: power
        
    - name: "House Load"
      unit_of_measurement: W
      device_class: power
      state: "{{((states('sensor.load_current')| float(0) * states('sensor.load_voltage')| float(0))) | round(2) }}"

    - trigger:
       - platform: mqtt
         topic: tele/D1_mini_1/RESULT

   

sensor:
  - platform: integration
    source: sensor.house_load
    name: energy_used
    unit_prefix: k
    round: 2

Also, when adding - trigger: - platform: mqtt topic: tele/D1_mini_1/RESULT
then sensors grid_power and house_load stop working also… Causing some kind of problem with the template i think?

see if this works. I put trigger before the sensor.

template:
  - trigger:
      - platform: mqtt
        topic: tele/D1_mini_1/RESULT
    sensor:
      - name: "Grid Power"
        unit_of_measurement: W
        device_class: power
        state: "{{((states('sensor.grid_current')| float(0) * states('sensor.grid_voltage')| float(0))) | round(2) }}"       
      - name: "Power into batt"
        state: "{{ states('sensor.grid_power') | float + states('sensor.pv_power') | float }}"
        unit_of_measurement: W
        device_class: power         
      - name: "House Load"
        unit_of_measurement: W
        device_class: power
        state: "{{((states('sensor.load_current')| float(0) * states('sensor.load_voltage')| float(0))) | round(2) }}"

Thanks very much, if also been having a bit of help on another thread i made, and is working now :+1::+1::+1::+1:

Pasted some more lines from giro above to test, but needs some editing as wrong values for current and capacity


# Loads default set of integrations. Do not remove.
default_config:

# Load frontend themes from the themes folder
frontend:
  themes: !include_dir_merge_named themes

# Text to speech
tts:
  - platform: google_translate

automation: !include automations.yaml
script: !include scripts.yaml
scene: !include scenes.yaml

http:
  use_x_forwarded_for: true
  trusted_proxies:
    - 172.30.33.0/24
    


modbus:
  - name: epever
    type: rtuovertcp
    host: 192.168.0.188
    port: 8088
    delay: 5
    timeout: 10
    close_comm_on_error: false
    retry_on_empty: true
    retries: 20
    sensors:
      # Utility
      - name: "Grid Voltage"
        unit_of_measurement: V
        slave: 10
        address: 0x3500
        input_type: input
        scale: 0.01
        precision: 2      
      - name: "Grid Current"
        unit_of_measurement: A
        slave: 10
        address: 0x3501
        input_type: input
        scale: 0.01
        precision: 2  
      - name: "Grid State"
        # 0:Normal, 1:Low input; 2:High input, 3: No connected
        slave: 10
        address: 0x3511
        input_type: input
      - name: "Grid Total"
        unit_of_measurement: kWh
        slave: 10
        address: 0x350F
        input_type: input
        scale: 0.01
        precision: 2
        data_type: int32
        swap: word
        count: 2
      # PV Array
      - name: "PV Voltage"
        unit_of_measurement: V
        slave: 10
        address: 0x3549
        input_type: input
        scale: 0.01
        precision: 2   
      - name: "PV Current"
        unit_of_measurement: A
        slave: 10
        address: 0x354A
        input_type: input
        scale: 0.01
        precision: 2
      - name: "PV Power"
        unit_of_measurement: W
        slave: 10
        address: 0x354B
        input_type: input
        scale: 0.01
        precision: 2
        data_type: int32
        swap: word
        count: 2
      - name: "PV Total"
        unit_of_measurement: kWh
        slave: 10
        address: 0x3557
        input_type: input
        scale: 0.01
        precision: 2
        data_type: int32
        swap: word
        count: 2
      # Load
      - name: "Load Voltage"
        unit_of_measurement: V
        slave: 10
        address: 0x3521
        input_type: input
        scale: 0.01
        precision: 2      
      - name: "Load Current"
        unit_of_measurement: A
        slave: 10
        address: 0x3522
        input_type: input
        scale: 0.01
        precision: 2   
      - name: "Load Total"
        unit_of_measurement: kWh
        slave: 10
        address: 0x3530
        input_type: input
        scale: 0.01
        precision: 2
        data_type: int32
        swap: word
        count: 2
      # Battery
      - name: "Battery Voltage"
        unit_of_measurement: V
        slave: 10
        address: 0x3580
        input_type: input
        scale: 0.01
        precision: 2      
      - name: "Battery Current"
        unit_of_measurement: A
        slave: 10
        address: 0x3581
        input_type: input
        scale: 0.01
        precision: 2   
      - name: "Battery Capacity"
        unit_of_measurement: "%"
        slave: 10
        address: 0x3586
        input_type: input
        scale: 1
      - name: "Battery Temp"
        #ElectricChrgBatteryTemp 
        unit_of_measurement: "°C"
        slave: 10
        address: 0x3512
        input_type: input
        scale: 0.01
      - name: "Battery State"
        # 0:Normal, 1:Overvoltage, 2:Undervoltage, 3:Undervoltage Disconnect, 4:Fault 
        slave: 10
        address: 0x3589
        input_type: input
      - name: "Charging Mode"
        # 1:Solar Priority, 2:Utility & Solar, 3:Solar
        slave: 10
        address: 0x9607
        input_type: holding
      - name: "Inverter Mode"
        # 0:Inverter priority, 1:Utility Priority
        slave: 10
        address: 0x9608
        input_type: holding
      - name: "Inverter Temp"
        #LoadHeatSink2Temp 
        unit_of_measurement: "°C"
        slave: 10
        address: 0x3533
        input_type: input
        scale: 0.01
       
       
        
        
        
template:
- sensor:
    - name: "Grid Power"
      unit_of_measurement: W
      device_class: power
      state: "{{((states('sensor.grid_current')| float(0) * states('sensor.grid_voltage')| float(0))) | round(2) }}"
      
    - name: "Power into batt"
      state: "{{ states('sensor.grid_power') | float + states('sensor.pv_power') | float }}"
      unit_of_measurement: W
      device_class: power
        
    - name: "House Load"
      unit_of_measurement: W
      device_class: power
      state: "{{((states('sensor.load_current')| float(0) * states('sensor.load_voltage')| float(0))) | round(2) }}"
    
- trigger:
  - platform: mqtt
    topic: tele/D1_mini_1/RESULT
      
  sensor:
    - name: Temperatura
      unit_of_measurement: "°C"
      state: "{{ (trigger.payload.split(',')[9] | float-100) }}"
    - name: Tensione
      unit_of_measurement: "V"
      state: "{{ (trigger.payload.split(',')[3] | float/100) }}"
    - name: Corrent
      unit_of_measurement: "A"
      state: "{{ (trigger.payload.split(',')[4] | float/100) }}"
    - name: Potenza
      unit_of_measurement: "W"
      state: "{{ (trigger.payload.split(',')[6] | float/100) }}"
    - name: Capacità
      unit_of_measurement: "%"
      state: "{{ (trigger.payload.split(',')[5] | float/11000*100) }}"
    - name: Consumato
      unit_of_measurement: "kWh"
      state: "{{ (trigger.payload.split(',')[6] | float/10000) }}"  
      

sensor:
  - platform: integration
    source: sensor.house_load
    name: energy_used
    unit_prefix: k
    round: 2
      
      ```

I used the info provided by OP and this thread to link my Juntek 100A shunt to Home assistant.
I appreciate this, it feels good to have this info visible without having to reach for my phone or walk to the display.

I was able to link the state of charge and I’ll paste my code in case others can use it.
My code has all the sections of r50 because I wanted to monitor the values to see the info it carried
This code goes in the configuration.yaml (putting this down as it stumped me when I found the thread as a newb)

One thing I’m stumped on as this is my first HA project, is the value for the AMPS being used is sent as a positive number even when the amps are being drawn.

I found the value that corresponds to the negative and positive switch.
It’s down the string at section [12], it returns a 0 if the amps are negative and it returns a 1 if the amps are positive.
Can anyone suggest a code that will watch the section at [12] and if it is 1 do nothing but if it is 0 it would take the value and subtract the value x 2.

var pos/neg
var amps
if [12] = 1
do nothing
if [12] = 0
pos/neg = amps - (amps + amps)

or a conversion trick to reverse polarity of an sensor value.
I’m new to HA code

template:
  - trigger:
      - platform: mqtt
        topic: tele/D1_mini_1/RESULT

    sensor:
      - name: SOCX
        unit_of_measurement: "%"
        state: "{{ (trigger.payload.split(',')[2] | float/11000*100) }}"
      - name: Voltage
        unit_of_measurement: "V"
        state: "{{ (trigger.payload.split(',')[3] | float/100) }}"
      - name: Current
        unit_of_measurement: "A"
        state: "{{ (trigger.payload.split(',')[4] | float/100) }}"
      - name: Amp Hours Remaining
        unit_of_measurement: "AH"
        state: "{{ (trigger.payload.split(',')[5] | float/1000) }}"
      - name: Battery Remaining
        unique_id: 0000420000-1
        unit_of_measurement: "%"
        state: "{{ (trigger.payload.split(',')[5] | float/10/400) }}"
      - name: Total Power Used
        unit_of_measurement: "AH"
        state: "{{ (trigger.payload.split(',')[6] | float/1000) }}"
      - name: Elec. Consumption
        unit_of_measurement: "kW-h"
        state: "{{ (trigger.payload.split(',')[7] | float/100000) }}"
      - name: Total kW-h
        unit_of_measurement: "kW-h"
        state: "{{ (trigger.payload.split(',')[8] | float/10000) }}"
      - name: Temperature
        unit_of_measurement: "°C"
        state: "{{ (trigger.payload.split(',')[9] | float-100) }}"
      - name: VoltageXX
        unit_of_measurement: "V"
        state: "{{ (trigger.payload.split(',')[10] | float/100) }}"
      - name: CurrentXX
        unit_of_measurement: "A"
        state: "{{ (trigger.payload.split(',')[11] | float/100) }}"
      - name: pos/neg
        state: "{{ (trigger.payload.split(',')[12]) }}"
      - name: Battery Life AH
        unit_of_measurement: "AH"
        state: "{{ (trigger.payload.split(',')[13] | float/10) }}"
      - name: Internal Resistance
        unit_of_measurement: "m-Ohm"
        state: "{{ (trigger.payload.split(',')[14] | float/100) }}"

Hi, my Tasmota consolle doesn’t show 11:27:23.727 MQT: tele/BatteryMonitor/RESULT = same as others. Did I miss something?

Hope you did not miss this

Rule1 on System#Boot do RuleTimer1 10 endon on Rules#Timer=1 do backlog SerialSend :R50=1,2,1,; RuleTimer1 10 endon

Rule1 1

Check also the connection between KG140F and your Wemos mini (or whatever you use)

Hi Giro,
can you please suggest a RS485 converter? Or send some detail (chip name and input and ouput connection) and a picture of your?
I buyed a rs485 to TTL but it doesn’t seem to be correct for this job.
Thank you very much.

Lucio

Hi,
I’m a noob in home assistant but i want to contribute with this community.
After reading the documentation about the KG140F DC 0-120V 100A and compare it with the information of this thread I got the following information:

The communication channel give me the following:
My shunt has this values:

r50=2,215,2056,200,5408,4592,9437,14353,134,0,0,0,162,30682

Explanation:


position    Description
1           2 represents the communication address;
2           215 represents the checksum;
3           2056 represents the voltage of 20.56V;
4           200 represents current 2.00A;
5           5408 represents the remaining battery capacity is 5.408Ah;
6           4593 means the cumulative capacity is 4.593Ah;
7           9437 represents the watt-hour is 0.09437kw.h;
8           14353 represents the running time of 14353s;
9           134 represents the ambient temperature is 34℃;
10          0 means the function is pending;
11          0 means the output status is ON; (0-ON, 1-OVP, 2-OCP, 3-LVP, 4-NCP, 5-OPP, 6-OTP, 255-OFF)
12          0 represents the direction of current, and the current is forward current; (0-forward, 1-reverse)
13          162 means battery life is 162 minutes;
14          30682 represents the internal resistance of the battery is 306.82mΩ.

Decoding:

                                HA position split
Address(1,2,3,4,5,6,....)               1
Checksum:153,		                    2
Voltage(V)(2056->20.56)                 3   
CurrentAmpere(A)(200->2.0)              4
RemainingAh(Ah)(5408->5.408)            5
ElapsedAH(Ah)			                6   
AccumulatedChargingCapacity(Kwh)	    7
RunningTimeSeconds,				        8
Temperature(ºC)(134->34ºc->134-100)     9
pending 		                        10
OutputStatus(alarms)                    11
CurrentDirection(0/1)                   12
BatteryLifeMinutes      	            13
ohm(30682->306.82->30682/100)           14

After struggling my head with the sensors, templates and so on, i finished with the following package(yaml file): pck_enrgyconsum_battery_control.yaml

input_number:
  number_ampere_preset:
    name: Number-Ampere-preset
    icon: mdi:battery-high
    min: 0
    max: 360
    initial: 127.5
    step: 0.1
    mode: box
    unit_of_measurement: Ah


template:
  - trigger:
      - platform: mqtt
        topic: tele/tasmota_03-ESP32-Shunt-PowerBank/RESULT
    sensor:
      - name: KG140F-01-Address
        # unit_of_measurement: ""
        state: "{{ (trigger.payload.split(',')[1] | float) }}"

      - name: KG140F-01-Checksum
        # unit_of_measurement: "V"
        state: "{{ (trigger.payload.split(',')[2] | float) }}"

      - name: KG140F-01-Voltage
        unit_of_measurement: "V"
        state: "{{ (trigger.payload.split(',')[3] | float/100) }}"  

      - name: KG140F-01-CurrentAmpere
        unit_of_measurement: "Ah"
        state: "{{ (trigger.payload.split(',')[4] | float/100) }}"

      - name: KG140F-01-RemainingAh
        unit_of_measurement: "Ah"
        state: "{{ (trigger.payload.split(',')[5] | float/1000) }}"

      - name: KG140F-01-ElapsedAH
        unit_of_measurement: "Ah"
        state: "{{ (trigger.payload.split(',')[6] | float/1000) }}"

      - name: KG140F-01-AccumChrgCapacity
        unit_of_measurement: "Kwh"
        state: "{{ (trigger.payload.split(',')[7] | float/100000) }}"        

      - name: KG140F-01-RunningTimeSeconds
        unit_of_measurement: "s"
        state: "{{ (trigger.payload.split(',')[8] | float) }}"

      - name: KG140F-01-RunningTimeHours
        unit_of_measurement: "h"
        state: "{{ (trigger.payload.split(',')[8] | float/60/60) }}"        

      - name: KG140F-01-Temperature
        unit_of_measurement: "ºC"
        state: "{{ (trigger.payload.split(',')[9] | float-100) }}"        

      - name: KG140F-01-Pending
        # unit_of_measurement: ""
        state: "{{ (trigger.payload.split(',')[10] | float) }}"

      - name: KG140F-01-OutputStatus
        # unit_of_measurement: ""
        state: "{{ (trigger.payload.split(',')[11] | float) }}"

      - name: KG140F-01-CurrentDirection
        # unit_of_measurement: ""
        state: "{{ (trigger.payload.split(',')[12] | float) }}"        

      - name: KG140F-01-BatteryLifeMinutes
        unit_of_measurement: "min"
        state: "{{ (trigger.payload.split(',')[13] | float) }}"

      - name: KG140F-01-BatteryLifeHours
        unit_of_measurement: "h"
        state: "{{ (trigger.payload.split(',')[13] | float/60) }}"

      - name: KG140F-01-Ohm      
        unit_of_measurement: "mΩ"
        state: "{{ (trigger.payload.split(',')[14] | float/100) }}"


sensor:
# Calculate current power
  - platform: template
    sensors:
      kg140f_01_currentpower:
        value_template: >
            {% set t = states('sensor.kg140f_01_currentdirection') | float(0) %}
            {% if t == 0 %}
              {{ '%0.1f' | format ( -1 |float * 
                                    ( 
                                      states('sensor.kg140f_01_voltage') | float * 
                                      states('sensor.kg140f_01_currentampere') | float 
                                    )
                                  )
              }}
            {% elif t == 1 %}
              {{ '%0.1f' | format 
                              ( 
                                states('sensor.kg140f_01_voltage') | float * 
                                states('sensor.kg140f_01_currentampere') | float 
                              )
              }}
            {% else %}
              {{ '%0.1f' | format 
                              ( 
                                states('sensor.kg140f_01_voltage') | float * 
                                states('sensor.kg140f_01_currentampere') | float 
                              )
              }}              
            {% endif %}           
        unit_of_measurement: 'W'
        friendly_name: KG140F-01 Current Power
      
      kg140f_01_ampereconsumption:
        value_template: >
            {% set t = states('sensor.kg140f_01_currentdirection') | float(0) %}
            {% if t == 0 %}
              {{ '%0.1f' | format ( -1 |float * states('sensor.kg140f_01_currentampere') | float ) }}
            {% elif t == 1 %}
              {{states('sensor.kg140f_01_currentampere')|float }}
            {% else %}
              {{states('sensor.kg140f_01_currentampere')|float }}
            {% endif %}          
        unit_of_measurement: 'Ah'
        friendly_name: KG140F-01 Ampere Consumption

      kg140f_01_battery_level:
        value_template: >
          {{ '%0.1f' | format
                        (
                          (states('sensor.kg140f_01_remainingah') | float * 100 ) /
                          states('input_number.number_ampere_preset') | float
                        )
          }}       
        unit_of_measurement: '%'
        friendly_name: KG140F-01 Battery Level

The only thing that is not working for me, is the tasmota rule, despite whatever i put in the rule, the transmission to the HA is every second… I bought some D1 mini, just for check if the problem is the ESP32 or not.

Rule1 on System#Boot do RuleTimer1 10 endon on Rules#Timer=1 do backlog SerialSend :R50=1,2,1,; RuleTimer1 10 endon

Rule1 1

So the dashboard is:
When the shunt detect the negative current:

When the shunt detect the positive current(charging):

Thanks a lot to all of you for your knowledge
Luis.

Thank you all for this. Seems perfect for RV use also!

Has anyone figured out how to filter only the “:R50=1,2,1” message?