简体   繁体   中英

Bash assign output to variable inside here document

In a bash script, what I need is to ssh to a server and do some commands, what I got so far is like this:

outPut="ss"
ssh user@$serverAddress << EOF
cd /opt/logs
outPut="$(ls -l)"
echo 'output is ' $outPut
EOF
echo "${outPut}"

But the output from terminal is:

output is  ss
ss

The output was assigned to the output from command ls -l , but what it showed is still the original value, which is ss . What's wrong here?

There are actually two different problems here. First, inside a here-document, variable references and command substitutions get evaluated by the shell before the document is sent to the command. Thus, $(ls -l) and $outPut are evaluated on the local computer before being sent (via ssh ) to the remote computer. You can avoid this either by escaping the $ s (and maybe some other characters, such as escapes you want sent to the far side), or by enclosing the here-doc delimiter in quotes ( ssh user@$serverAddress << "EOF" ) which turns that feature off for the document.

Second, variable assignments that happen on the remote computer stay on the remote computer. There's no way for the local and remote shells to share state. If you want information from the remote computer, you need to send it back as output from the remote part of the script, and capture that output (with something like remoteOutput=$(ssh ...) or ssh ... >"$tempFile" ). If you're sending back multiple values, the remote part of the script will have to format its output in such a way that the local part can parse it. Also, be aware that any other output from the remote part (including error messages) will get mixed in, so you'll have to parse carefully to get just the values you wanted.

No, sorry that will not work.

  1. Either use command substitution value (to printf) inside the here-doc (lines bettween EOF):

     ssh user@$serverAddress << EOF printf 'output is %s\\n' "$(ls -l /opt/logs)" EOF 
  2. Or you capture the execution of command from inside ssh, and then use the value.

     outPut="$( ssh user@$serverAddress << EOF cd /opt/logs ls -l EOF )" echo 'output is ' "$outPut" echo "${outPut}" 

Option 1 looks cleaner.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM