2012-04-05 38 views
11

我想讓我的shell檢測人類行爲,然後顯示提示。在bash中檢查isatty

因此,假設文件名是test.bash

#!/bin/bash 
if [ "x" != "${PS1:-x}" ] ;then 
read -p "remove test.log Yes/No" x 
[ "$x" = "n" ] && exit 1 
fi 
rm -f test.log 

但是,我發現,如果我沒有設置PS1它不能正常工作。有更好的方法嗎?

我的測試方法:

./test.bash     # human interactive 
./test.bash > /tmp/test.log # stdout in batch mode 
ls | ./test.bash    # stdin in batch mode 

回答

28

闡述,我會嘗試

if [ -t 0 ] ; then 
    # this shell has a std-input, so we're not in batch mode 
    ..... 
else 
    # we're in batch mode 

    .... 
fi 

我希望這有助於。

+3

您的示例適用於** stdin **的情況,對於** stdout **,我們可以使用'if [-t 1]'。如果[-t 0] && [-t 1]' – 2012-08-21 01:49:36

+1

。這似乎是一個好主意。有時少就是更多,有時少就是少。所以......這是一個我不知道的shell腳本的新範例,還是您的個人意見?祝你們好運。 – 2012-08-21 01:55:51

+0

感謝您的分享,最好的答案是 – shellter 2012-08-21 02:52:31

7

help test

-t FD   True if FD is opened on a terminal. 
+0

謝謝,你的回答是正確的,但下一個答案更清晰。 – 2012-08-21 01:44:04

5

你可以利用/usr/bin/tty方案:

if tty -s 
then 
    # ... 
fi 

我承認我不確定它是如何移植的,但它至少是GNU coreutils的一部分。

+0

根據[this](http://pubs.opengroup.org/onlinepubs/9699919799/utilities/tty.html),'tty'可能不支持'-s'選項。所以要麼使用'[-t N]',要麼將輸出重定向到'/ dev/null'。 – 2016-11-16 23:25:49

+0

而且,如果你想檢查stdout,而不是stdin,請執行'tty 2016-11-16 23:27:04

2

請注意,這是沒有必要使用仡&&||外殼運營兩個獨立的運行結合[命令,因爲[命令有其自己的內置-a-o運算符讓你將幾個簡單的測試組合成一個結果。

所以,這裏是你如何可以實現你要的測試 - 採用[一個調用 - 在這裏你翻轉到如果要麼輸入輸出已經從TTY重定向離開批處理模式:

if [ -t 0 -a -t 1 ] 
then 
    echo Interactive mode 
else 
    echo Batch mode 
fi 
+0

Shellcheck說'[a] && [b]'比'[a -ab]'更便於攜帶,不過。 – bacondropped 2016-09-03 20:25:44

+0

(如果你對細節感興趣,下面給出它的信息:'SC2166:由於[p -a q]沒有很好的定義,所以首選[p] && [q] – bacondropped 2016-09-03 20:31:53