我想找出一种方法来访问描述当前命令运行之前运行的命令的字符串。
例如,如果我运行:
ls | myscripthere
我希望能够知道“ls”命令是生成我通过 STDIN 获得的输出的命令。有什么办法可以做到这一点吗?
谢谢
答案1
管道接收端的程序实际上没有办法知道传入数据的来源是什么。使用你的例子:
$ ls | myscript
的标准输出ls
将被重定向到 的标准输入myscript
。然而,这与以下内容完全没有区别:
$ ls > datafile
$ myscript < datafile
或者
$ ls > datafile
$ cat datafile | myscript
或者
$ wget -o - https://www.example.com/some/file/that/resembles/the/output/of/ls | myscript
或者
$ ls | sed '/secrethiddenfile/d' | myscript
甚至
$ cat - | myscript
文字只是文字。
答案2
你可以这样做:
echo 'ls' | read var;echo $var > var_file;$var | myscript
它将把命令的值写入文件中var_file
。
echo 'ls'
将ls
作为字符串输入给出,并且 的值var
将变为ls
。$var
将扩展为ls
并将其输出通过管道提供给myscript
。
如果您有多个命令并希望在 中逐行获取它们var_file
,则替换>
为>>
ie:
echo 'ls' | read var;echo $var >> var_file;$var | myscript
答案3
一般来说,这是不可能的,因为:
管道中的每个命令都在其自己的子 shell 中执行
(来自bash手册)。
如果发送命令持续的时间足够长,您就有机会找到它。下面是一个“接收者”脚本示例;它从中获取lsof
与接收器的 stdin 相对应的NODE 列,然后lsof
在更广泛的输出中搜索 stdout NODE 匹配的进程:
#!/bin/sh
# look for f0 and get its node
node=$(lsof -p "$$" -Ffi | awk '/^p/ { node=""; } /^f0$/ { getline; node=substr($0, 2); exit; } END { print node }')
# run lsof and get the pid(s) with f1 whose node match $node
lsof -Ffci | awk -v node="$node" '
/^c/ { procname=substr($0, 2); }
/^f1$/ { getline; thisnode=substr($0, 2); }
/^p/ { if (procname != "" && thisnode == node) { print procname; procname=""; thisnode=""; } }
END { if (procname != ""&& thisnode == node) print procname; }
'
cat
答案4
我在我的程序中使用这个函数.bash_aliases
来提供一个类似于 Tee 的工具:
function teee {
#This can be used between pipes to print on screen what is coming in from the left command and flows to the next command
v="$(</dev/stdin)";
echo '---------------- pipe entry-------------' >/dev/tty;
while read -r l;do
echo "$l" >/dev/tty;
done <<<"$v";
echo '---------------- pipe exit-------------' >/dev/tty;
echo "$v"; ##echo to pipe buffer - necessary to keep the data flow to the next command
}
测试:
cat file11
1
2
3
8
9
cat file11 |sed 's/3//' |teee |sed 's/1//'
---------------- pipe entry-------------
1
2
8
9
---------------- pipe exit-------------
2
8
9
在您的情况下,您可以将所有内容替换>/dev/tty
为>logfile
脚本内的内容。