IBP*_*BPX 31 bash spaces heredoc indentation
对于我所从事的个人开发和项目,我们使用四个空格而不是制表符.但是,我需要使用heredoc,我不能在不打破缩进流的情况下这样做.
我能想到的唯一可行的方法是:
usage() {
cat << ' EOF' | sed -e 's/^ //';
Hello, this is a cool program.
This should get unindented.
This code should stay indented:
something() {
echo It works, yo!;
}
That's all.
EOF
}
Run Code Online (Sandbox Code Playgroud)
有一个更好的方法吗?
如果这属于Unix/Linux Stack Exchange,请告诉我.
che*_*ner 40
(如果你使用bash4,滚动到最后我认为是纯shell和可读性的最佳组合.)
对于shell脚本,使用选项卡不是首选项或样式; 这就是语言的定义方式.
usage () {
?# Lines between EOF are each indented with the same number of tabs
?# Spaces can follow the tabs for in-document indentation
?cat <<-EOF
??Hello, this is a cool program.
??This should get unindented.
??This code should stay indented:
?? something() {
?? echo It works, yo!;
?? }
??That's all.
?EOF
}
Run Code Online (Sandbox Code Playgroud)
另一种选择是完全避免使用此处的文档,代价是必须使用更多的引号和行继续:
usage () {
printf '%s\n' \
"Hello, this is a cool program." \
"This should get unindented." \
"This code should stay indented:" \
" something() {" \
" echo It works, yo!" \
" }" \
"That's all."
}
Run Code Online (Sandbox Code Playgroud)
如果您愿意放弃POSIX兼容性,则可以使用数组来避免显式行继续:
usage () {
message=(
"Hello, this is a cool program."
"This should get unindented."
"This code should stay indented:"
" something() {"
" echo It works, yo!"
" }"
"That's all."
)
printf '%s\n' "${message[@]}"
}
Run Code Online (Sandbox Code Playgroud)
下面再次使用here文档,但这次使用bash4的readarray命令来填充数组.参数扩展负责从每个谎言的开头移除固定数量的空格.
usage () {
# No tabs necessary!
readarray message <<' EOF'
Hello, this is a cool program.
This should get unindented.
This code should stay indented:
something() {
echo It works, yo!;
}
That's all.
EOF
# Each line is indented an extra 8 spaces, so strip them
printf '%s' "${message[@]# }"
}
Run Code Online (Sandbox Code Playgroud)
最后一个变体:您可以使用扩展模式来简化参数扩展.不必计算用于缩进的空格数,只需使用选定的非空格字符结束缩进,然后匹配固定前缀.我用:.(冒号后面的空格是为了便于阅读;可以通过对前缀模式稍作更改来删除它.)
(另外,对于你使用以空格开头的here-doc分隔符的非常好的技巧的一个缺点是它阻止你在here-doc中执行扩展.如果你想这样做,你会有要么使分隔符保持未缩进,要么对你的无标签规则做一个小的例外,并使用<<-EOF一个制表符缩进的结束分隔符.)
usage () {
# No tabs necessary!
closing="That's all"
readarray message <<EOF
: Hello, this is a cool program.
: This should get unindented.
: This code should stay indented:
: something() {
: echo It works, yo!;
: }
: $closing
EOF
shopt -s extglob
printf '%s' "${message[@]#+( ): }"
shopt -u extglob
}
Run Code Online (Sandbox Code Playgroud)