在bash中用其内容替换“源文件"并扩展变量 [英] Replacing 'source file' with its content, and expanding variables, in bash
问题描述
在script.sh中,
In a script.sh,
source a.sh
source b.sh
CMD1
CMD2
CMD3
如何用其内容替换 source * .sh
(不执行命令)?我想看看在寻找文件并扩展所有变量之后,bash解释器将执行什么操作.
how can I replace the source *.sh
with their content (without executing the commands)?
I would like to see what the bash interpreter executes after sourcing the files and expanding all variables.
我知道我可以使用 set -n -v
或运行 bash -n -v script.sh 2> output.sh
,但这不会代替源代码命令(如果a.sh或b.sh包含变量,则更少).
I know I can use set -n -v
or run bash -n -v script.sh 2>output.sh
, but that would not replace the source commands (and even less if a.sh or b.sh contain variables).
我考虑使用子外壳,但这仍然不能扩展源代码行.我在源代码行之前和之后尝试了 set + n + v
和 set -n -v
的组合,但这仍然行不通.
I thought of using a subshell, but that still doesn't expand the source lines. I tried a combination of set +n +v
and set -n -v
before and after the source lines, but that still does not work.
我将使用ssh将输出发送到远程计算机.我可以使用<< output.sh
将内容通过管道传递到ssh命令,但是我不能以root用户身份登录到远程计算机,但是我是一个sudoer.因此,我认为我可以创建脚本并将其作为base64编码的字符串发送(使用
I'm going to send that output to a remote machine using ssh.
I could use <<output.sh
to pipe the content into the ssh command, but I can't log as root onto the remote machine, but I am however a sudoer.
Therefore, I thought I could create the script and send it as a base64-encoded string (using that clever trick )
base64 script | ssh remotehost 'base64 -d | sudo bash'
有解决方案吗?还是您有更好的主意?
Is there a solution? Or do you have a better idea?
推荐答案
您可以执行以下操作:
inline.sh:
inline.sh:
#!/usr/bin/env bash
while read line; do
if [[ "$line" =~ (\.|source)\s+.+ ]]; then
file="$(echo $line | cut -d' ' -f2)"
echo "$(cat $file)"
else
echo "$line"
fi
done < "$1"
请注意,这假定存在 source
d个文件,并且不处理错误.您还应该处理可能的哈希爆炸.如果 source
文件本身包含 source
,则需要递归应用脚本,例如像(未经测试)这样的东西:
Note this assumes the source
d files exist, and doesn't handle errors. You should also handle possible hashbangs. If the sourced
files contain themselves source
, you need to apply the script recursively, e.g. something like (not tested):
while egrep -q '^(source|\.)' main.sh; do
bash inline.sh main.sh > main.sh
done
让我们测试一下
main.sh:
source a.sh
. b.sh
echo cc
echo "$var_a $var_b"
a.sh:
echo aa
var_a="stack"
b.sh:
echo bb
var_b="overflow"
结果:
bash inline.sh main.sh
echo aa
var_a="stack"
echo bb
var_b="overflow"
echo cc
echo "$var_a $var_b"
bash inline.sh main.sh | bash
aa
bb
cc
stack overflow
顺便说一句,如果您只想查看bash执行的操作,则可以运行
BTW, if you just want to see what bash executes, you can run
bash -x [script]
或远程
ssh user@host -t "bash -x [script]"
这篇关于在bash中用其内容替换“源文件"并扩展变量的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!