Hi Alexander,
A. Regarding the patching problem: your package uses the "File Associations" dialog. As a result, a Component named "ExtReg" is added dynamically to the MSI database during the build process. Therefore, when creating the patch, the Component rules are broken: there is an "ExtReg" Component with different GUIDs for the "Target" and "Upgraded" images.
This is a bug in AI and it will be fixed in the next version which will be released soon.
In the meantime, you will find below a script that sets the GUID of the "ExtReg" Component for a MSI file to the GUID of this Component from another MSI file. This change can also be performed manually using Orca.
Code: Select all
'''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
' extregmod.vbs
' Usage: cscript extregmod.vbs <sourcefile.msi> <destfile.msi>
'
' Script that sets the `ComponentId` column of the ExtReg Component of <destfile.msi>
' to the value of the same column from <sourcefile.msi>
'
' That is, after this script is run, the ExtReg Component of <destfile.msi> will have
' the same GUID as the ExtReg Component of <sourcefile.msi>
'''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
Option Explicit
Const msiOpenDatabaseModeReadOnly = 0
Const msiOpenDatabaseModeDirect = 2
' Show help if no arguments or if argument contains ?
Dim argCount : argCount = Wscript.Arguments.Count
If argCount > 0 Then
If InStr(1, Wscript.Arguments(0), "?", vbTextCompare) > 0 Then
argCount = 0
End If
End If
If argCount < 2 Then
WScript.Echo "Usage: cscript extregmod.vbs <sourcefile.msi> <destfile.msi> " &_
vbLf & "This script sets the GUID of the ExtReg Component of < destfile.msi> " &_
vbLf & "to the GUID of this Component from <sourcefile.msi>" & vbLf &_
vbLf & " The 1st argument is the path to the source MSI file" &_
vbLf & " The 2nd argument is the path to the MSI file that will be modified"
WScript.Quit 1
End If
' Get the paths of the 2 database files
Dim sourceMsiPath : sourceMsiPath = Wscript.Arguments (0)
Dim destMsiPath : destMsiPath = Wscript.Arguments(1)
Wscript.Echo "Database paths: " &_
vbLf & " Source MSI: " & sourceMsiPath &_
vbLf & " Destination MSI: " & destMsiPath & vbLf
' Connect to Windows installer object
On Error Resume Next
Dim installer
Set installer = CreateObject("WindowsInstaller.Installer") : CheckError
WScript.Echo "Connected to Windows Installer object"
Dim database
' Open the source database
Set database = installer.OpenDatabase(sourceMsiPath, _
msiOpenDatabaseModeReadOnly) : CheckError
WScript.Echo "Opened source database"
Dim thecommand,view,record
' Extract the GUID of the "ExtReg" Component
thecommand = "SELECT `Component`.`ComponentId` FROM `Component` " &_
"WHERE `Component`.`Component`='ExtReg'"
Set view = database.OpenView(thecommand) : CheckError
view.Execute : CheckError
Set record = view.Fetch : CheckError
Dim extregGuid : extregGuid = record.StringData(1)
Wscript.Echo " The GUID of the ExtReg Component is " & extregGuid
Set database = Nothing
Set view = Nothing
Set record = Nothing
' Open the destination database
Set database = installer.OpenDatabase(destMsiPath, _
msiOpenDatabaseModeDirect) : CheckError
WScript.Echo "Opened destination database"
thecommand = "UPDATE `Component` SET `Component`.`ComponentId`='" &_
extregGuid & "' WHERE `Component`.`Component`='ExtReg'"
Set view = database.OpenView(thecommand) : CheckError
view.Execute : CheckError
database.Commit : CheckError
WScript.Echo " The GUID of the ExtReg Component has been set successfully"
Set database = Nothing
Set view = Nothing
Set record = Nothing
Set installer = Nothing
Wscript.Echo vbLf & "Done"
Sub CheckError
Dim message, errRec
If Err = 0 Then Exit Sub
message = Err.Source & " " & Hex(Err) & ": " & Err.Description & vbcrlf & query
If Not installer Is Nothing Then
Set errRec = installer.LastErrorRecord
If Not errRec Is Nothing Then message = message & vbLf & errRec.FormatText
End If
Fail message
End Sub
Sub Fail(message)
Wscript.Echo message
Wscript.Quit 2
End Sub
A BAT file that will invoke the script might be useful:
Code: Select all
@echo off
cscript extregmod.vbs original_package.msi upgraded_package.msi
In order to use this script:
1. After building the Target and Upgraded MSI packages, execute the script specifying their paths. This will ensure that the "ExtReg" Component will have the same GUID for both MSI packages. Use a BAT file as specified above.
2. For a minor upgrade patch (that is, the "ProductCode" remains the same, the "ProductVersion" changes), the name of the Upgraded MSI file must be the same as the name of the Target MSI file. Thus, after performing the GUID change operation as specified above, store the 2 MSI packages in different folders and with the same name).
3. Now change the Patch project accordingly and build the MSP between the target and upgraded MSI packages (they will have the same name and the same Component GUIDs).
4. Test the patch on a clean system.
B. Regarding the upgrade problem using a new MSI package: this is a really strange issue and I am not sure what is causing it.
1. Does this happen on the machine on which you have tried previously to apply the patch or on a fresh Windows installation? Because the patch failure may have caused inconsistencies in the Windows Installer configuration information.
2. If this happens on a clean machine, what version of Windows Installer is available on this computer? Determine the version of "msi.dll" from "Windows\system32". Does this problem appear on other computers as well?
3. Create a verbose log when installing each MSI package (the original and then the upgrade MSI). Use the following command to do this:
Code: Select all
msiexec /I package.msi /L*V "C:\package.log"
Send both log files to our support email address so I can investigate this issue further.
I hope this helps.
Regards,
Ionut