使用 PyInstaller noconsole 显示标准输出

如何解决使用 PyInstaller noconsole 显示标准输出

如何使用 PyInstaller 创建一个也提供 CLI 而无需弹出 shell 的 GUI 应用程序?

例如,如果我使用 pyinstaller argparse_gui.py --noconsole 创建以下应用程序,shell 中不会显示标准输出

C:\projects\argparse_gui\dist\argparse_gui>argparse_gui.exe -V

C:\projects\argparse_gui\dist\argparse_gui>

我可以使用 argparse_gui.exe -V > log.txt 2>&1 将 stdout/stderr 重定向一个文件,但这并不完全是用户友好的。如果在没有 --noconsole 的情况下构建,我可以看到 stdout,但随后会出现一个烦人的单独 shell 窗口。

# argparse_gui.py
import sys
import argparse
from PyQt5 import QtCore,QtWidgets,QtGui


class MainWindow(QtWidgets.QMainWindow):

    def __init__(self):
        super().__init__()

        self.init_widgets()
        self.init_layout()

    def init_widgets(self):
        self.label = QtWidgets.QLabel('Hello,world!')

    def init_layout(self):
        layout = QtWidgets.QVBoxLayout()
        layout.addWidget(self.label)

        centralWidget = QtWidgets.QWidget()
        centralWidget.setLayout(layout)
        self.setCentralWidget(centralWidget)


if __name__ == '__main__':

    parser = argparse.ArgumentParser()

    parser.add_argument("-V","--version",help="display application information",action='store_true')

    args = parser.parse_args()

    if args.version:
        print('Version 123',flush=True)
    else:
        app = QtWidgets.QApplication(sys.argv)
        main_window = MainWindow()
        main_window.show()
        sys.exit(app.exec_())

解决方法

编辑:我找到了一种迂回的方法来做到这一点,但控制台窗口会一直出现,直到 GUI 加载完毕。我将以下代码放在主脚本的顶部,并在没有 --windowed 的情况下运行 Pyinstaller。如果脚本不是从现有控制台运行,这将隐藏控制台窗口。

import ctypes
kernel32 = ctypes.WinDLL('kernel32',use_last_error=True)
process_array = (ctypes.c_uint8 * 1)()
num_processes = kernel32.GetConsoleProcessList(process_array,1)
if num_processes < 3: ctypes.WinDLL('user32').ShowWindow(kernel32.GetConsoleWindow(),0)

否则,我将得出结论,没有办法使用 PyInstaller。如果 --noconsole/--windowed,则 EXE 与 pythonw 捆绑在一起。 PythonW 没有附加控制台,即使从控制台启动也是如此。

然而,命令行参数仍然被传递。您仍然可以使用 sys.argv 或 argparser 来访问它们。

--noconsole 中运行时,sys.stdout 是一个 NullWriter 对象,而 sys.__stdout__None。在 1 上使用 open() 会引发异常,CON 和 CONOUT$ 无法执行任何操作。将控制台重定向到 >&1 会引发错误。

注意:在某些条件下,stdin、stdout 和 stderr 以及 stdinstdoutstderr 的原始值可以是 None。它 > 通常是未连接到 Windows GUI 应用程序的情况 控制台和 Python 应用程序以 pythonw 开头。 https://docs.python.org/3/library/sys.html#sys.__stderr__

如果 EXE 是使用 --noconsole 构建的,Pyinstaller 会明确使用 PythonW.exe。我无法找到解决此问题的方法,例如如果从 cli 调用则加载控制台引导加载程序,否则加载 pythonw。

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。

相关推荐


Selenium Web驱动程序和Java。元素在(x,y)点处不可单击。其他元素将获得点击?
Python-如何使用点“。” 访问字典成员?
Java 字符串是不可变的。到底是什么意思?
Java中的“ final”关键字如何工作?(我仍然可以修改对象。)
“loop:”在Java代码中。这是什么,为什么要编译?
java.lang.ClassNotFoundException:sun.jdbc.odbc.JdbcOdbcDriver发生异常。为什么?
这是用Java进行XML解析的最佳库。
Java的PriorityQueue的内置迭代器不会以任何特定顺序遍历数据结构。为什么?
如何在Java中聆听按键时移动图像。
Java“Program to an interface”。这是什么意思?
Java在半透明框架/面板/组件上重新绘画。
Java“ Class.forName()”和“ Class.forName()。newInstance()”之间有什么区别?
在此环境中不提供编译器。也许是在JRE而不是JDK上运行?
Java用相同的方法在一个类中实现两个接口。哪种接口方法被覆盖?
Java 什么是Runtime.getRuntime()。totalMemory()和freeMemory()?
java.library.path中的java.lang.UnsatisfiedLinkError否*****。dll
JavaFX“位置是必需的。” 即使在同一包装中
Java 导入两个具有相同名称的类。怎么处理?
Java 是否应该在HttpServletResponse.getOutputStream()/。getWriter()上调用.close()?
Java RegEx元字符(。)和普通点?