面向工业应用的 InfluxDB 1.8 架构设计?
InfluxDB 1.8 schema design for industrial application?
我有 node-red-S7PLC link 以 1.5 秒的周期将以下数据推送到 InfluxDB。
msg.payload = {
name: 'PLCTEST',
level1_m: msg.payload.a90, "value payload from PLC passed to influx"
power1: msg.payload.a93,
valvepos_%: msg.payload.a107,
temp1: msg.payload.a111,
washer_acidity: msg.payload.a113,
etc.
}
return msg;
总共 130 个单独的数据点,由二进制状态组成,例如警报、按钮按下和测量(温度、压力、流量...)
作为对数据库写入的压力测试,这已经 运行 一周了。写作似乎很好,但我注意到,如果我在 Grafana 仪表板中从 10 次温度测量和 30 分钟查询 window 切换到 3 小时查询,加载时间开始变得令人讨厌。 12 小时 window 是不行的。我认为这是因为我所有的东西都被推送为字段键和字段值。没有索引,这会使数据库不堪重负。
Grafana 查询检查器每个 measurement_query 给我 1081 行,所以 x10 = 10810 rows/dasboard_query。但整个池涌入必须经过 130 次测量 x 1081 = 140530 行/3 小时 window.
我想获得一些关于如何优化架构的建议。我有以下想法。
数据库:Aplication_nameX
测量值:Process_metrics、
标签:温度、压力、流量、%、液位、酸度、功率
Tag_values:CT-xx1...CT-xxn,CP-xx1...CP-xxn,CF-xx1...CF-xxn,....
字段键=值,字段值=值
测量值:Alarms_On,
Fieldkey=状态,fieldvalue=“真”,“假”
Measurement:Binary_ON
Fieldkey: State, fieldvalue= "true", "false"
这将在几个临时工时处于节点红色(我认为):
msg.payload = [{
Value: msg.payload.xxx, "value payload from PLC passed to influx"
Value: msg.payload.xxx,
Value: msg.payload.xxx
},
{
Temp:"CT_xx1",
Temp:"CT_xx2",
Temp:"CT_xx2"
}];
return msg;
编辑:遵循罗伯茨的评论。
在写这里之前,我在网上阅读了一周的涌入手册和其他示例。一些涌入与正常 SQL 思维定式的不同和独特之处,我确实发现这异常困难。但是周末我确实有一些清晰的时刻。
我觉得下面这样比较合适
DB: Station_name
measurements: Process_metrics,Alarms, Binary.
Tags: "SI_metric"
Values= "Temperature", "Pressure" etc.
Fieldkey: "proces_position"= CT/P/F_xxx.
values= process_values
这应该可以防止基数与我最初的想法相悖。
我认为警报和二进制文件可以只保留为 fieldkey/fieldvalue,将它们分开到自己的测量值应该提供足够的过滤。这些也仅在状态更改时记录,因此与 1s 周期的类似物相比,对数据库的输入要少得多。
按照我原来的 node-red 流程代码,这将转换为批输出功能:
msg.payload = [
{
measurement: "Process_metrics",
fields: {
CT_xx1: msg.payload.xxx,
CT_xx2: msg.payload.xxx,
CT_xx3: msg.payload.xxx
},
tags:{
metric:"temperature"
},
{
measurement: "Process_metrics",
fields: {
CP_xx1: msg.payload.xxx,
CP_xx2: msg.payload.xxx,
CP_xx3: msg.payload.xxx
},
tags:{
metric:"pressure"
},
{
measurement: "Process_metrics",
fields: {
CF_xx1: msg.payload.xxx,
CF_xx2: msg.payload.xxx,
CF_xx3: msg.payload.xxx
},
tags:{
metric:"flow"
},
{
measurement: "Process_metrics",
fields: {
AP_xx1: msg.payload.xxx,
AP_xx2: msg.payload.xxx,
AP_xx3: msg.payload.xxx
},
tags:{
metric:"Pumps"
},
{
measurement: "Binary_states",
fields: {
Binary1: msg.payload.xxx,
Binary2: msg.payload.xxx,
Binary3: msg.payload.xxx
},
{
measurement: "Alarms",
fields: {
Alarm1: msg.payload.xxx,
Alarm2: msg.payload.xxx,
Alarm3: msg.payload.xxx
}
];
return msg;
编辑 2:
测试我的上述想法并进一步完善后的最终想法。
我的第二个想法没有按预期工作。 Grafana 变量的最后一步不起作用,因为流程数据具有字段中所需的信息,而不是标签。这使得 Grafana 方面对从字段到 link 到 grafana 变量下拉列表的 plc 标签名称信息的 rexec 查询感到恼火。因此再次 运行 资源密集型字段查询。
我无意中发现了一个博客 post,内容是关于如何使用 TSDB 理清思路,而上述想法仍然太 SQL 类似于使用 TSDB 处理数据的方法。我进一步改进了数据库结构,我似乎发现了不同步骤(PLC->NodeRed->influxDB->Grafana)中编码时间和数据库查询负载的妥协。从写入和查询压力时的 1gb ram 使用到正常使用测试中的 100-300MB。
目前正在测试中:
Python 脚本,用于将 PLC 端标签和描述从 csv 压缩为 Node-Red 的可复制粘贴格式。从 csv 中提取温度测量值并格式化为 nodered 的示例。
import pandas as pd
from pathlib import Path
file1 = r'C:\Users\....pandastestcsv.csv
df1 = pd.read_csv(file1, sep=';')
dfCT= df1[df1['POS'].str.contains('CT', regex=False, na=False)]
def my_functionCT(x,y):
print( "{measurement:"+'"temperature",'+"fields:{value:msg.payload."+ x +",},tags:{CT:\"" + y +'\",},},' )
result = [my_functionCT(x, y) for x, y in zip(dfCT['ID'], dfCT['POS'])]
此输出是来自 CSV 的所有温度测量值 CT。 {measurement:"temperature",fields:{value:msg.payload.a1,},tags:{CT:"tag description with process position CT_310",},},
此列表可以复制粘贴到 Node-Red 数据link 有效负载到 influxDB。
InfluxDB:
数据库:PLCTEST
测量:温度、压力、流量、泵、阀门、警报,on_off.....
标签键:CT、CP、CF、misc_mes...
标签字段:“标签的 PLC 描述”
字段键:值
字段值:“来自 PLC 有效载荷的过程测量值”
这可以在合理范围内检查每个测量的基数,并且可以更好地针对相关数据进行查询,而无需 运行 通过整个数据库。 Ram 和 CPU 负载现在很小,并且在 Grafana 中从 1h 跳到 12h 查询在几秒钟内加载而没有锁定。
在设计 InfluxDB 测量模式时,我们需要非常小心地选择标签和字段。
每个标签值将创建单独的系列,随着标签值数量的增加,InfluxDB 服务器的内存需求将呈指数增长。
从问题中给出的测量描述中,我可以看出您将温度、压力等高基数值保留为标记值。这些值应该保留为字段。
通过将这些值保留为标签,influxdb 将为这些值编制索引以加快搜索速度。对于每个标签值,将创建一个单独的系列。随着标签值数量的增加,系列的数量也会增加,导致内存不足错误。
引自 InfluxDB 文档。
Tags containing highly variable information like UUIDs, hashes, and
random strings lead to a large number of series in the database, also
known as high series cardinality. High series cardinality is a primary
driver of high memory usage for many database workloads.
更多详细信息,请参阅用于设计架构的 influxDB 文档。
https://docs.influxdata.com/influxdb/v1.8/concepts/schema_and_data_layout/
我有 node-red-S7PLC link 以 1.5 秒的周期将以下数据推送到 InfluxDB。
msg.payload = {
name: 'PLCTEST',
level1_m: msg.payload.a90, "value payload from PLC passed to influx"
power1: msg.payload.a93,
valvepos_%: msg.payload.a107,
temp1: msg.payload.a111,
washer_acidity: msg.payload.a113,
etc.
}
return msg;
总共 130 个单独的数据点,由二进制状态组成,例如警报、按钮按下和测量(温度、压力、流量...)
作为对数据库写入的压力测试,这已经 运行 一周了。写作似乎很好,但我注意到,如果我在 Grafana 仪表板中从 10 次温度测量和 30 分钟查询 window 切换到 3 小时查询,加载时间开始变得令人讨厌。 12 小时 window 是不行的。我认为这是因为我所有的东西都被推送为字段键和字段值。没有索引,这会使数据库不堪重负。
Grafana 查询检查器每个 measurement_query 给我 1081 行,所以 x10 = 10810 rows/dasboard_query。但整个池涌入必须经过 130 次测量 x 1081 = 140530 行/3 小时 window.
我想获得一些关于如何优化架构的建议。我有以下想法。
数据库:Aplication_nameX
测量值:Process_metrics、
标签:温度、压力、流量、%、液位、酸度、功率
Tag_values:CT-xx1...CT-xxn,CP-xx1...CP-xxn,CF-xx1...CF-xxn,....
字段键=值,字段值=值
测量值:Alarms_On,
Fieldkey=状态,fieldvalue=“真”,“假”
Measurement:Binary_ON
Fieldkey: State, fieldvalue= "true", "false"
这将在几个临时工时处于节点红色(我认为):
msg.payload = [{
Value: msg.payload.xxx, "value payload from PLC passed to influx"
Value: msg.payload.xxx,
Value: msg.payload.xxx
},
{
Temp:"CT_xx1",
Temp:"CT_xx2",
Temp:"CT_xx2"
}];
return msg;
编辑:遵循罗伯茨的评论。
在写这里之前,我在网上阅读了一周的涌入手册和其他示例。一些涌入与正常 SQL 思维定式的不同和独特之处,我确实发现这异常困难。但是周末我确实有一些清晰的时刻。
我觉得下面这样比较合适
DB: Station_name
measurements: Process_metrics,Alarms, Binary.
Tags: "SI_metric"
Values= "Temperature", "Pressure" etc.
Fieldkey: "proces_position"= CT/P/F_xxx.
values= process_values
这应该可以防止基数与我最初的想法相悖。
我认为警报和二进制文件可以只保留为 fieldkey/fieldvalue,将它们分开到自己的测量值应该提供足够的过滤。这些也仅在状态更改时记录,因此与 1s 周期的类似物相比,对数据库的输入要少得多。
按照我原来的 node-red 流程代码,这将转换为批输出功能:
msg.payload = [
{
measurement: "Process_metrics",
fields: {
CT_xx1: msg.payload.xxx,
CT_xx2: msg.payload.xxx,
CT_xx3: msg.payload.xxx
},
tags:{
metric:"temperature"
},
{
measurement: "Process_metrics",
fields: {
CP_xx1: msg.payload.xxx,
CP_xx2: msg.payload.xxx,
CP_xx3: msg.payload.xxx
},
tags:{
metric:"pressure"
},
{
measurement: "Process_metrics",
fields: {
CF_xx1: msg.payload.xxx,
CF_xx2: msg.payload.xxx,
CF_xx3: msg.payload.xxx
},
tags:{
metric:"flow"
},
{
measurement: "Process_metrics",
fields: {
AP_xx1: msg.payload.xxx,
AP_xx2: msg.payload.xxx,
AP_xx3: msg.payload.xxx
},
tags:{
metric:"Pumps"
},
{
measurement: "Binary_states",
fields: {
Binary1: msg.payload.xxx,
Binary2: msg.payload.xxx,
Binary3: msg.payload.xxx
},
{
measurement: "Alarms",
fields: {
Alarm1: msg.payload.xxx,
Alarm2: msg.payload.xxx,
Alarm3: msg.payload.xxx
}
];
return msg;
编辑 2:
测试我的上述想法并进一步完善后的最终想法。
我的第二个想法没有按预期工作。 Grafana 变量的最后一步不起作用,因为流程数据具有字段中所需的信息,而不是标签。这使得 Grafana 方面对从字段到 link 到 grafana 变量下拉列表的 plc 标签名称信息的 rexec 查询感到恼火。因此再次 运行 资源密集型字段查询。
我无意中发现了一个博客 post,内容是关于如何使用 TSDB 理清思路,而上述想法仍然太 SQL 类似于使用 TSDB 处理数据的方法。我进一步改进了数据库结构,我似乎发现了不同步骤(PLC->NodeRed->influxDB->Grafana)中编码时间和数据库查询负载的妥协。从写入和查询压力时的 1gb ram 使用到正常使用测试中的 100-300MB。
目前正在测试中:
Python 脚本,用于将 PLC 端标签和描述从 csv 压缩为 Node-Red 的可复制粘贴格式。从 csv 中提取温度测量值并格式化为 nodered 的示例。
import pandas as pd
from pathlib import Path
file1 = r'C:\Users\....pandastestcsv.csv
df1 = pd.read_csv(file1, sep=';')
dfCT= df1[df1['POS'].str.contains('CT', regex=False, na=False)]
def my_functionCT(x,y):
print( "{measurement:"+'"temperature",'+"fields:{value:msg.payload."+ x +",},tags:{CT:\"" + y +'\",},},' )
result = [my_functionCT(x, y) for x, y in zip(dfCT['ID'], dfCT['POS'])]
此输出是来自 CSV 的所有温度测量值 CT。 {measurement:"temperature",fields:{value:msg.payload.a1,},tags:{CT:"tag description with process position CT_310",},},
此列表可以复制粘贴到 Node-Red 数据link 有效负载到 influxDB。
InfluxDB:
数据库:PLCTEST
测量:温度、压力、流量、泵、阀门、警报,on_off.....
标签键:CT、CP、CF、misc_mes...
标签字段:“标签的 PLC 描述”
字段键:值
字段值:“来自 PLC 有效载荷的过程测量值”
这可以在合理范围内检查每个测量的基数,并且可以更好地针对相关数据进行查询,而无需 运行 通过整个数据库。 Ram 和 CPU 负载现在很小,并且在 Grafana 中从 1h 跳到 12h 查询在几秒钟内加载而没有锁定。
在设计 InfluxDB 测量模式时,我们需要非常小心地选择标签和字段。
每个标签值将创建单独的系列,随着标签值数量的增加,InfluxDB 服务器的内存需求将呈指数增长。
从问题中给出的测量描述中,我可以看出您将温度、压力等高基数值保留为标记值。这些值应该保留为字段。
通过将这些值保留为标签,influxdb 将为这些值编制索引以加快搜索速度。对于每个标签值,将创建一个单独的系列。随着标签值数量的增加,系列的数量也会增加,导致内存不足错误。
引自 InfluxDB 文档。
Tags containing highly variable information like UUIDs, hashes, and random strings lead to a large number of series in the database, also known as high series cardinality. High series cardinality is a primary driver of high memory usage for many database workloads.
更多详细信息,请参阅用于设计架构的 influxDB 文档。
https://docs.influxdata.com/influxdb/v1.8/concepts/schema_and_data_layout/