Iterate array using loop over ssh

A simple script:

#!/bin/bash
test=test
test1=(test1 test2 test3)
echo ${test1
[*]}
ssh server 'echo '$test'; echo '${test1
[*]}' ; echo '${test1[1]}' ; for m in $(seq 1 $(echo '${test1
[*]}' | tr " " "\n" | wc -l)); do echo $m ; echo '${test1[$m]}'; done'

Here is the result:

test1 test2 test3
testing
test
test1 test2 test3
test2
1
test1
2
test1 ***this should be "test2"
3
test1 ***this should be "test3"

Why is it not being iterated as expected?

I read somewhere that ssh doesn't know about the variables, etc etc. Then why can I see that "echo ${test1
[*]}" iterates correctly?

BUMMER :frowning: I really need this :frowning:

Can you guys help me out?

**EDIT: Forgot the CODE tags, sorry :slight_smile:

I think, this is expected.

When your commands go to server, all the variables are replaced by its values.
The 'echo '${test1[$m]}' at the end of your command is evaluated by your local system (the first element of the array since it cannot make out what $m is) and would be replaced by 'test1' by the time it reaches the server . So it prints the same for all the iterations.

1 Like

Yes, makes sense (now that you mention it :))

But that's the nice thing about BASH, there's no "No way out" problem:

#!/bin/bash
TEST=test
TEST1=(test1 test2 test3)
ssh server 'TEST2=('${TEST1
[*]}') ; for m in $(seq 0 $(eval echo \${TEST2
[*]} | tr " " "\n" | wc -l)); eval echo \${TEST2[$m]}; done'

Declaring a Variable, that is iterated before the loop, so that the array gets populated as expected and then iterated together with the loop variable $m.

Thank you for the hint. A nice day to you all :slight_smile:

1 Like

Another way around the variable problem, a particularly robust one, is this:

ssh username@host /bin/sh -s arg1 arg2 arg3 <<"EOF"
literal script contents
that don't even need
extra quotes
or escaping
EOF

Also, "${ARRAY[@]}" is a safer way to expand an array, because it splits upon elements, not spaces. It works for commandline arguments too. Also, your loop can be simplified quite a lot. How about this:

ssh username@host /bin/sh -s "${TEST1[@]}" <<"EOF"
echo "$@"
echo "${1}"

N=0
for m in "$@" # Expands into $1 $2 $3 ...
do
        echo $m
        echo $N
        let N=N+1
done
EOF

Never thought of using it for ssh. I wonder if it iterates all variables as expected. I will give it a try!

Thanks. Your improvement advice actually reflects my running script (more or less :))

I kinda messed up in trying to keep the example script simple :smiley:

A nice Weekend to all.

Depends what you expect. You get nothing but the $1 $2 $3 ... arguments you put into it.