#bash #shell #zsh
#bash #оболочка #zsh
Вопрос:
Я знаю, что для bash и zsh можно использовать, например [ -t 1 ]
, для определения, является ли STDIN интерактивным сеансом tty.
Однако, похоже, нет способа проверить, перенаправляется ли stdin из файла или передается из команды:
foo < ./file
bar | foo
Есть ли какой-либо способ определить разницу между этими двумя? Отдельно, есть ли какой-либо способ получить путь к перенаправляемому файлу (за пределами /proc/self, который недоступен в macOS)?
Комментарии:
1. Какого ответа вы ожидаете, если ./file является именованным каналом?
Ответ №1:
Вы можете проверить, является ли /dev/stdin
это обычным файлом или каналом:
$ cat tmp.sh
#!/bin/bash
if [ -f /dev/stdin ]; then
echo "file"
elif [ -p /dev/stdin ]; then
echo "pipe"
fi
$ bash tmp.sh < foo.txt
file
$ echo foo | bash tmp.sh
pipe
Однако это зависит от /dev/stdin
наличия в вашей файловой системе.
Вы также можете использовать stat
команду, которая вернет информацию о стандартном вводе без указания аргумента имени файла. Как вы упомянули, что используете macOS, вы можете использовать %HT
формат:
$ stat -f %HT
Character Device
$ stat -f %HT < foo.txt
Regular File
$ echo foo | stat -f %HT
Fifo File
Комментарии:
1. «Bash обрабатывает несколько имен файлов, особенно когда они используются при перенаправлениях», включая /dev/stdin
2.
-f /dev/stdin
однако это не перенаправление.