我想中止 Qt Installer Framework 进程,这可以通过多种方式完成(按照 Qt 为此提供的示例,或者抛出未捕获的异常,或者只是注入无效命令以导致硬崩溃......)。但无论如何,退出代码似乎是0(即“成功”)!有什么方法可以使它成为 1 (或其他东西)?
我可以想到一些丑陋的、笨拙的替代方案来以编程方式评估这个过程的成功,但我真的希望这不是必需的......
我想中止 Qt Installer Framework 进程,这可以通过多种方式完成(按照 Qt 为此提供的示例,或者抛出未捕获的异常,或者只是注入无效命令以导致硬崩溃......)。但无论如何,退出代码似乎是0(即“成功”)!有什么方法可以使它成为 1 (或其他东西)?
我可以想到一些丑陋的、笨拙的替代方案来以编程方式评估这个过程的成功,但我真的希望这不是必需的......
我 没有找到真正的解决方案,所以我这样做了......
基本上,我的解决方法是抛出未捕获的异常,并在“失败时退出”条件下写入错误日志文件。日志的存在表明发生了问题。如果没有这样的日志,那么安装成功。如果您只关心通过/失败,只需检查文件是否存在。否则,请阅读文件以获取详细信息。
在我的解决方案中,我允许客户端将参数传递给安装程序,为错误日志指定特定的路径/名称。如果未提供,它将写入临时目录上的默认路径。
请注意,除非我错了,否则我看不到在 QtIFW 脚本中直接写入文件、删除文件或解析临时路径的方法。所以,我只使用 shell 操作。我使用它们的方式是从 shell 返回路径分辨率,从而隐式允许在文件路径中使用环境变量。
这是完整的Windows特定解决方案:
function clearErrorLog() {
var path = installer.value( "errlog", "%temp%\\installer.err" );
var deleteCmd = "echo off && del \"" + path + "\" /q\necho " + path + "\n";
var result = installer.execute( "cmd.exe", ["/k"], deleteCmd );
if( result[1] != 0 )
throw new Error("Clear error log failed.");
try{
var cmdOutLns = result[0].split("\n");
path = cmdOutLns[cmdOutLns.length-2].trim();
}
catch(e){ path = ""; }
if( path=="" || installer.fileExists( path ) )
throw new Error("Clear error log failed. (file exists)");
console.log("Cleared error log: " + path);
}
function writeErrorLog( msg ) {
var path = installer.value( "errlog", "%temp%\\installer.err" );
var writeCmd = "echo off && echo " + msg + " > \"" + path + "\"\necho " + path + "\n";
var result = installer.execute( "cmd.exe", ["/k"], writeCmd );
if( result[1] != 0 )
throw new Error("Write error log failed.");
try{
var cmdOutLns = result[0].split("\n");
path = cmdOutLns[cmdOutLns.length-2].trim();
}
catch(e){ path = ""; }
if( path=="" || !installer.fileExists( path ) )
throw new Error("Write error log failed. (file does not exists)");
console.log("Wrote error log to: " + path);
}
function silentAbort( msg ) {
writeErrorLog( msg );
throw new Error( msg );
}
在脚本开始时,清除日志。
function Controller() {
clearErrorLog();
...
}
将第一行替换为clearErrorLog()
:
var path = installer.value( "errlog", "/tmp/installer.err" );
var deleteCmd = "rm \"" + path + "\";echo " + path;
var result = installer.execute( "sh", ["-c", deleteCmd] );
并将第一行替换为writeErrorLog()
:
var path = installer.value( "errlog", "/tmp/installer.err" );
var writeCmd = "echo " + msg + " > \"" + path + "\";echo " + path;
var result = installer.execute( "sh", ["-c", writeCmd] );
如果要检查平台,systemInfo.kernelType
将返回"winnt"
、"linux"
或"darwin"
(对于 macOS)以及其他可能的值。
silentAbort( msg )
. 在 QtIWF 脚本中,没有主异常处理程序或诸如此类的东西,因此只要您没有将那个 silentAbort 函数嵌套在 try 块中,异常就会立即有效地终止程序。
为了明确说明要使用的路径,请使用“errlog”键作为参数启动安装程序,如下所示myinstaller.exe errlog=mylog.err
:如果您不包含完整路径,则将使用当前工作目录。
如果需要,您可以自行删除日志。当然,在临时目录中也留下垃圾是很常见的(并不是说我真的很喜欢那个......)。