数据写入数据库时​​丢失数据

Missing data while data writing to the database

我有一个每秒向 InfluxDB 写入数据的程序,我发现了一些错误。有时数据库中会丢失一秒钟。它不是经常丢失数据,而是每 1 分钟大约丢失一秒。

我的程序是这样的:

def monitoring():           
try:
    client = InfluxDBClient(host=IpAdress, port="8086", database="DB")
    print("Connected to InfluxDB")      
except:
    print('{} :Can`t connect to the database, with error {}'.format(datetime.now().strftime("%Y-%m-%d %H:%M:%S"), exc_info()[0]))

#=============================================== GPIO ==========================================
GPIO.setwarnings(False)                     # Ignore warning for now
GPIO.setmode(GPIO.BCM)                    # Use physical pin numbering
GPIO.setup(27, GPIO.IN, pull_up_down=GPIO.PUD_DOWN)                 
GPIO.setup(18, GPIO.IN, pull_up_down=GPIO.PUD_DOWN)                 
GPIO.setup(25, GPIO.IN, pull_up_down=GPIO.PUD_DOWN)                
GPIO.setup(12, GPIO.IN, pull_up_down=GPIO.PUD_DOWN)                
GPIO.setup(22, GPIO.IN, pull_up_down=GPIO.PUD_DOWN)                
GPIO.setup(19, GPIO.IN, pull_up_down=GPIO.PUD_DOWN)                 
GPIO.setup(17, GPIO.IN, pull_up_down=GPIO.PUD_DOWN)                 
GPIO.setup(23, GPIO.IN, pull_up_down=GPIO.PUD_DOWN)                
GPIO.setup(24, GPIO.IN, pull_up_down=GPIO.PUD_DOWN)                
GPIO.setup(26, GPIO.IN, pull_up_down=GPIO.PUD_DOWN)                
GPIO.setup(16, GPIO.IN, pull_up_down=GPIO.PUD_DOWN)                
GPIO.setup(20, GPIO.IN, pull_up_down=GPIO.PUD_DOWN)                 
GPIO.setup(21, GPIO.IN, pull_up_down=GPIO.PUD_DOWN)  
last_update = int(time.time())
while True:
    if GPIO.input(27):
        run_01 = 1
    elif GPIO.input(18):
        run_01 = 1
    else:                
        run_01 = 0
#checking all GPIO if they are UP or DOWN
    now_time = int(time.time())
    if last_update < now_time:        
        #===============================================Write_Data==========================================
        json_writer = [ 
            {
                "measurement": "measurement",
                "tags": {
                    "some_tag": "{}".format(some_tag)
                },
                    "time": datetime.now().strftime("%Y-%m-%d %H:%M:%S.%f"), 
                    "fields": {
                        "data_to_DB": data_to_DB
                    }
            }
        ]
        try:
            client.write_points(json_writer)
        except:
            print('{} :Writing data to database error: {}'.format(datetime.now().strftime("%Y-%m-%d %H:%M:%S"), exc_info()[0]))
        last_update = now_time
client.close()

程序 运行 在 Docker 容器内的 Rpi 3 或 Rpi 4 上 Python 3.7.3 和 InfluxDB 1.7.7

我想就这些了,但如果您需要更具体的信息,请写信给我,我会升级我的问题。

你有什么解决这个问题的提示吗?

编辑:

原始时间戳数据,另一列只是一些字符串和 0 或 1:

1580460015000029184
1580460016000039168
1580460017000029184
1580460018000050176
1580460019000039936
1580460020000034048
1580460021000029184
1580460022000039168
1580460023000036864
1580460024000029952
1580460025000036096
1580460026000036096
1580460027000029184
1580460028000050176
1580460029000044032
1580460032878979072
1580460033127377152
1580460034000029184
1580460035000040960
1580460036000046848
1580460037000040960
1580460038000033024
1580460039000033024
1580460040000033024
1580460041000026880
1580460042000040960
1580460043000026112
1580460044000036096
1580460045000039168
1580460046000039936
1580460047000036096
1580460048000043008
1580460049000026880
1580460050000049152
1580460051000032000
1580460052000045056
1580460053000036096
1580460054000039168
1580460055000029952
1580460056000039168
1580460057000033024
1580460058000046848
1580460059000049152
1580460060000035072
1580460061000036096
1580460062000035072
1580460063000039168
1580460064000029952
1580460065000039168
1580460066000039168
1580460067000043008
1580460068000036864
1580460069000049152
1580460070000036096
1580460071000029184
1580460072000040960
1580460073000043008
1580460074000033024

恕我直言 2 values/timestamp 丢失:

1580460029000044032
1580460030...
1580460031...
1580460032878979072

有趣的事实:

  • 有些数据在纳秒级精度上正好有 1 秒的差异(我不相信用户 space 中的 python 可以有这种精度)
1580460038000033024
1580460039000033024
1580460040000033024
  • 毫秒部分通常为000

我会

  • 尝试和 time_precision 一起玩:
client.write_points(json_writer, time_precision=?)
  • 将发布的时间戳与存储的时间戳进行比较
  • 验证丢失的时间戳是否已发布(可能有任务,例如优先级更高的 cron,因此摄取代码的执行只会延迟)- 检查丢失的时间戳中是否存在时间模式

感谢提示。

我试过了你所有的建议。

主要问题是:有时记录需要3秒左右。 通常约为 0.03 秒。

否则,我通过将 client.write_points(json_writer) 移动到另一个线程来解决这个问题。