mirror of
https://github.com/qelectrotech/qelectrotech-source-mirror.git
synced 2026-10-07 20:34:14 +02:00
Write the messages of a headless run to stderr on Windows too
The exports, --info, --resave and --run return before QetLogger's handler is installed, so they keep Qt's default handler. On Linux and macOS it writes to stderr. On Windows it writes to the debugger when the program has no console, and a GUI program started by another program never has one: everything a headless run reported -- a wire that could not be reconnected, which way the project database was filled, an element that could not be read -- was lost to the caller, a test or a tool like qet-mcp. Install a handler for these runs that writes to stderr in the form the default handler uses on the other systems (the default message pattern, UTF-8). On macOS the stderr of --info, --resave, --run and --export-svg is byte-identical before and after (memory addresses aside). On Windows, tst_databasefromdocument and tst_terminaluuids, which read these messages, fail before and pass after. Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com>
This commit is contained in:
@@ -42,6 +42,13 @@
|
||||
#include <QStyleFactory>
|
||||
#include <QtConcurrentRun>
|
||||
|
||||
#include <cstdio>
|
||||
#include <cstdlib>
|
||||
#ifdef Q_OS_WIN
|
||||
#include <fcntl.h>
|
||||
#include <io.h>
|
||||
#endif
|
||||
|
||||
#ifdef Q_OS_MACOS
|
||||
#include <QFileOpenEvent>
|
||||
|
||||
@@ -120,6 +127,41 @@ static QStringList headlessArguments(const QStringList &args)
|
||||
return kept;
|
||||
}
|
||||
|
||||
/**
|
||||
The headless runs below (the exports, --info, --resave and --run) return
|
||||
before the log-file handler is installed further down, so they keep
|
||||
Qt's default handler. On Linux and macOS that one writes to stderr. On
|
||||
Windows it writes to the debugger when the program has no console, and
|
||||
a GUI program started by another program never has one: what the run
|
||||
reports -- a wire that could not be reconnected, which way the project
|
||||
database was filled -- never reached the caller. Write it to stderr
|
||||
ourselves, in the form the default handler uses on the other systems,
|
||||
so a caller reads the same lines on every system.
|
||||
*/
|
||||
static void headlessMessageHandler(QtMsgType type,
|
||||
const QMessageLogContext &context,
|
||||
const QString &msg)
|
||||
{
|
||||
const QByteArray line = qFormatLogMessage(type, context, msg).toUtf8();
|
||||
fprintf(stderr, "%s\n", line.constData());
|
||||
fflush(stderr);
|
||||
if (type == QtFatalMsg) {
|
||||
abort();
|
||||
}
|
||||
}
|
||||
|
||||
static void installHeadlessMessageHandler()
|
||||
{
|
||||
#ifdef Q_OS_WIN
|
||||
// stderr is in text mode on Windows and turns "\n" into "\r\n": a
|
||||
// caller would read lines ending in '\r' where the other systems give
|
||||
// none, and what the script logs with qet.log() already ends in "\n"
|
||||
// alone. Binary mode gives one line ending for both.
|
||||
_setmode(_fileno(stderr), _O_BINARY);
|
||||
#endif
|
||||
qInstallMessageHandler(headlessMessageHandler);
|
||||
}
|
||||
|
||||
int main(int argc, char **argv)
|
||||
{
|
||||
// before creating Application:
|
||||
@@ -190,6 +232,7 @@ int main(int argc, char **argv)
|
||||
for (int i = 0; i < argc; ++i)
|
||||
raw_args << QString::fromLocal8Bit(argv[i]);
|
||||
if (CLIExport::isExportRequest(raw_args)) {
|
||||
installHeadlessMessageHandler();
|
||||
QApplication export_app(argc, argv);
|
||||
// No crash-recovery backups in one-shot CLI mode: the backup write
|
||||
// runs on a background thread referencing the project and races the
|
||||
@@ -207,6 +250,7 @@ int main(int argc, char **argv)
|
||||
// #162). Same reasoning as the export branch above for running
|
||||
// before SingleApplication and answering message boxes headlessly.
|
||||
if (QetScripting::isRunRequest(raw_args)) {
|
||||
installHeadlessMessageHandler();
|
||||
QApplication script_app(argc, argv);
|
||||
QETProject::setBackupEnabled(false);
|
||||
QET::QetMessageBox::setNonInteractive(true);
|
||||
|
||||
Reference in New Issue
Block a user