What is the difference between execution ssh
command followed by remote command with and quotes and the remote command without quotes?
E.g. what is the difference between:
ssh remotehost tar xf archivename.tar
and
ssh remotehost "tar xf archivename.tar"
or what is the difference between:
ssh remotehost <path to script>/myscript.sh param
and
ssh remotehost "<path to script>/myscript.sh param"
The trailing arguments are combined into a single string which is passed to as an argument to the -c
option of your login shell on the remote machine. In your first example, there is little difference. However, consider the following:
$ ssh remotehost echo *
Here, *
is expanded locally, and the result is passed to the remote machine. On my machine, my working directory consisted of a single entry containing an apostrophe (single quote), so the remote host tried to run a command like
bash -c "echo chepner's folder"
which of course resulted in an error.
$ ssh remotehost "echo *"
Now the remote host gets a literal *
, but it is subject to shell expansion before being passed to bash -c
. As a result, you output all the files in your home directory on the remote host.
$ ssh remotehost "echo \*"
Finally, the remote shell gets a quoted asterisk in its input, so you get a single literal *
as output.
The quotes prevents expansion of special characters.
Imagine if there were any in your command you want to execute remotely (;, &, &&, |, ||, >, >>
etc.). They would take effect before actually getting to your remote host, because bash would not know that all of it is just an argument to ssh
.
Also, if the path to your script contained more spaces, they'd get lost and script wouldn't be found.