我有一种生产者-消费者设置,在这种设置中,生产者(不同线程上的多个生产者)将数据排到redis队列中,而使用者(单线程上的单个使用者)监视这个队列。当队列长度达到(例如>= 10000项)时,使用者应该从队列中提取前10000项,从队列中删除它们并对其进行某种类型的计算。
使用redis-py客户端,我使用以下代码提取前10000项,并删除它们:
logs = REDIS_CLIENT.lrange(task_queue, 0, 9999)
REDIS_CLIENT.ltrim(task_queue, start=10000, end=REDIS_CLIENT.llen(task_queue))我的问题是,这里有丢失数据的机会吗?例如,任务是否有可能在调用函数ltrim()和队列实际被修剪之间的时间内排队(在这种情况下,最新的日志将丢失,因为end的值将是较旧的长度)?或者是将锁放置在队列上,直到ltrim操作完成?
发布于 2020-05-25 10:09:49
是的,您可能会丢失数据,因为ltrim和llen之间有一个时间窗口。
为了关闭该时间窗口,可以将-1设置为结束偏移量:
REDIS_CLIENT.ltrim(task_queue, start=10000, end=-1)-1意味着列表的结束,并且不需要显式地指定结束偏移量。
https://stackoverflow.com/questions/61999288
复制相似问题