You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Inno Setup中如何实现单文件夹安装及旧版本升级目录重命名?

从并行版本目录切换到单目录的Inno Setup升级方案

核心思路

无需先安装到旧版本目录再重命名,直接将新版本安装到无版本号的MySoftware目录即可。通过Inno脚本自动完成旧版本路径检测、用户配置迁移、旧版本静默卸载和残留目录清理,实现平滑升级。

具体实现步骤

1. 配置Setup段基础参数

给新版本分配独立的AppId(避免与旧版本冲突),指定默认安装目录为无版本号路径:

[Setup]
AppId={你的新版本GUID} ; 必须与所有旧版本的AppId不同
AppName=MySoftware
AppVersion=4.0
DefaultDirName={pf}\MySoftware
DirExistsWarning=auto ; 自动处理目录已存在的情况
PrivilegesRequired=admin ; 如需安装到Program Files,保留此配置

2. 编写代码段实现旧版本检测与处理

在[Code]段中实现旧版本路径识别、配置迁移、旧版本卸载和目录清理逻辑:

var
  OldInstallPath: String;
  // 列出所有旧版本的AppId(每个并行版本对应一个唯一AppId)
  OldAppIdList: TArrayOfString;

function InitializeSetup(): Boolean;
var
  I: Integer;
begin
  Result := True;
  OldAppIdList := ['{旧版本v2的AppId}', '{旧版本v3的AppId}'];
  OldInstallPath := '';

  // 遍历检测旧版本的安装路径(先查HKLM,再查HKCU)
  for I := 0 to GetArrayLength(OldAppIdList) - 1 do
  begin
    if RegQueryStringValue(HKLM, 'Software\Microsoft\Windows\CurrentVersion\Uninstall\' + OldAppIdList[I] + '_is1', 'InstallLocation', OldInstallPath) then
      Break;
    if RegQueryStringValue(HKCU, 'Software\Microsoft\Windows\CurrentVersion\Uninstall\' + OldAppIdList[I] + '_is1', 'InstallLocation', OldInstallPath) then
      Break;
  end;
end;

procedure CurStepChanged(CurStep: TSetupStep);
var
  UninstallExe: String;
  ErrorCode: Integer;
  ConfigPath: String;
begin
  // 安装完成后执行旧版本处理逻辑
  if CurStep = ssPostInstall then
  begin
    if OldInstallPath <> '' then
    begin
      // 1. 迁移用户配置文件(根据实际需要调整文件名)
      ConfigPath := OldInstallPath + '\config.ini';
      if FileExists(ConfigPath) then
      begin
        CopyFile(ConfigPath, ExpandConstant('{app}\config.ini'), False);
      end;

      // 2. 静默卸载旧版本
      UninstallExe := OldInstallPath + '\unins000.exe';
      if FileExists(UninstallExe) then
      begin
        Exec(UninstallExe, '/silent /norestart', '', SW_HIDE, ewWaitUntilTerminated, ErrorCode);
      end;

      // 3. 清理旧目录残留
      if DirectoryExists(OldInstallPath) then
      begin
        RemoveDir(OldInstallPath);
      end;
    end;
  end;
end;

3. 特殊场景适配

  • 旧版本非Inno安装:如果旧版本不是用Inno Setup打包的,可修改InitializeSetup函数,通过遍历{pf}下的MySoftware*格式目录来识别旧路径:
    function InitializeSetup(): Boolean;
    var
      FindRec: TFindRec;
    begin
      Result := True;
      OldInstallPath := '';
      if FindFirst(ExpandConstant('{pf}\MySoftware*'), FindRec) then
      begin
        repeat
          if (FindRec.Attributes and FILE_ATTRIBUTE_DIRECTORY) <> 0 then
          begin
            OldInstallPath := ExpandConstant('{pf}\') + FindRec.Name;
            Break;
          end;
        until not FindNext(FindRec);
        FindClose(FindRec);
      end;
    end;
    
  • 多旧版本共存:如果用户同时安装了多个旧版本,可修改代码遍历所有找到的旧目录,逐个执行迁移、卸载和清理操作。

关键注意事项

  • 新版本AppId必须与旧版本完全不同,确保安装程序能同时识别新旧版本,避免升级逻辑混乱。
  • 迁移配置文件时,需确认文件路径和名称与旧版本一致,避免遗漏用户自定义设置。
  • 测试时需覆盖全新安装、单旧版本升级、多旧版本共存升级等场景,确保流程稳定。

内容的提问来源于stack exchange,提问作者Waits321

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.18 08:22:03