LinuxForum.Fans
Тема

Мониторинг вывода команд в Less

Автор: SamuelLinux 9 сообщений 2115 просмотров
#178756

Здравствуйте.

Утилита Less позволяет осуществлять наблюдение за файлами в реальном времени. Это реализуется посредством следующей команды:

[console]
 less +F /some/file
[/console]

А возможно ли вместо файла осуществлять мониторинг вывода некоторой команды, пишущей в STDOUT?

Вот пример того, как это должно выглядеть (код нерабочий!):

[console]
 ruby -e 'i = 0; loop { i = i.succ; sleep 1; puts i }' | less +F
[/console]

В этом примере создается канал, в левой части которого выполняется программа на Ruby, последовательно повышающая значение некоторой переменной на единицу и выводящая это значение в STDOUT. В правой части канала запущена утилита Less с ключом +F, и, по идее, она должна считывать стандартный вывод в реальном времени и отображать значения выводимые сценарием Ruby.

Как заставить Less читать стандартный вывод?

Спасибо.

#178762

Ещё раз, более подробно.

В Less'е есть режим мониторинга (less +F или Shift + f в уже запущенной программе). В этом режиме можно наблюдать в реальном времени за изменением некоторого файла. То есть, если какая-то программа пишет что-либо в него, то эти данные сразу же отображаются в запущенном Less'е и становятся доступными для анализа. В любой момент можно нажать Ctrl + c, выйти из режима мониторинга, просмотреть весь файл, прокручивая его по необходимости вверх и вниз, а затем снова нажать Sift + f и продолжить наблюдение.

Многие программы осуществляют непрерывный вывод в STDOUT и в некоторых случаях было бы удобно этот вывод перенаправлять в Less, который запущен в режиме мониторинга и работать с поступающими данными так, как я описал выше.

Вот этого я и хочу добиться.

#178764
SamuelLinux написал:
Многие программы осуществляют непрерывный вывод в STDOUT и в некоторых случаях было бы удобно этот вывод перенаправлять в Less, который работает в режиме мониторинга и работать с поступающими данными так, как я описал выше.

это невозможно.

причина в том, что stdout не является обычным файлом, это fifo.

Показать
A FIFO special file (a named pipe) is similar to a pipe, except that it is accessed as part of the file
system. It can be opened by multiple processes for reading or writing. When processes are exchanging
data via the FIFO, the kernel passes all data internally without writing it to the file system. Thus, the
FIFO special file has no contents on the file system; the file system entry merely serves as a reference
point so that processes can access the pipe using a name in the file system.

The kernel maintains exactly one pipe object for each FIFO special file that is opened by at least one
process. The FIFO must be opened on both ends (reading and writing) before data can be passed. Normally,
opening the FIFO blocks until the other end is opened also.

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

less позволяет возвращаться на любое количество символов назад, потому и режим работы с fifo там не реализован.

Вы можете либо создать обычный файл (например в памяти), либо использовать tail -f.

#178782

Здравствуйте, DrBatty.


less позволяет возвращаться на любое количество символов назад, потому и режим работы с fifo там не реализован.

Вот пример:

1.
[console]
$ mkfifo /tmp/my_fifo
[/console]

2.
[console]
 less -f +F /tmp/my_fifo
[/console]

3.
[console]
$ ruby -e "100.times { |i| sleep 1; File.open('/tmp/my_fifo', 'w+') { |f| f.puts i } }"
[/console]

4.
[console]

0
1
2
3
4
<...>
99
[/console]

Есть две консоли. В первой консоли создается именованный канал (1). Во второй консоли запускается Less в режиме наблюдения с форсированным открытием FIFO-файла (2). В первой консоли запускается программа на Ruby, которая последовательно печатает числа в именованный канал с интервалом в одну секунду (3). По мере работы этой программы, во второй консоли начинают отображаться выводимые числа (4). Можно в любой момент выйти из режима мониторинга, просмотреть выведенные данные, используя прокрутку, и без проблем вернуться в исходный режим.

Похоже, дело вовсе не в FIFO.

#178794
SamuelLinux написал:
Похоже, дело вовсе не в FIFO.

в них...

просто:

NOTES
The stream stderr is unbuffered. The stream stdout is line-buffered when it points to a terminal. Par‐
tial lines will not appear until fflush(3) or exit(3) is called, or a newline is printed. This can pro‐
duce unexpected results, especially with debugging output. The buffering mode of the standard streams (or
any other stream) can be changed using the setbuf(3) or setvbuf(3) call. Note that in case stdin is asso‐
ciated with a terminal, there may also be input buffering in the terminal driver, entirely unrelated to
stdio buffering. (Indeed, normally terminal input is line buffered in the kernel.) This kernel input
handling can be modified using calls like tcsetattr(3); see also stty(1), and termios(3).

Как видим, stderr вообще не буферезирован, а stdout не буферезирован в вашем случае. Потому-то и откат невозможен. Ну а mkfifo создаёт буферезированные fifo...

less в таком случае сама должна буферезировать поток, создавая например mkfifo.

SamuelLinux написал:
По мере работы этой программы, во второй консоли начинают отображаться выводимые числа (4). Можно в любой момент выйти из режима мониторинга, просмотреть выведенные данные, используя прокрутку, и без проблем вернуться в исходный режим.

Разве это не решение? Создаёте FIFO, и заварачиваете туда stdout, а читаете этот fifo командой less. smile

ЗЫЖ SamuelLinux, И вам не болеть wink

#178799


Разве это не решение?

Нет, к сожалению. Нужна только одна консоль, а здесь требуется целых две.

#178804
SamuelLinux написал:
Нет, к сожалению. Нужна только одна консоль, а здесь требуется целых две.

зачем? просто саму команду в бекграунде запускаете...

text
ruby -e "100.times { |i| sleep 1; File.open('/tmp/my_fifo', 'w+') { |f| f.puts i } }" & less -f +F /tmp/my_fifo

странно... почему-то так не работает:

text
ruby -e 'i = 0; loop { i = i.succ; sleep 1; puts i }'  >/tmp/my_fifo & less -f +F /tmp/my_fifo
#178838
SamuelLinux написал:
Нет, к сожалению. Нужна только одна консоль, а здесь требуется целых две.

почему именно две? лениво писать пример, но я уверен, что это сработает.

#178848

В общем-то ответ на интересующий меня вопрос я получил.

SamuelLinux написал:

Как заставить Less читать стандартный вывод?
drBatty написал:

это невозможно.

Да, можно использовать файлы или FIFO-файлы как посредников между процессами, но меня в этом качестве интересовал именно стандартный вывод.

Fat-Zer, drBatty, спасибо за ваши ответы и внимание к этому топику.

Войдите или зарегистрируйтесь, чтобы ответить.