maxim4d
maxim4d

Reputation: 41

Determine if the stdout is terminal under ssh

To test whether the output is terminal we can do -t STDOUT:

if (-t STDOUT) {
  # print with terminal control chars
} else {
  # just plain print
}

But when the script is executed in the ssh session not run from terminal (Jenkins in my case), the -t test still returns true and my output gets polluted with control chars:

ssh user@server "/my/script.pl"

Why does the -t detects the terminal?

Upvotes: 1

Views: 262

Answers (2)

ikegami
ikegami

Reputation: 385675

I don't know why ssh is allocating a terminal for you — mine defaults to not doing that even if the output of ssh goes to a terminal — but passing -T to ssh will disable pseudo-tty creation on the remote end.

$ ssh -t localhost "perl -E'say -t STDOUT ?1:0'"
1
Connection to localhost closed.

$ ssh -T localhost "perl -E'say -t STDOUT ?1:0'"
0

From ssh's man page:

-T Disable pseudo-tty allocation.

-t Force pseudo-tty allocation. This can be used to execute arbitrary screen-based programs on a remote machine, which can be very useful, e.g. when implementing menu services. Multiple -t options force tty allocation, even if ssh has no local tty.

Upvotes: 2

BRPocock
BRPocock

Reputation: 13914

Perhaps it would be better if you instead forced ssh to allocate a pty —

From the ssh manual:

-t Force pseudo-tty allocation. This can be used to execute arbitrary screen-based programs on a remote machine, which can be very useful, e.g. when implementing menu services. Multiple -t options force tty allocation, even if ssh has no local tty.

The longer answer: -t (the Perl or Bourne shell function) reliably detects whether the stream is a “typewriter,” but ssh will normally only allocate a pseudo-teletype (pty) stream in interactive shells, not when other programs are being started.

See also RequestTTY as an option in .ssh/config.

Upvotes: 1

Related Questions