Create multiple / different sensors from UART Reading

Hi all,
i would like to use an ESPHome to create Sensors in HA from an UART Reading.
My oven send every second a long String through an UART interface. The String looks like this:

State= 30. 31, Temp= 29.3, SOLL-Pos= 5, IST-Pos= 76, MotorMAX=1520, Zeit=45143, TempAV= 29, MAX_Temp=749, TempGradient= 0, Tuer=1, ECO= 0, LEDRot=1, LEDGruen=0, ST= 0, Magnet=0, Relais=1, Control=0, PRIME= 1, BetriebsStdn= 1391

Is there a possibility to extract the values out of the string (RegExp?) and create sensors for each value? I mean not just a text sensor.

Currently its working with FHEM and the ECMD and some RegExp to create separate readings for each. But I want to move this to HA with ESPhome.

Thank you

If you get the string in to HA then you can perhaps use this template to convert it to a json that can be placed as attributes and probably should work.

Just replace the string with the entity

{% set str = "State= 30. 31, Temp= 29.3, SOLL-Pos= 5, IST-Pos= 76, MotorMAX=1520, Zeit=45143, TempAV= 29, MAX_Temp=749, TempGradient= 0, Tuer=1, ECO= 0, LEDRot=1, LEDGruen=0, ST= 0, Magnet=0, Relais=1, Control=0, PRIME= 1, BetriebsStdn= 1391" %}
{% set str = str.replace("= ", "=") %}
{% set arr = str.split(", ") %}

{
{% for ar in arr -%}
  {% set  pair = ar.split("=") %}
  {% for p in pair -%}
    "{{ p }}"
    {%- if loop.first %}: {% elif loop.last %}, {% endif -%}
  {%- endfor %}
{%- endfor %}
}

Hello,
i’m a little bit further in my approach.
I’ve got on temprature reading to HA. And it is done at the ESP.
I mixed a littlebit the UART Text sensor with general custom sensor stuff.

But now my next try is to create a sensor and a binarysensor in one component. Like the Custom_Sensor with the two outputs.

Two sensors works but i want one sensor and one binary_sensor.
What i have to do?

Here is my current code:

#include "esphome.h"

class UartReadLineSensor : public Component, public UARTDevice{
 public:
  UartReadLineSensor(UARTComponent *parent) : UARTDevice(parent) {}
  Sensor *temperature_sensor = new Sensor();
  Sensor *tuer_sensor = new Sensor();



  void setup() override {
    // nothing to do here
  }

  int readline(int readch, char *buffer, int len)
  {
    static int pos = 0;
    int rpos;

    if (readch > 0) {
      switch (readch) {
        case '\n': // Ignore new-lines
          break;
        case '\r': // Return on CR
          rpos = pos;
          pos = 0;  // Reset position index ready for next time
          return rpos;
        default:
          if (pos < len-1) {
            buffer[pos++] = readch;
            buffer[pos] = 0;
          }
      }
    }
    // No end of line has been found, so return -1.
    return -1;
  }

  void loop() override {
    const int max_line_length = 240;
    static char buffer[max_line_length];
    char buffer2[max_line_length];
    String mystring = "123";
    float temp = 0;
    bool tuer = 0;
    while (available()) {
      if(readline(read(), buffer, max_line_length) > 0) {
        mystring = String(buffer);
        //mystring = mystring.substring(20, 24);
        temp = mystring.substring(20, 25).toFloat();
        tuer = mystring.substring(133, 134).toInt();
        mystring.toCharArray(buffer2,max_line_length);
        temperature_sensor->publish_state(temp);
        tuer_sensor->publish_state(tuer);
      }
    }
  }
};
esphome:
  name: ofen
  includes:
   - uart_read_line_sensor.h

esp8266:
  board: d1_mini

# Enable logging
logger:
  baud_rate: 0

# Enable Home Assistant API
api:
  encryption:
    key: "tj8nb0V/+h+Kg2PG0tk4dXO6c3rbwoLz9iwI3Kzcio4="

ota:
  password: "58d941a95dc79c655f97d7cacf1c51bf"

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

  # Enable fallback hotspot (captive portal) in case wifi connection fails
  ap:
    ssid: "Ofen Fallback Hotspot"
    password: "gmRPVSPN89GD"

captive_portal:

uart:
  id: uart_bus
  rx_pin: RX
  #rx_buffer_size: 2048
  baud_rate: 38400
  data_bits: 8
  parity: NONE
  stop_bits: 1
  #debug:
  # direction: BOTH
  #  dummy_receiver: true
  #  after:
  #    bytes: 300
  #    delimiter: "\r\n"
  #  sequence:
  #    - lambda: UARTDebug::log_string(direction, bytes);

sensor:
- platform: custom
  lambda: |-
    auto my_custom_sensor = new UartReadLineSensor(id(uart_bus));
    App.register_component(my_custom_sensor);
    return {my_custom_sensor->temperature_sensor, my_custom_sensor->tuer_sensor};
  sensors:
    - name: "ofen"
      accuracy_decimals: 1
    - name: "ofentuer"
      accuracy_decimals: 1

1 Like