首页 文章

将InstallScope更改为“perMachine”后,如何修复wix设置的升级逻辑

提问于
浏览
13

我们使用wix为我们的应用程序创建设置 . 对于用户已安装旧版本应用程序的情况,我们使用MajorUpgrade XML element进行重大升级 . 这一切都按预期工作:如果安装了旧版本,它将以透明方式升级 . 如果存在较新版本,则安装程序将以明确消息中止 .

但是,我现在想要将InstallScope从"perUser"更改为"perMachine" . 不幸的是,这打破了升级逻辑 . 新安装程序似乎未检测到并删除以前的"perUser"安装 . 相反,它只是在同一ProgramFiles位置的旧版本之上安装 . 用户可以在"add/remove programs"列表中看到两个条目,并在桌面上看到两个相同的快捷方式(旧的用户特定的快捷方式和新的perMachine快捷方式) .

如何在不破坏升级逻辑的情况下将安装程序从“perUser”转换到“perMachine”安装范围?

4 回答

  • 0

    从每台机器配置开始 .

    <Property Id="ALLUSERS" Value="1" />
    

    这将运行一个自动的每机器检查(如果您有MajorUpgrade元素工作,我推测),它不会接收以前的每用户安装:

    Action start 15:46:35: FindRelatedProducts.
    MSI (c) (D0:0C) [15:46:35:496]: FindRelatedProducts: current install is per-machine.  Related install for product '{0C6604FB-58EC-48B9-8259-5871EFDADEB9}' is per-user.  Skipping...
    MSI (c) (D0:0C) [15:46:35:496]: FindRelatedProducts: current install is per-machine.  Related install for product '{0C6604FB-58EC-48B9-8259-5871EFDADEB9}' is per-user.  Skipping...
    

    因此,在安装之前,请确保对已安装在用户范围内的产品运行另一个 FindRelatedProducts 调用(例如,如下所示):

    <!-- temporarily switch to per-user install scope-->   
    <Publish Dialog="MyWelcomeDlg" Control="Next" Property="ALLUSERS" Value="{}">1</Publish>
    <!-- find related products that have been installed per-user -->
    <Publish Dialog="MyWelcomeDlg" Control="Next" Event="DoAction" Value="FindRelatedProducts">1</Publish>
    <!-- switch back to per-machine install scope-->
    <Publish Dialog="MyWelcomeDlg" Control="Next" Property="ALLUSERS" Value="1">1</Publish>
    

    这反过来发现每用户安装:

    Action start 15:46:36: FindRelatedProducts.
    FindRelatedProducts: Found application: {0C6604FB-58EC-48B9-8259-5871EFDADEB9}
    MSI (c) (D0:88) [15:46:36:716]: PROPERTY CHANGE: Adding WIX_UPGRADE_DETECTED property. Its value is '{0C6604FB-58EC-48B9-8259-5871EFDADEB9}'.
    MSI (c) (D0:88) [15:46:36:716]: PROPERTY CHANGE: Adding MIGRATE property. Its value is '{0C6604FB-58EC-48B9-8259-5871EFDADEB9}'.
    

    无论在何处检查,现有产品都将被删除 .

    Action start 15:46:41: RemoveExistingProducts.
    RemoveExistingProducts: Application: {0C6604FB-58EC-48B9-8259-5871EFDADEB9}
    

    另请注意:这并不能解决当您拥有两用安装程序时出现的基本困难:计算机上的User1可能安装在每个用户范围内,然后User2安装每台计算机 . User1将在他的程序/功能表中看到这两个安装,我不知道哪个安装优先 . 因此,请考虑仅按计算机安装 .

  • 7

    遗憾的是,Windows Installer不支持这一点 . 你的软件包外面的一些进程(一个bootstrapper / chainer?)必须管理从每个用户到每个机器的升级 .

  • 1

    您可以使用此技术从每台计算机安装中检测每个用户的安装:http://www.mail-archive.com/wix-users@lists.sourceforge.net/msg35197.html

  • 5

    这将找到现有的perUser和/或perMachine安装 . 并强制新安装到perMachine安装(显然,可以按照您的意愿应用该条件的逻辑) . 这在普通安装运行时以及在LocalSystem(静默升级)下静默安装时有效 . 请记住,它只能在以该用户身份运行时找到perUser安装 .

    创建自定义操作(在DLL中)

    #pragma comment(linker, "/EXPORT:RunFindRelatedProducts=_RunFindRelatedProducts@4")
    extern "C" __declspec(dllexport) UINT __stdcall RunFindRelatedProducts(MSIHANDLE a_hInstall)
    {
    MsiSetProperty(a_hInstall, "ALLUSERS", "1");
    MsiDoAction(a_hInstall, "FindRelatedProducts");
    MsiSetProperty(a_hInstall, "ALLUSERS", "");
    MsiDoAction(a_hInstall, "FindRelatedProducts");
    MsiSetProperty(a_hInstall, "ALLUSERS", "1");
    return ERROR_SUCCESS;
    }//end function
    

    然后使用自定义操作“替换”标准FindRelatedProducts

    <InstallUISequence>
      <FindRelatedProducts>0</FindRelatedProducts>
      <Custom Action="RunFindRelatedProducts" Before='FindRelatedProducts'>NOT Installed</Custom>
    </InstallUISequence>
    <InstallExecuteSequence>
      <FindRelatedProducts>0</FindRelatedProducts>
      <Custom Action="RunFindRelatedProducts" Before='FindRelatedProducts'>NOT Installed</Custom>
    </InstallExecuteSequence>
    

相关问题