1

I'm trying to run cat < /tmp/test.txt on remote host host2 through host1. The file /tmp/test.txt exists on host2. I try:

# locally
ssh -t host1 ssh host2 "cat < /tmp/test.txt"

The above command results in:

bash: /tmp/test.txt: No such file or directory

If I run a similar command on host1 directly, it works. The working command is:

# on host1
ssh host2 "cat < /tmp/test.txt"

Why do I get No such file or directory? What is the right local command?

0

1 Answer 1

1

In general ssh is able to build a command from many arguments it gets. This kinda crates an impression the arguments are passed to the remote side as an array. They are not; the remote command is always a single string to be interpreted by the remote shell.

Your command:

# locally
ssh -t host1 ssh host2 "cat < /tmp/test.txt"

is equivalent to this:

# locally
ssh -t host1 'ssh host2 cat < /tmp/test.txt'

They both result in the same command being passed to the shell on host1. The command is:

# on host1
ssh host2 cat < /tmp/test.txt

The above command makes the shell on host1 try to redirect stdin of this ssh. No such file or directory comes from this redirection attempt on host1. If the redirection worked, the string passed to a shell on host2 would be cat.

Your desired command on host1 is:

# on host1
ssh host2 "cat < /tmp/test.txt"

which does not involve any redirection on host1 and passes cat < /tmp/test.txt to a shell on host2.

There are many forms of local command that result in passing exactly cat < /tmp/test.txt to a shell on host2. This is the one I would use:

# locally
ssh -t host1 'ssh host2 "cat < /tmp/test.txt"'

The outer quotes (single-quotes in this case) are for the local shell. The inner quotes (double-quotes in this case) are for the shell on host1. The command run on host1 is exactly your desired command.

More insight here: How to execute complex command line over ssh?

Note ssh -t host1 … allocates a tty on host1, which is useful if ssh host2 … on host1 asks for password (I suspect this is the reason you used ssh -t), but it may distort the content of /tmp/test.txt. In other words, if you locally redirected output to a regular file, then the file might not be identical to the original /tmp/test.txt. You cannot reliably transfer arbitrary data this way (see ssh with separate stdin, stdout, stderr AND tty).

1
  • About '-t', I use that for debug like ssh -t host1 ssh host2, then I type cat < /tmp/test.txt Commented Jun 21 at 2:05

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .