Store data in InfluxDB show in Chronograf

Hi,

Below a testflow to get data in InfluxDB. What kind of conversion or function do I need to store the data in InfluxDB?

[{"id":"ba27c0a00ee1ad6c","type":"debug","z":"eb156835682f62e8","name":"","active":true,"tosidebar":true,"console":false,"tostatus":false,"complete":"false","x":550,"y":260,"wires":[]},{"id":"1f945f65e7400655","type":"influxdb out","z":"eb156835682f62e8","influxdb":"1cdcc0c4c2f1b992","name":"AirQuality","measurement":"3545","precision":"","retentionPolicy":"","database":"InfluxEx","precisionV18FluxV20":"ms","retentionPolicyV18Flux":"","org":"organisation","bucket":"bucket","x":540,"y":320,"wires":[]},{"id":"bc178de67f461d1e","type":"inject","z":"eb156835682f62e8","name":"Payload_Encode ","props":[{"p":"payload"}],"repeat":"","crontab":"","once":false,"onceDelay":0.1,"topic":"","payload":"{\"protocol_version\":2,\"device_id\":3545,\"battery_voltage\":{\"displayName\":\"Battery voltage\",\"value\":3.095,\"unit\":\"V\"},\"air_temperature\":{\"displayName\":\"Air temperature\",\"value\":32.861448081178,\"unit\":\"°C\"},\"air_humidity\":{\"displayName\":\"Air humidity\",\"value\":37.53871976806287,\"unit\":\"%\"},\"barometric_pressure\":{\"displayName\":\"Barometric pressure\",\"value\":101010,\"unit\":\"Pa\"},\"ambient_light_visible_infrared\":{\"displayName\":\"Ambient light (visible + infrared)\",\"value\":3},\"ambient_light_infrared\":{\"displayName\":\"Ambient light (infrared)\",\"value\":1},\"illuminance\":{\"displayName\":\"Illuminance\",\"value\":2.108544,\"unit\":\"lx\"},\"co2_concentration\":{\"displayName\":\"CO2 concentration\",\"value\":852,\"unit\":\"ppm\"},\"co2_sensor_status\":{\"displayName\":\"CO2 sensor status\",\"value\":0},\"raw_ir_reading\":{\"displayName\":\"Raw IR reading\",\"value\":35456},\"activity_counter\":{\"displayName\":\"Activity counter\",\"value\":35},\"total_voc\":{\"displayName\":\"Total VOC\",\"value\":194,\"unit\":\"ppb\"}}","payloadType":"json","x":300,"y":280,"wires":[["1f945f65e7400655","ba27c0a00ee1ad6c"]]},{"id":"1cdcc0c4c2f1b992","type":"influxdb","hostname":"127.0.0.1","port":"8086","protocol":"http","database":"database","name":"Rpi4","usetls":false,"tls":"355a70c2.0410c8","influxdbVersion":"1.8-flux","url":"","rejectUnauthorized":true,"credentials":{}},{"id":"355a70c2.0410c8","type":"tls-config","name":"","cert":"","key":"","ca":"","certname":"","keyname":"","caname":"","servername":"","verifyservercert":false}]

What from that data are you trying to store? What field and tag names do you want for each value?

Once you know the answers to those questions then look at the help text for the node to see how the data must be formatted in msg.payload.

Are you intentionally specifying the flux query language setting for influx?

Also, if you have multiple devices with similar data then do not store them in separate Measurements, use the same Measurement and put the device id in a tag. Then you can query for the data using the device id.

For now, to find out how to do that, I want to try to save, for example, only the temperature and humidity of this sensor. Later I add other values. I have several similar devices, so that should be taken into account as well.

I assumed that the json output of my injectnode would immediately arrive correctly in InfluxDB, partly because I found the following in the help of the InfluxDb node: "If msg.payload is an object containing multiple properties, the fields will be written to the measurement" ... but apparently that's not the case here.

That is exactly the case, but you are providing objects in the fields and influx can only store simple values. So if you want to store just temp and humidity you would need something like this in the payload
{air_temperature: 23.3, air_humidity: 45.5}
Or if you want the device id in a tag
[{air_temperature: 23.3, air_humidity: 45.5}, {device_id: "3425"}]

I thought the "node-red-influxdb-line-protocol " node can fix that for me, cause if I understand correctly it should just be placed between the inject and database nodes . Unfortunately ... it loos like installed but the node is not visible in the left pane.

