我有一个为我们公司维护的InstallShield 2012 Basic MSI项目。我不是一个训练有素的InstallShield开发人员(仅仅是图腾柱上最低的[当时]),但是我已经在几个月内完成了从版本到版本的顺利运行。
最近,我们的一位客户坚持要求修复我们已在最新版本中修复过的旧版本产品中的错误。我们通常不会创建补丁,因为完整的安装程序兼作更新程序,但在这个例子中我们遵守,在他们所处的版本创建了分支,并向他们发送了更新补丁。该补丁中只包含一个文件,并且它与要替换的文件具有相同的版本。一切都很好。
今天,客户希望升级到我们的最新版本。实际上我们正在将他们的分支合并回主线,并且由于他们的分支没有额外的组件或客户端特定的代码,我认为我们可以简单地给他们我们的常规安装程序并覆盖所有内容。不是这样......
当我复制他们的分支安装并尝试更新文件时,安装程序成功运行并替换所有内容但是它们的分支dll。修补' omus' amus',强制覆盖等等,什么都不改变。事先删除文件不会做任何事情。无论我尝试什么,分支dll仍然存在,日志看起来像这样(名称更改,以保护有罪,版本和guids保持完整):
正确更新的DLL:
Executing op: RegisterSharedComponentProvider(,,File=dll_that_works.r1,Component={B4F132E0-6C2A-4138-990B-16B991F8C54D},ComponentVersion=1.1.1.195,ProductCode={B2F1D6AC-95A4-44A9-9A52-631A3AD14389},ProductVersion=1.1.1,PatchSize=0,PatchAttributes=0,PatchSequence=0,SharedComponent=0,IsFullFile=0)
Executing op: FileCopy(SourceName=SY2F9C~1.DLL|dll_that_works.dll,SourceCabKey=dll_that_works.r1,DestName=dll_that_works.dll,Attributes=16384,FileSize=51584,PerTick=65536,,VerifyMedia=1,,,,,CheckCRC=0,Version=1.1.1.195,Language=0,InstallMode=130023424,,,,,,,)
File: C:\inetpub\wwwroot\Service\bin\dll_that_works.dll; Overwrite; Won't patch; REINSTALLMODE specifies all files to be overwritten
Source for file 'dll_that_works.r1' is compressed
不更新的分支DLL:
Executing op: SetSourceFolder(Folder=C:\Windows\Installer\$PatchCache$\Managed\CA6D1F2B4A599A44A92536A1A31D3498\1.1.1)
Executing op: RegisterSharedComponentProvider(PatchGUID={EC6657A6-01A1-4AFC-86F9-1F4BF5F15481},MediaCabinet=#PCW_CAB_Family1,File=branched_dll.r,Component={74531F91-82A9-421D-A227-15DDDEDFC2FA},ComponentVersion=1.1.1.195,ProductCode={B2F1D6AC-95A4-44A9-9A52-631A3AD14389},ProductVersion=1.1.1,PatchSize=35952,PatchAttributes=0,PatchSequence=10000,SharedComponent=0,IsFullFile=0)
Executing op: FileCopy(SourceName=branched_dll.r,SourceCabKey=branched_dll.r,DestName=branched_dll.dll,Attributes=0,FileSize=225664,PerTick=65536,,VerifyMedia=0,,TotalPatches=1,,,CheckCRC=0,Version=1.1.1.195,Language=0,InstallMode=130023424,,,,,,,)
File: C:\inetpub\wwwroot\Service\bin\branched_dll.dll; Overwrite; Smart patch; REINSTALLMODE specifies all files to be overwritten
Redirecting file copy of 'C:\inetpub\wwwroot\Service\bin\branched_dll.dll' to 'C:\Config.Msi\PTB2C9.tmp'. A subsequent patch will update the intermediate file, and then copy over the original.
Source for file 'branched_dll.r' is uncompressed, at 'C:\Windows\Installer\$PatchCache$\Managed\CA6D1F2B4A599A44A92536A1A31D3498\1.1.1\'.
这有点超出我的深度。接近我可以告诉它正在尝试修补分支的DLL,不能这样做,并且由于某种原因将文件抛出到临时目录中(我无法找到关于究竟是什么&smart?补丁'手段)。我已经看到应用于错误版本的补丁会发生这种情况,但这不是一个补丁!它是使用REINSTALLMODE = v(oa)mus和REINSTALL = ALL运行的常规安装程序。它应该只看到旧版本,看到它嵌入了更新的版本,并将旧版本吹走。
(一时兴起,我尝试手动更新DLL,而不是使用我们给客户端的更新程序。一切都正确更新,所以它不会阻塞文件本身)
我的直接目标是让这个客户端恢复同步,最好没有任何卸载和一个统一的安装程序,而不是为他们创建一个特殊的更新程序。由于文件已经存在,如果不可行,我可以忍受特殊情况。我的未来目标是让这个工作自然地像我想象的那样 - 文件是旧版本,文件被替换,没有其他重要。
我认为我提供了相关的一切,但如果没有,我可以提供更多信息。我今天花了很多时间来看这个,我根本无法找到任何类似于这种情况的材料。
答案 0 :(得分:2)
根据您对场景的描述,它听起来像您为客户打补丁的组件的密钥文件的“修改日期”可能晚于升级包中的日期,但版本是相同的。 Windows Installer可能无法替换该文件。请参阅Replacing Existing Files以及FileF
行中的示例在应用最新升级之前,此客户可能需要使用卸载已修补组件的自定义程序包。