python / cpython

The Python programming language
https://www.python.org
Other
63.48k stars 30.4k forks source link

subprocess.Popen doesn't redirect child process' stderr to stdout #126848

Open yurivict opened 5 hours ago

yurivict commented 5 hours ago

Bug report

Bug description:

Testcase:

import time
import subprocess

with open('log', 'w') as log:

    p = subprocess.Popen(['python', 'sp-child.py'],
                         stdout=log,
                         stderr=subprocess.STDOUT)
    time.sleep(10)
    p.communicate()

Additional file sp-child.py:

import sys

print('I am a child!')
print(f' ... in-terminal: stdout={sys.stdout.isatty()} stderr={sys.stderr.isatty()}')

The subprocess.Popen argument requests child's stderr to be redirected to stdout and this doesn't happen.

The child process prints:

I am a child!
 ... in-terminal: stdout=False stderr=False

CPython versions tested on:

3.11

Operating systems tested on:

Linux

brianschubert commented 4 hours ago

Hi yurivict, could you clarify what you are expecting to happen, and how that differs from what actually happens?

Are you perhaps expecting stderr=subprocess.STDOUT to cause the child process' stderr to go the parent process' stdout (and therefore sys.stderr.isatty() would be True, not False)? If so, that's not quite what that means. stderr=subprocess.STDOUT means that the child process' stderr will be redirected to the same handle as its stdout, similar to using 2>&1 in a shell. In this case, that means that both stdout and stderr will be directed to the log file. If you want the child process' stderr to be directed to the parent process' stdout, I believe you can pass stderr=sys.stdout.