inotify + stdout piping - 输出在管道中丢失

时间:2015-01-27 16:24:14

标签: linux shell buffering

我有一些用于inotify的单行生成事件。

while true; do for i in $(seq 1 100); do touch /tmp/ino/foo$i; sleep 1s; done; rm /tmp/ino/foo*; done

然后我设置了一个小的bash管道来观察该文件夹,忽略了有关ISDIR的事件(也许我可以用inotifywait做到这一点,但那不相关):

inotifywait -m -e close /tmp/ino 2>/dev/null | grep -v ISDIR

这很好用,我看到像/tmp/ino/ CLOSE_WRITE,CLOSE foo57这样的行。

但如果我在最后添加一个额外的管道,我就不会得到任何输出。为了简单起见,让我们使用grep pattern是幂等的事实。

inotifywait -m -e close /tmp/ino 2>/dev/null | grep -v ISDIR | grep -v ISDIR

这会产生 no 输出。我知道我的生成器仍在运行,另一个终端中的无管inotifywait -m -e close /tmp/ino仍在生成输出。

经过一番思考,我认为这可能是一个缓冲问题(这样的问题似乎经常出现)。我将管道改为

inotifywait -m -e close /tmp/ino 2>/dev/null | grep -v ISDIR --line-buffered | grep -v ISDIR

现在我再次获得输出,以便解决问题。

然而,我并不真正理解为什么在没有强制行缓冲的情况下它无法工作。我从来没有遇到像grep这样的问题,即使是“慢生产”这样的问题。输出。 但是,管道中的其他一些程序强制sedsed -u,并强制我在每个fflush()语句的末尾添加awk

那么,在这里强制进行奇怪的缓冲是什么,以及如何解决它(不必在寻找深奥的力线缓冲命令的手册页中拼抢)?

1 个答案:

答案 0 :(得分:1)

inotifywait可能正在缓冲。我建议使用stdbuf

stdbuf -oL inotifywait -m -e close /tmp/ino 2>/dev/null | grep ...