[英]Calling one Bash script from another Script passing it arguments with quotes and spaces
我在 Linux 上制作了兩個測試 bash 腳本以明確問題。
TestScript1
看起來像: echo "TestScript1 Arguments:"
echo "$1"
echo "$2"
echo "$#"
./testscript2 $1 $2
TestScript2
看起來像: echo "TestScript2 Arguments received from TestScript1:"
echo "$1"
echo "$2"
echo "$#"
testscript1
時: ./testscript1 "Firstname Lastname" testmail@example.com
TestScript1 Arguments:
Firstname Lastname
testmail@example.com
2
TestScript2 Arguments received from TestScript1:
Firstname Lastname
testmail@example.com
2
TestScript1 Arguments:
Firstname Lastname
testmail@example.com
2
TestScript2 Arguments received from TestScript1:
Firstname
Lastname
3
我該如何解決這個問題? 我想獲得所需的輸出而不是實際輸出。
在 Testscript 1 中引用您的參數:
echo "TestScript1 Arguments:"
echo "$1"
echo "$2"
echo "$#"
./testscript2 "$1" "$2"
您需要使用: "$@"
(帶引號)或"${@}"
(相同,但也告訴 shell 變量名稱的開始和結束位置)。
(並且不要使用: $@
或"$*"
或$*
)。
前任:
#testscript1:
echo "TestScript1 Arguments:"
for an_arg in "$@" ; do
echo "${an_arg}"
done
echo "nb of args: $#"
./testscript2 "$@" #invokes testscript2 with the same arguments we received
我不確定我是否理解你的其他要求(你想用單引號調用'./testscript2'?)所以這里有2個瘋狂的猜測(改變上面的最后一行):
'./testscript2' "$@" #only makes sense if "/path/to/testscript2" containes spaces?
./testscript2 '"some thing" "another"' "$var" "$var2" #3 args to testscript2
請給我你想要做的確切事情
編輯:在他的評論說他嘗試 tesscript1 "$1" "$2" "$3" "$4" "$5" "$6" 運行: salt 'remote host' cmd.run './testscript2 $1 $2 $3 $4 $5 $6'
您有許多中間級別:主機 1 上的 testscript1,需要運行“salt”,並給它一個字符串,啟動“testscrit2”,參數用引號引起來......
您可以通過以下方式“簡化”:
#testscript1
#we receive args, we generate a custom script simulating 'testscript2 "$@"'
theargs="'$1'"
shift
for i in "$@" ; do
theargs="${theargs} '$i'"
done
salt 'remote host' cmd.run "./testscript2 ${theargs}"
如果這不起作用,那么不要運行“testscript2 ${theargs}”,而是將上面的最后一行替換為
echo "./testscript2 ${theargs}" >/tmp/runtestscript2.$$ #generate custom script locally ($$ is current pid in bash/sh/...)
scp /tmp/runtestscript2.$$ user@remotehost:/tmp/runtestscript2.$$ #copy it to remotehost
salt 'remotehost' cmd.run "./runtestscript2.$$" #the args are inside the custom script!
ssh user@remotehost "rm /tmp/runtestscript2.$$" #delete the remote one
rm /tmp/runtestscript2.$$ #and the local one
您可以執行以下操作來解析所有參數:
注意/bin/bash
的使用
測試腳本1:
#!/bin/bash
echo "TestScript1 Arguments:"
echo "$1"
echo "$2"
echo "$#"
# Build PARAMS to be a list of arguments
# Each wrapped in quotes and
# any existing quotes escapes with \
for var in "$@"
do
PARAMS="$PARAMS \"${var//\"/\\\"}\""
done
# Call the second script with eval, also passing an extra parameter.
eval ./testscript2 "ExtraParam" $PARAMS
測試腳本2:
#!/bin/bash
echo "TestScript2 Arguments received from TestScript1:"
echo "$1"
echo "$2"
echo "$3"
echo "$#"
然后當您執行以下操作時:
./testscript1 "Firstname Lastname" testmail@example.com
輸出將是:
TestScript1 Arguments:
Firstname Lastname
testmail@example.com
2
TestScript2 Arguments received from TestScript1:
ExtraParam
Firstname Lastname
testmail@example.com
3
通過使用\"${var//\"/\\\"}\""
以這種方式構建 PARAMS,它允許腳本正常運行,即使在參數中使用引號調用,如下所示:
./testscript1 "Firstname's Last\"name" testmail@example.com
輸出將是:
TestScript1 Arguments:
Firstname's Last"name
testmail@example.com
2
TestScript2 Arguments received from TestScript1:
ExtraParam
Firstname's Last"name
testmail@example.com
3
所有引號和空格都正確地從一個腳本傳遞到另一個腳本。
如果您不想傳遞所有參數,請忽略 for 循環,只需將 eval 與相關參數一起使用。
例如:
eval ./testscript2 "\"${1//\"/\\\"}\"" "Test1" "Test2"
${1...
表示第一個參數,使用${2...
作為第二個等。
這將導致:
TestScript1 Arguments:
Firstname's Last"name
testmail@example.com
2
TestScript2 Arguments received from TestScript1:
Firstname's Last"name
Test1
Test2
3
如果你確定你永遠不會在參數中得到引號,那么不要使用"\"${1//\"/\\\"}\""
只需使用"$1"
。
我發現以下程序對我有用
test1.sh
a=xxx
test2.sh $a
在 test2.sh 中,您使用$1
來引用 test1.sh 中的變量a
回聲 $1
輸出將是xxx
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.