在XDEL之后调用XREAD不会阻塞流,但是会立即返回。预期的行为是XREAD再次阻止。
127.0.0.1:6379> XADD my-stream * field1 string1
"1554300150697-0"
127.0.0.1:6379> XREAD BLOCK 5000 STREAMS my-stream 1554300150697-0
(nil)
(5.07s)
127.0.0.1:6379> XADD my-stream * field2 string2
"1554300285984-0"
127.0.0.1:6379> XREAD BLOCK 5000 STREAMS my-stream 1554300150697-0
1) 1) "my-stream"
2) 1) 1) "1554300285984-0"
2) 1) "field2"
2) "string2"
127.0.0.1:6379> XDEL my-stream 1554300285984-0
(integer) 1
127.0.0.1:6379> XLEN my-stream
(integer) 1
127.0.0.1:6379> XREAD BLOCK 5000 STREAMS my-stream 1554300150697-0
1) 1) "my-stream"
2) (empty list or set)
127.0.0.1:6379>
如您在上面看到的,第一次调用XREAD会阻塞5秒-预期。
对XREAD的第二次调用将立即返回,并给出新的条目-预期。
对XREAD的第三次调用立即返回(empty list or set)
-不可预期!
预期:命令应阻塞5秒钟。
我不确定这是一个错误还是我错过了某些东西。请告知。
谢谢
答案 0 :(得分:0)
您似乎遇到了this known bug。
请特别参阅第二条评论,该注释指出所提供的部分修复不能解决您遇到的问题:
这不是针对阻塞问题的完整解决方案,因为它仅解决了空流的阻塞行为。
如果流中仍然包含某些条目,但是所有ID的ID都比last-received-id参数所请求的ID大,则该请求仍将以空结果列表进行同步答复。
答案 1 :(得分:0)
通过5.0.4的源代码,我找到了一种通过未记录的命令->last_id
XSETID
成员的方法。
尽管在源代码https://github.com/antirez/redis/blob/f72f4ea311d31f7ce209218a96afb97490971d39/src/t_stream.c#L1837中它表示语法为XSETID <stream> <groupname> <id>
,但实际上是XSETID <stream> <id>
(关于此语法有一个开放的问题:https://github.com/antirez/redis/issues/5519,但我希望他们会为组添加一个新命令,例如XGROUPSETID
,并按原样保留该命令),这正是我想要的,所以这样做:
XSETID my-stream 1554300150697-0
会做:
127.0.0.1:6379> XREAD BLOCK 5000 STREAMS my-stream 1554300150697-0
(nil)
(5.08s)
127.0.0.1:6379>
正常工作-它会阻塞。
对于使用此解决方案的任何人(我认为这更像是一种解决方法):请谨慎使用,因为在高吞吐量的机器/系统/环境中,Redis可以使用以下命令生成/添加新的
my-stream
条目与已删除的1554300285984-0
相同的ID,导致客户端可能重复的数据。