I know nothing about that node.

Okay, I'll leave that node for later.
Back to your advice:

[{air_temperature: 23.3, air_humidity: 45.5}, {device_id: "3425"}]

So my payload has to be converted to the above format and if so, is that possible with a Change node?

Yes.

There’s a great page in the docs (Working with messages : Node-RED) that will explain how to use the debug panel to find the right path to any data item.

Pay particular attention to the part about the buttons that appear under your mouse pointer when you over hover a debug message property in the sidebar.

BX00Cy7yHi

Though personally I would do it in a Function node, as it is fiddly in a Change node, as you have to move the payload somewhere else before then moving the bits back again.

Not much progress, more spicy than I thought, I have a function where the values are put in an array but that does not give the desired result.

var array = [];

var d = new Date();
    dformat = [d.getFullYear(),
    d.getMonth(),
    d.getDate()].join('.')+' '+
    [d.getHours(),
    d.getMinutes(),
    d.getSeconds()].join(':');
//limit to first gateway, keep it simple
 i = 0;
 array = [{
 DateTime: dformat,  
 //counter: msg.counter,
 Temperature: msg.payload.air_temperature,
 Humidity: msg.payload.air_humidity,
 Pressure: msg.payload.barometric_pressure,
// battery: msg.payload.batt,
// pressure: msg.payload.press,
// weighta: (msg.payload.weight)+((reft-((msg.payload.temp)-100))*calib)
 }
];

var msg1 = {};
msg1.payload = array;

return [msg1];

Actually, with the payload like in the Inject node, I want to see the following in Influx (this is from an old Database that unfortunately no longer works):

> show field keys on TTN
name: 3545
fieldKey fieldType
-------- ---------
value    float

name: 3545
fieldKey                  fieldType
--------                  ---------
GasTotalVOC               float
RawIRRead                 float
activityCount             float
airHumidity               float
airTemp                   float
ambientLightCH0           float
ambientLightCH1           float
barometricPress           float
batteryVolt               float
carbonDioxideCon          float
carbonDioxideSensorStatus float
id                        float
timestamp                 float
value                     string
version                   float

Other solutions to get this result?

If you don't want the device id as a tag then you don't need an array, you just need an object containing the fields, as described in the help text. Take out the square brackets and feed it into a debug node and check what it looks like. Only when it looks right connect it to the influx node.

Also, as the data is for the current time, don't include a timestamp. Influx will put it in for you.

I modified this code for the function node:

var inputjson = JSON.parse(msg.payload);
var _fields = {};
for(var item in inputjson){
    _fields[item] = inputjson[item];
}

msg.payload = [
    {
        measurement: payload.device_id,   //device name as measurement
        fields: _fields,
        timestamp: new Date()
    },
    ];
return msg;

but it gives the error:

22/07/2022, 23:21:38node: 3e037558c11ae452
function : (error)
"SyntaxError: Unexpected token o in JSON at position 1"

Why have you added the parse at the front, the payload is already a JavaScript object? Your previous attempt was almost correct. I told you what to do in my last posts.

I thought this code does just the opposite; make the object suitable for Influx line protocol because I read:
Use JSON Parse to separate JavaScript Object Notation (JSON) text into a table schema for the purpose of downstream processing ...

But back to your suggestion; I've cleaned the code from the brackets and timestamp with the following results:

  msg.payload =
    {
        measurement: "3545",
        temp: msg.payload.air_temperature,
        hum: msg.payload.air_humidity,
        }
    
return msg;

Is this the correct format for Influxdb? When I connect the influxdb node I don't see the desired result.

No, you must supply just a simple object with the field values that you want, not objects

msg.payload = 
{
  temp: msg.payload.air_temperature.value
  hum: msg.payload.air_humidity.value
}
return msg

Read the help text again to see how to set the measurement.

Here are some examples where I'm feeding individual values to InfluxDB

I have trouble with "measurement" . Where and how should it come in the function code?
According to the Influxdb node information I can use msg.measurement if the Influxnode Measurement is left blank.
I get an error:

Function node:

msg.measurement = "3545"
 msg.payload =
    {
        temp: msg.payload.air_temperature,
        hum: msg.payload.air_humidity,
    }
   
return msg;
Error: A 400 Bad Request error occurred: {"error":"unable to parse '3545 hum=[object Object],temp=[object Object]': invalid boolean"}

Do you have a function to get the right format for Influxdb?