shell脚本中高效使用换行符

shell脚本中高效使用换行符

语境: 我有一个任务要在远程计算机上运行一些脚本,然后退出

我有一个脚本,但我不知道如何使用里面的换行符,

triggerPerformanceTest(){
report=$1
userDataFiles=$2
baseURL=$3
cdnURL=$4
streamingURL=$5
echo "Startin the Jmeter script"
ssh -tt -i Test.ppk username@<test server> <<EOF
cd apache-jmeter-3.1/bin/
JVM_ARGS="-Xms512m -Xmx25000m" ./jmeter.sh -n -t /home/ubuntu/JMeter/Test.jmx --jmeterproperty XMLReport=$report --jmeterproperty UserDataFile=$userDataFiles --jmeterproperty BaseUrl=$baseURL --jmeterproperty CdnUrl=$cdnURL --jmeterproperty StreamingUrl=$streamingURL --jmeterproperty isBenchMark=false --jmeterproperty Enable_DigitalExhaust=true --jmeterproperty Enable_Health=true --jmeterproperty HealthPollingInterval=6
exit
EOF
echo "Test successfully executed"
}

triggerPerformanceTest Log.csv UserDataFile.csv localhost localhost localhost

在第二步中,我运行 JMeter 脚本,它有很多属性。有没有一种方法可以在这里使用换行符,这样它就会认为所有行都在一个步骤中。就像下面提到的

ssh user@server << EOF
  command_one
  command_two argument1 argument2 argument3 argument4
              argument5 argument6 argument7
  command_three
EOF

答案1

<<在here文档中, (here )后面的分隔符EOF没有被引用,<backslash><newline>序列被删除,这是一个行延续

实际上,唯一<backslash><newline>没有被删除的情况是:

  • 单引号内
  • 在此处引用分隔符的文档中
  • 其中反斜杠本身被引用 ( <backslash><backslash><newline>)

cat << EOF
foo\
bar
EOF

输出

foobar

所以,在这里你可以这样做:

ssh user@server << EOF
  command_one
  command_two argument1 argument2 argument3 argument4 \
              argument5 argument6 argument7
  command_three
EOF

最终ssh会被喂饱:

  command_one
  command_two argument1 argument2 argument3 argument4               argument5 argument6 argument7
  command_three

在其标准输入上。

即使您使用:ssh ... << 'EOF'以避免在此处文档内执行参数扩展、命令替换和算术扩展,ssh也会被输入:

  command_one
  command_two argument1 argument2 argument3 argument4 \
              argument5 argument6 argument7
  command_three

但远程 shell 会将其解释<backslash><newline>为续行,因此它会具有相同的效果。

请注意,当您这样做时:

ssh user@server << EOF

sshd在远程主机上运行用户的登录 shell 来解释该代码。由于它可以是任何东西,不一定是类似 Bourne 的 shell,所以最好运行:

ssh user@server sh << EOF

其中sshd运行user-s-login-shell -c sh,因此您知道类似 Bourne 的 shell 正在解释您的代码。

JVM_ARGS="-Xms512m -Xmx25000m" ./jmeter.sh...作为Bourne-shell 或兼容语法的示例。它可以在cshtcshrces、 shell中工作,因此如果on的登录 shell是这些 shell 之一,则fish无法使用。ssh user@server sh << EOFuserserver

但一个显着的区别是,在这种情况下,user-s-login-shell它不会作为登录 shell 启动,因此不会读取/etc/profile~/.profile(或用户登录 shell 的等效项)来设置登录会话。

或者,您可以将该代码转换为与所有这些 shell 兼容的语法:(env JVM_ARGS='-Xms512m -Xmx25000m' ./jmeter.sh...使用单引号而不是双引号,并用于env传递 env var 而不是 Bourne/rc 特定envvar=value cmd语法)。

可以通过使用来避免反斜杠xargs

ssh user@server sh << EOF
  command_one
  xargs command_two << END_OF_ARGS
    argument1 argument2 argument3 argument4
    argument5 argument6 argument7
  END_OF_ARGS
  command_three
EOF

或者使用像rcksh93zshbashyash数组这样的 shell:

使用rc/zsh语法:

ssh user@server zsh << 'EOF'
  command_one
  args=(
    argument1 argument2 argument3 argument4
    argument5 argument6 argument7
  )
  command_two $args
  command_three
EOF

(此处引用EOF,以便$args本地 shell 不会扩展)。

或者使用ksh93//bash语法yash(也适用于zsh):

ssh user@server bash << 'EOF'
  command_one
  args=(
    argument1 argument2 argument3 argument4
    argument5 argument6 argument7
  )
  command_two "${args[@]}"
  command_three
EOF

答案2

是的,以 a 结束行\以继续下一行。

ssh user@server << EOF
  command_one
  command_two argument1 argument2 argument3 argument4\
              argument5 argument6 argument7
  command_three
EOF

相关内容