-
Notifications
You must be signed in to change notification settings - Fork 384
Closed
Labels
Description
Example case is running Invoke's own test runner, inv test (which does run('spec', pty=True)) within a Git pre-push hook. Git runs the hook script in some non-pty environment (even if one is running git from a terminal window) and so pexpect's attempt to do things like tty.tcgetattr(self.STDIN_FILENO) explodes with termios.error: (25, 'Inappropriate ioctl for device').
Sure enough, examining that fileno value when running by hand vs hook script shows that os.isatty(self.STDIN_FILENO) is False when things blow up.
I can see two ways to handle this:
- Simply print a more useful error message (either raising a custom exception or reraising the real exception), e.g. "You seem to be running a command with
pty=Truewhen you don't actually have a PTY of your own! Please changepty=Falseor don't run this task headless."- Pretty easy to do.
- Not very friendly; I expect most places where this error pops up would be, well, exactly what I just ran into: a command normally ran by hand which is being run by an automated system instead.
- Fall back to
pty=Falsebehavior whenos.isatty(sys.stdin.fileno())is False, i.e. do best-effort re: running the requested command.- In at least some use cases, commands that normally "want" a PTY will still run without one, just with different behavior or uglier output, so we're better off than before.
- In the other cases, there's simply no way the subcommand could ever have possibly worked (requires a real, true PTY present at top of invocation chain) so failure is still failure and we're no worse off.
- IT could be confusing, however (since the underlying command's non-pty behavior may be subtle or unexpected, compared to how it works under a pty) so we should probably emit a warning?