2015-07-16 2 views
1

Мне нужно выполнить команду в сценарии bash.Как узнать, был ли вывод отправлен в stderr

Если команда выходит с кодом выхода! = 0 и/или записывает в stderr, произошел сбой, который должен быть обработан.

Первое условие прост. Но как узнать, был ли вывод на stderr? Я не хочу перехватывать или захватывать вывод (если нет другого пути), мне просто нужно знать , если был какой-то.

+1

Я не думаю, что есть какой-либо способ, если сама команда ничего не сообщит. Захват stderr и проверка того, есть ли что-то, легки, и я не совсем уверен, почему вы хотите сделать это, как обычно, можно было бы * захватить * либо или и то, и другое. Не просто проверить, есть ли что-то в ошибке. Кроме того, команда может также выводить предупреждающие сообщения на stderr. Таким образом, надежный способ проверки * сбоя * заключается в использовании кода возврата. –

+0

Если в любом случае был разумный код возврата, вы были правы; к сожалению, это не так. Но комбинация кода stderr и возврата дает нам правильный результат. – wonk0

+0

Код выхода можно получить из '$?'. Что касается 'stderr', я не уверен, что его можно проверить или, возможно, вам нужно записать во временный файл – krato

ответ

0

Вы можете сделать это, отметив, что дескрипторы файлов процесса выставлены в/proc/. Например, если вы

$ ls -l /proc/self/fd/2 
lrwx------ 1 meuh meuh 64 Jul 16 10:06 /proc/self/fd/2 -> /dev/pts/2 

в XTerm или подобное, вы можете увидеть, что STDERR для себя, Баш, является псевдотерминал. Следуйте симлинк в ls, чтобы получить реальное время последней модификации PTY:

$ ls -lL /proc/self/fd/2 
crw--w---- 1 meuh tty 136, 2 Jul 16 10:05 /proc/self/fd/2 

Лучше команда использования является стат, которая дает лучшее разрешение по времени.

$ stat -L -c %y /proc/self/fd/2 
2015-07-16 10:03:54.553125813 

Так просто сохранить метку времени перед вашей командой, и сравнить его после команды , чтобы увидеть, если она отличается.

before=$(stat -L -c %y /proc/self/fd/2) 
if mycommand && 
after=$(stat -L -c %y /proc/self/fd/2) && 
[ "$after" = "$before" ] 
then echo 'command ok' 
else echo 'command fail' 
fi 
+0

Это будет работать только в Linux. Например, в OS X нет '/ proc', в UNIX, которые поддерживают'/proc', макет отличается. 'stat (1)' также является специфичным для GNU. – cdarke

+0

Это решает мою проблему, спасибо вам большое. Это не переносимо, но это не важно для моей конкретной цели. – wonk0

0

Предложение: «tee» stderr во временный файл и проверить, имеет ли этот файл ненулевой размер в конце команды.