如何构建Wix安装程序升级以将GAC组件移动到常规文件夹中?

时间:2014-08-13 20:42:10

标签: wix windows-installer com-interop gac

我有一个现有的安装,其中包括为COM Interop注册并安装在GAC中的.NET程序集。这些DLL仅由我们也包含在安装中的非托管EXE使用。

一个简单的示例组件(从真实的东西混淆)看起来像这样:

  <Component Id="MyApp.ClientInterop.dll" Guid="{9A9C2B62-531C-4E60-ABD2-EDD447643C4F}">
    <Class Id="{963057C7-83B4-4602-87B4-B0AB9D3D149A}" Context="InprocServer32" Description="MyApp.ClientInterop.ClientAppUpdate" ThreadingModel="both" ForeignServer="mscoree.dll">
      <ProgId Id="MyApp_Interop.ClientAppUpdate" Description="MyApp.ClientInterop.ClientAppUpdate" />
    </Class>
    <File Id="MyApp.ClientInterop.dll" Name="MyApp.ClientInterop.dll" KeyPath="yes" Assembly=".net">
      <TypeLib Id="{08963623-70A8-4DD8-A8DA-EAF209919797}" Description="MyApp_ClientInterop" Language="0" MajorVersion="1" MinorVersion="0">
        <Interface Id="{207BB6C4-3054-4853-BA20-40D99EA6ACFE}" Name="IClientAppUpdate" ProxyStubClassId="{00020424-0000-0000-C000-000000000046}" ProxyStubClassId32="{00020424-0000-0000-C000-000000000046}" />
      </TypeLib>
    </File>
    <RegistryValue Root="HKCR" Key="CLSID\{963057C7-83B4-4602-87B4-B0AB9D3D149A}\Implemented Categories\{62C8FE65-4EBB-45e7-B440-6E39B2CDBF29}" Value="" Type="string" Action="write" />
    <RegistryValue Root="HKCR" Key="CLSID\{963057C7-83B4-4602-87B4-B0AB9D3D149A}\InprocServer32\1.0.0.0" Name="Class" Value="MyApp.ClientInterop.ClientAppUpdate" Type="string" Action="write" />
    <RegistryValue Root="HKCR" Key="CLSID\{963057C7-83B4-4602-87B4-B0AB9D3D149A}\InprocServer32\1.0.0.0" Name="Assembly" Value="MyApp.ClientInterop, Version=1.0.0.0, Culture=neutral, PublicKeyToken=cf47a01d50a7b0f5" Type="string" Action="write" />
    <RegistryValue Root="HKCR" Key="CLSID\{963057C7-83B4-4602-87B4-B0AB9D3D149A}\InprocServer32\1.0.0.0" Name="RuntimeVersion" Value="v4.0.30319" Type="string" Action="write" />
    <RegistryValue Root="HKCR" Key="CLSID\{963057C7-83B4-4602-87B4-B0AB9D3D149A}\InprocServer32" Name="Class" Value="MyApp.ClientInterop.ClientAppUpdate" Type="string" Action="write" />
    <RegistryValue Root="HKCR" Key="CLSID\{963057C7-83B4-4602-87B4-B0AB9D3D149A}\InprocServer32" Name="Assembly" Value="MyApp.ClientInterop, Version=1.0.0.0, Culture=neutral, PublicKeyToken=cf47a01d50a7b0f5" Type="string" Action="write" />
    <RegistryValue Root="HKCR" Key="CLSID\{963057C7-83B4-4602-87B4-B0AB9D3D149A}\InprocServer32" Name="RuntimeVersion" Value="v4.0.30319" Type="string" Action="write" />
  </Component>

由于以下几个原因,我不想进入这里,我们想重新设计应用程序,让DLL存放在包含可执行文件的文件夹中,而不是在GAC中。

这可以通过主要升级来完成,而无需用户完全卸载以前的版本。我们的安装程序已按顺序排列,因此在最终确定期间会删除旧版本,因为大多数升级只会更改一小部分组件。

我最初计划对每个GAC组件进行以下更改:

  1. 删除程序集=&#34; .Net&#34;属性
  2. 在Component元素上生成新的Guid
  3. 这应该适用于文件系统。但是,我不确定,,,和元素会发生什么。如果我不更改它们,我怀疑当旧版本在最后卸载时会将其删除,从而导致安装损坏。

    这是一个准确的解释吗?这是否意味着我需要为所有Interop类强制新的Interface / Typelib / CLSID值?我通过Interop在这个项目中有超过1000个课程。

    我可以更改顺序,以便先安装旧产品吗?我担心这样做是因为这意味着我必须坚持这个顺序,直到我能确定我的所有客户都超出了那个版本。它还将显着增加安装程序时间(之前已经过测试)。

    也许还有其他选择我不知道?

1 个答案:

答案 0 :(得分:0)

在开始时使用RemoveExistingProducts进行主要升级会更安全,可以说是一个干净的平板。但是我认为如果符合以下情况,它最终会与REP一起使用:

  1. 您的程序集将获得一个新的组件guid,以便从GAC中删除旧的产品程序集。

  2. 注册表项未进行版本控制,因此始终会覆盖它们。您应该能够保留相同的WiX组件ID,但无论如何您都需要添加CodeBase位置,因此应该很容易看出它是否全部工作。显然,在升级之后,您不需要GAC中的程序集,普通文件系统中的程序集以及指向它们的CodeBase注册表项,以及可以将其称为ok的客户端:)