Bash脚本:如何获取运行脚本

时间:2015-05-19 10:07:27

标签: bash io-redirection

我想运行一个bash脚本,并能够看到用于启动它的命令行:

sh myscript.sh arg1 arg2 1> output 2> error

以便了解用户是否使用了" 标准重定向" &#39 1为卤素;'和' 2>',因此调整我的脚本的输出。

是否可以使用内置变量?

感谢。

2 个答案:

答案 0 :(得分:2)

不太可能。您可以检查stdoutstderr是否指向终端:[ -t 1 -a -t 2 ]。但如果他们这样做,并不一定意味着他们没有重定向(想想>/dev/tty5)。如果他们不这样做,则无法区分stdoutstderr被关闭以及被重定向。即使你确定 被重定向,你也无法从脚本本身告诉他们在重定向后指向的位置。

答案 1 :(得分:2)

在Linux和一些类似unix的系统上,/proc/self/fd/1/proc/self/fd/2 std重定向所指向的符号链接。使用readlink,我们可以通过将它们与父进程进行比较来查询它们是否被重定向。文件描述符。

但我们不会使用self而是使用$$,因为$(readlink /proc/"$$"/fd/1)会生成一个新的shell,因此self不再引用当前的bash脚本而是引用子shell。

$ cat test.sh
#!/usr/bin/env bash

#errRedirected=false
#outRedirected=false
parentStderr=$(readlink /proc/"$PPID"/fd/2)
currentStderr=$(readlink /proc/"$$"/fd/2)
parentStdout=$(readlink /proc/"$PPID"/fd/1)
currentStdout=$(readlink /proc/"$$"/fd/1)
[[ "$parentStderr" == "$currentStderr" ]] || errRedirected=true
[[ "$parentStdout" == "$currentStdout" ]] || outRedirected=true

echo "$0 ${outRedirected:+>$currentStdout }${errRedirected:+2>$currentStderr }$@"

$ ./test.sh
./test.sh

$ ./test.sh 2>/dev/null
./test.sh 2>/dev/null

$ ./test.sh arg1 2>/dev/null # You will lose the argument order!
./test.sh 2>/dev/null arg1

$ ./test.sh arg1 2>/dev/null >file ; cat file
./test.sh >/home/camusensei/file 2>/dev/null arg1

$

不要忘记用户还可以重定向到 3rd 文件描述符,该描述符在其他内容上打开...!