Collect data over TCP connection

I have a home automation server, where I can get sensor data over a simple TCP connection.
I send a command over TCP, like GET 1 and the server will return the status of device 1 like 1,0,22.0,15.5,-300. In this case 15.5 is room temperature, and 22.0 is the set temperature on the thermostat.

So I thought it must be possible to scrape this data with telegraf (I hope), but every time I google for this, I get examples of how to get TCP traffic and TCP connections, so I am not getting to the answer I need.
Can you please point me to the right direction?

Hello,

So, in the Github page you can find the socket_listener plugin:

telegraf/plugins/inputs/socket_listener at master · influxdata/telegraf · GitHub

There is a tutorial on how to use the plugin:

Telegraf Socket Listener Input Plugin | Blog | InfluxData

Is this what you are looking for?

OK, so it does not work the way I thought.
I think rather need to use the exec plugin to send GET 1 text to the server, and use the CSV plugin to process the data which is getting returned.
I will play around with that.

Hmmm, I am not sure if this would work. I can certainly use the EXEC and CSV plugin, but I am not sure if I could configure it.
I think the exec part is straight forward:

[[inputs.exec]]
  ## Send TCP command
  commands = ["echo GET 1 | netcat 192.168.1.213 10000 -q 10"]

This calls the TCP port, sends GET 1 and quits after the first new line character.

Next I can override the metric from exec:

  ## override the default metric name of "exec"
  name_override = "homeautomation"

And finally process the response from the server using CSV:

  ## Data format to consume.
  ## Each data format has its own unique set of configuration options, read
  ## more about them here:
  ##   https://github.com/influxdata/telegraf/blob/master/docs/DATA_FORMATS_INPUT.md
  data_format = "csv"
  csv_header_row_count = 0
  csv_column_names = [,,"ambient","settemp",,]
  csv_delimiter = ","

So it will skip the first two and the last two values (I don’t need them) and use the two temperature values. But I am not sure who I could add some fixed tag? Like device = thermostat. Can I do this?

  [inputs.exec.tags]
    device = "thermostat"

As an idea to try, you could script something with bash/python/a language of your choice maybe (I prefer powershell) then

  1. connect to your home automation server with the script
  2. use that LIST command in your screenshot, assign the devices to an array
  3. Iterate through that array for each ID with the GET command
  4. format your data either in JSON or Influx Line Protocol

Without knowing a great deal about your set up, a very basic version might be something like this:

$Devices = That LIST command

foreach($Device in $Devices){
    $Metrics = that GET command | pipe the devices to the get command

    foreach($Metric in $Metrics){
        #based on the screenshot
        $DevoceID = $Metric[0] #Array ID for the ID value for the device
        $DeviceName = $Metric[1] #The ID for the value for Device name 
        $RoomTemp = $Metric[5] # The ID for the metric you want
        #Write-Host in Powershell, maybe ECHO if using bash
        # Format: measurement name,tags and tag values THEN fields and field values.
        # The space between DeviceName and RoomTemp indicates to telegraf the end of tags and beginning of fields
        Write-Host "your_measurement,DeviceID=$($DeviceID),DeviceName=$($DeviceName) RoomTemp=$($RoomTemp)"
    }

}

You’d only need to run the exec plugin then.

1 Like

Yes, this is how it works