I have some python code using subprocess.Popen
to open a console application and get stdout/stderr from it.
Launching from the interpreter works fine and as intended.
After using cx_freeze with --base-name Win32GUI
option the Popen pops up in a console window now and I can't capture stdout/stderr. If I remove --base-name Win32GUI
it works as intended but I now have a console behind the UI.
Here is the code (I've tried it without startupinfo
and without shell=False
):
startupinfo = subprocess.STARTUPINFO()
startupinfo.dwFlags |= subprocess.STARTF_USESHOWWINDOW
startupinfo.wShowWindow = subprocess.SW_HIDE
subprocess.Popen(['exe', 'arg1', 'arg2'], stdout=subprocess.PIPE, stderr=subprocess.PIPE, shell=False, startupinfo=startupinfo)
I'm using out, err = p.communicate()
to grab stdout/stderr
Okay I found a solution. It looks like since its a windows GUI Application stdout handle doesn't exist and it looks like subprocess inherits that behavior. So a workaround is a simple one and a more complicated one involved with the win32api and creating a pipe for it (didn't try this method).
Here is what finally worked:
startupinfo = subprocess.STARTUPINFO()
startupinfo.dwFlags |= subprocess.STARTF_USESHOWWINDOW
startupinfo.wShowWindow = subprocess.SW_HIDE
stdout_file = tempfile.NamedTemporaryFile(mode='r+', delete=False)
process = subprocess.Popen(['exe', 'arg1', 'arg2'], stdin=subprocess.PIPE, stdout=stdout_file, stderr=subprocess.PIPE, shell=False, startupinfo=startupinfo)
return_code = process.wait()
stdout_file.flush()
stdout_file.seek(0) # This is required to reset position to the start of the file
out = stdout_file.read()
stdout_file.close()