管道输出从命令到另一个命令
Pipe output from command to another command
bash 函数 prepend_line
有两个参数:一个字符串和一个文件的完全限定路径。它用于记录,插入当前 date/time 和日志文件顶部的字符串。
独立使用效果很好:prepend_line "test string" "$log_file"
如何获取命令的输出,例如mv -fv "$fileOne" "$fileTwo"
用作 prepend_line
?
的第一个参数
我已经尝试了各种管道组合到 xargs
,但我不明白它是如何工作的,而且我不相信它是无论如何最好的方法。
如果你真的需要:
export -f prepend_line
mv -fv "$fileOne" "$fileTwo" |
xargs -0 bash -c 'prepend_line "" "$log_file"' --
-0
将该行解析为以零分隔的蜜蜂。由于 mv -v
输出中不应该有零,因为文件名不能有零字节,所以你只会得到一个元素。这个 element/line 将作为第一个参数传递给 bash 子 shell。
测试:
prepend_line() {
printf "%s\n" "$@" | xxd -p
}
fileOne=$'1\x01\x02\x031234566\n\t\e'
fileTwo=$'2\x01\x02\x031234566\n\t\e \n\n\n'
export -f prepend_line
printf "%s\n" "$fileOne -> $fileTwo" |
xargs -0 bash -c 'prepend_line "" "$log_file"' --
脚本会输出(从xxd -p
里面的prepend_line
输出):
31010203313233343536360a091b202d3e2032010203313233343536360a
091b200a0a0a0a0a0a
相同的十六进制输出,带有一些额外的换行符和注释:
# first filename $'1\x01\x02\x031234566\n\t\e'
31010203313233343536360a091b
# the string: space + '->' + space
202d3e20
# second filename $'2\x01\x02\x031234566\n\t\e \n\n\n'
32010203313233343536360a091b200a0a0a0a0a0a
如果您真的需要解析一些奇怪的输入,您可以使用 xxd -p
将您的字符串转换为十六进制。然后,稍后,使用 xxd -r -p
将其转换回机器表示并直接流式传输到输出中:
prepend_line() {
# some work
# append the output of the "" command to the log_file
<<<"" xxd -p -r >> ""
# some other work
}
prepend_line "$(mv -fv "$fileOne" "$fileTwo" | xxd -p)" "$log_file"
但我怀疑您是否需要处理此类情况。谁使用 $'\x01'
和带有空换行符的后缀命名文件名 'great_script.sh'$'\n\n'
?
无论如何,客观上我更愿意将界面视为使用流:
mv -fv "$fileOne" "$fileTwo" | prepend_line "$log_file"
需要 set -o pipefail
才能正确传播错误。在 prepend_line
内部,我只是将输出重定向到日志文件或一些临时文件,省去了解析和特殊情况的需要。
bash 函数 prepend_line
有两个参数:一个字符串和一个文件的完全限定路径。它用于记录,插入当前 date/time 和日志文件顶部的字符串。
独立使用效果很好:prepend_line "test string" "$log_file"
如何获取命令的输出,例如mv -fv "$fileOne" "$fileTwo"
用作 prepend_line
?
我已经尝试了各种管道组合到 xargs
,但我不明白它是如何工作的,而且我不相信它是无论如何最好的方法。
如果你真的需要:
export -f prepend_line
mv -fv "$fileOne" "$fileTwo" |
xargs -0 bash -c 'prepend_line "" "$log_file"' --
-0
将该行解析为以零分隔的蜜蜂。由于 mv -v
输出中不应该有零,因为文件名不能有零字节,所以你只会得到一个元素。这个 element/line 将作为第一个参数传递给 bash 子 shell。
测试:
prepend_line() {
printf "%s\n" "$@" | xxd -p
}
fileOne=$'1\x01\x02\x031234566\n\t\e'
fileTwo=$'2\x01\x02\x031234566\n\t\e \n\n\n'
export -f prepend_line
printf "%s\n" "$fileOne -> $fileTwo" |
xargs -0 bash -c 'prepend_line "" "$log_file"' --
脚本会输出(从xxd -p
里面的prepend_line
输出):
31010203313233343536360a091b202d3e2032010203313233343536360a
091b200a0a0a0a0a0a
相同的十六进制输出,带有一些额外的换行符和注释:
# first filename $'1\x01\x02\x031234566\n\t\e'
31010203313233343536360a091b
# the string: space + '->' + space
202d3e20
# second filename $'2\x01\x02\x031234566\n\t\e \n\n\n'
32010203313233343536360a091b200a0a0a0a0a0a
如果您真的需要解析一些奇怪的输入,您可以使用 xxd -p
将您的字符串转换为十六进制。然后,稍后,使用 xxd -r -p
将其转换回机器表示并直接流式传输到输出中:
prepend_line() {
# some work
# append the output of the "" command to the log_file
<<<"" xxd -p -r >> ""
# some other work
}
prepend_line "$(mv -fv "$fileOne" "$fileTwo" | xxd -p)" "$log_file"
但我怀疑您是否需要处理此类情况。谁使用 $'\x01'
和带有空换行符的后缀命名文件名 'great_script.sh'$'\n\n'
?
无论如何,客观上我更愿意将界面视为使用流:
mv -fv "$fileOne" "$fileTwo" | prepend_line "$log_file"
需要 set -o pipefail
才能正确传播错误。在 prepend_line
内部,我只是将输出重定向到日志文件或一些临时文件,省去了解析和特殊情况的需要。