2

У меня есть сценарий, где я хочу фильтровать файлы журналов. Чтобы сделать это, я хочу следовать последним примерно 10 строкам файла журнала и, когда новые строки считываются, передать их через программу awk, а затем перенаправить вывод на порт прослушивания на удаленном хосте через netcat.

В настоящее время мой скрипт содержит следующую строку:

echo "\`awk -f rules.awk <(tail -F $@)\`" | nc -u 127.0.0.1 5004

Где $@ - это список аргументов, предоставленных в начальном вызове, а rules.awk просто содержит некоторые желаемые шаблоны для сопоставления.

Вызов скрипта с помощью ./script logfile.log похоже, ничего не делает, и скрипт зависает. Я предполагаю, что канал на самом деле требует завершения процесса до того, как его окончательный вывод будет передан новой команде.

Поэтому я попробовал другой подход, запустив следующее в моем терминале:

nc -u 127.0.0.1 5004 <(awk -f rules.awk <(tail -F logfile.log))

Это привело к следующей ошибке:

Invalid port specification: /dev/fd/63

Похоже, что перенаправление фактически прошло логическое устройство потока, а не его «значение», но я просто еще раз угадать.

Может ли кто-то с немного большим количеством BASH Nous указать мне в правильном направлении с этим?

2 ответа2

1

Файловые дескрипторы немного сбивают с толку, они, безусловно, более запутанные, чем каналы. Поэтому, прежде чем пытаться перенаправить вывод подоболочки (<()) как стандартный ввод команды, попробуйте получить то, что вам нужно, с помощью каналов. Кроме того, это может помочь заставить команды вывода работать правильно перед отправкой ввода целевой команде (nc).

cat <(tail -F /var/log/daemon.log ) | cat -n | awk 'NR>3 { print}'

это эквивалентно

tail -F /var/log/daemon.log | cat -n | awk 'NR>3 {print}';

но "лучше", поскольку он не опирается на специфичный для bash синтаксис `<()'

0

Оффханд, кажется, это должно работать для меня

tail -F $@ | awk -f rules.awk | nc -u 127.0.0.1 5004

Всё ещё ищете ответ? Посмотрите другие вопросы с метками .