Shebang多个参数

时间:2017-08-10 11:35:02

标签: linux shell awk shebang

我目前正在编写一个awk脚本,如下所示:

#!/usr/bin/awk -f
BEGIN {
    print "Starting extracting data"
}
{
    print $0
}
END {
    print "End of file"
}

我的脚本在我的计算机上工作得很好,但它不便携......我想做类似的事情

#!/usr/bin/env awk -f
...

但Debian shell不接受单个shebang中的几个参数。我得到"awk -f" no such file or directory。我可以使用任何解决方法,还是完全不可能?

2 个答案:

答案 0 :(得分:0)

没有简单的方法可以干净利落地做到这一点;如glenn jackman's comment中所述,shebangs由execve()实现,只接受解释器和单个可选参数。

您需要一种解决方法。

对问题的评论暗示你不需要包装器脚本,但如果它包含在最终的~awk脚本中会怎样?

#!/bin/sh
awk -f - "$@" << 'EOF'
#!/usr/bin/awk -f

BEGIN {
    print "Starting extracting data"
}
{
    print $0
}
END {
    print "End of file"
}

这在shebang中使用了可移植的POSIX shell,然后在标准输入(-f -)上使用heredoc的awk代码立即调用awk,并传递其他参数和选项("$@") awk as files。引用了heredoc(<< 'EOF'),因此$0之类的东西不会被POSIX shell解释。由于不存在仅由EOF组成的行,因此heredoc以文件结束。

(第二个shebang没有被任何东西阅读。对于阅读代码的人来说,这纯粹是装饰性的。如果你用.awk后缀命名这个文件,像vim这样的编辑将默认他们的语法突出显示为awk尽管第一个shebang的内容。)

该代码不适用于将内容传递到文件中,因为脚本本身已通过管道输入awk。如果你想支持管道,使用bash的输入process substitution<(…)),它需要更加丑陋:

#!/bin/bash
exec awk -f <(awk 'NR > 2' "$0") "$@"
#!/usr/bin/awk -f

BEGIN {
    print "Starting extracting data"
}
{
    print $0
}
END {
    print "End of file"
}

这告诉bash在从第二个awk命令创建的命名管道上执行awk,该命令读取完整脚本(bash将$0解释为它正在运行的文件的名称)并打印第3行和更高行。同样,第二个shebang纯粹是装饰性的,因此只是一个评论。

答案 1 :(得分:0)

没有理由在shebang中调用awk。只需通过sh:

调用它
#!/bin/sh
exec awk '
BEGIN {
    print "Starting extracting data"
}
{
    print $0
}
END {
    print "End of file"
}
' "$@"