Как передать вывод активного потока другим командам

2

Я пытаюсь передать активный поток другой команде (возможно, bash-скрипту), но он всегда хочет дождаться завершения всего потока, прежде чем обработает команду. С.Г. Я могу сделать это:

tail file.log | grep keyword | xargs -L 1 echo ...

и он правильно выводит совпадающие строки из файла file.log, которому предшествует «...». Очевидно, я не хочу просто повторять, это просто для упрощения примера (я бы заменил его на собственный скрипт bash). Теперь, когда я пытаюсь это:

tail -f file.log | grep keyword

это работает, то есть выводит совпадающие строки, затем делает паузу до изменения file.log, затем выводит любые новые совпадающие строки. Однако, если я попробую это:

tail -f file.log | grep keyword | xargs -L 1 echo ...

Он ничего не выводит - я полагаю, он ожидает окончания потока, открытого tail -f. Я попробовал это также:

tail -f file.log | grep keyword | while read line; do echo...$line; end

без изменений в поведении. Я читал на другие вопросы здесь, что это должно работать. Я использую Ubuntu 14.04, есть ли какая-то разница из-за этого? Как я могу заставить это работать?

lalitm
источник

Ответы:

1

Вы правы, xargs ожидает ввода от стандартного ввода, следовательно, он ожидает окончания потока. Один из способов заставить это работать с помощью процесс замены , так как ...

Подстановка процесса - это форма перенаправления, в которой ввод или вывод процесса (некоторая последовательность команд) отображается как временный файл.

Итак, вы должны попробовать:

while IFS= read -r newline; do echo $newline | grep keyword | cat >> filename  ; done < <(tail -f file.log)

который обходится без xargs в целом.

MariusMatutiae
источник
Это работает отлично! Я видел синтаксис & lt; & lt; (...) в другом месте, но не понимал, что это значит (или почему пространство в середине было важным). Спасибо за объяснение!
lalitm