Visual Basic Code , VB.NET Code, VB Code
  Home   :  Code   :  Forums   :  Submit   :  Mailing List   :  About   :  Contact


Problems Determining Patch Application State - WindowsInstaller


Problems Determining Patch Application State - WindowsInstaller

Author
Message
Superfreak3
Superfreak3
Forum God
Forum God (678 reputation)Forum God (678 reputation)Forum God (678 reputation)Forum God (678 reputation)Forum God (678 reputation)Forum God (678 reputation)Forum God (678 reputation)Forum God (678 reputation)Forum God (678 reputation)

Group: Forum Members
Posts: 2, Visits: 4
Hi all,

I hope someone can help me here.  There aren't many good code examples out there dealing with Windows Installer patches (.msp).  We have an update widget that will install or apply a patch simply if the .msp is located in the application's update folder location.  I want to try to change that to first, determine if the patch actually needs to be applied.

First, I need to grab the Patch/Product codes from the .msp, then check the Patch.State against the Product Code.  The first part is working fine, but I'm having problems checking the State...

  1. Const MinMsiVersion = "3.0" 'Minimum version to support functionality
  2. Const MSIPATCHSTATE_APPLIED = 1 'Patch is applied to this product instance.
  3. Const msiInstallContextMachine = 4 'Enumerate products that are under the machine account.
  4.  
  5. Dim iInstaller As WindowsInstaller.Installer
  6. Dim pPatch 'As WindowsInstaller.Patch
  7.         '= CreateObject("WindowsInstaller.Installer")
  8.  
  9. Dim strPatchPath, _
  10.     strPatchCode, _
  11.     strProdCode As String
  12. Dim strPatchXML As String
  13. Dim xmlMsiPatch As XmlDocument = New XmlDocument()
  14.  
  15. Try      
  16.     If MinMsiVersion > iInstaller.Version Then
  17.         MsgBox("Minimum Windows Installer version " & MinMsiVersion & " required.  Current version is " & iInstaller.Version, MsgBoxStyle.OkOnly, "Windows Installer version problem...")
  18.     End If
  19.  
  20.     iInstaller = CType(CreateObject("WindowsInstaller.Installer"),  _
  21.                    WindowsInstaller.Installer)
  22.  
  23.     strPatchPath = "C:\Program Files (x86)\MyComp\Adept80\MyApp\Install\MyAppPatch.msp"
  24.     strPatchXML = iInstaller.ExtractPatchXMLData(strPatchPath)
  25.  
  26.     xmlMsiPatch.LoadXml(strPatchXML)
  27.  
  28.     strPatchCode = xmlMsiPatch.DocumentElement.Attributes("PatchGUID").Value
  29.     strProdCode = xmlMsiPatch.GetElementsByTagName("TargetProductCode").Item(0).InnerText
  30.  
  31.     pPatch = iInstaller.Patch(strPatchCode, strProdCode, "", msiInstallContextMachine)
  32.  
  33.     If pPatch.State = MSIPATCHSTATE_APPLIED Then 'already applied
  34.         MsgBox("Write to log... Patch has already been applied (" & pPatch.State & ")!")
  35.     Else
  36.         MsgBox("I'm installing the patch")
  37.     End If
  38.  
  39. Catch ex As Exception
  40.     MsgBox(Err.Number)
  41.     MsgBox(Err.Description)
  42.     'MsgBox(ex.Message)
  43.     MsgBox(ex.ToString)
  44.  
  45.     'ERROR_PATCH_NOT_APPLIED
  46. End Try

 

This code is failing on line 31 with an error 13 - Return Argument Has An Invalid Type.  Can anyone help get me around this?  I've attached an image with some more info from this error.

 

Since all of this may have to be ported to C++, I wonder if its better to try to get the following code up and running...

 

  1. Const MinMsiVersion = "3.0" 'Minimum version to support functionality
  2. Const MSIPATCHSTATE_APPLIED = 1 'Patch is applied to this product instance.
  3. Const msiInstallContextMachine = 4 'Enumerate products that are under the machine account.
  4.  
  5. Dim iInstaller = CreateObject("WindowsInstaller.Installer")
  6.  
  7. Dim strPatchPath, _
  8.     strPatchCode, _
  9.     strProdCode As String
  10. Dim strPatchXML As String
  11. Dim xmlMsiPatch As XmlDocument = New XmlDocument()
  12.  
  13. Try
  14.  
  15. If MinMsiVersion > iInstaller.Version Then
  16.      MsgBox("Minimum Windows Installer version " & MinMsiVersion & " required.  Current version is " & iInstaller.Version, MsgBoxStyle.OkOnly, "Windows Installer version problem...")
  17. End If
  18.  
  19. strPatchPath = "C:\Program Files (x86)\MyComp\MyApp\Client\Install\MyAppPatch.msp"
  20. strPatchXML = iInstaller.ExtractPatchXMLData(strPatchPath)
  21.  
  22. xmlMsiPatch.LoadXml(strPatchXML)
  23.  
  24. strPatchCode = xmlMsiPatch.DocumentElement.Attributes("PatchGUID").Value
  25. strProdCode = xmlMsiPatch.GetElementsByTagName("TargetProductCode").Item(0).InnerText
  26.  
  27. Dim pPatch = iInstaller.Patch(strPatchCode, strProdCode, "", msiInstallContextMachine)
  28.  
  29. If pPatch.State = MSIPATCHSTATE_APPLIED Then 'already applied
  30.     MsgBox("Write to log... Patch has already been applied (" & pPatch.State & ")!")
  31. Else
  32.     MsgBox("I'm installing the patch")
  33. End If
  34.  
  35. Catch ex As Exception
  36.     MsgBox(Err.Number)
  37.     MsgBox(Err.Description)
  38.     'MsgBox(ex.Message)
  39.     MsgBox(ex.ToString)
  40.  
  41.     'ERROR_PATCH_NOT_APPLIED
  42. End Try

 

However this code snippet was failing on...

If pPatch.State = MSIPATCHSTATE_APPLIED Then

The error number I eventually was able to get from it was -21470223249 which after digging a bit I found was ERROR_PATCH_NOT_APPLIED.

I'm not currently able to handle if the patch has not been applied with this code. If the patch is installed, the return, 1, is fine and the log write would occur (in this case msgbox). If not installed or applied, BOOM!

In the first code snipped, these were the imports...

Imports WindowsInstaller
Imports System
Imports System.Xml

In the second code segment, Windowsinstaller was commented out.

I hope someone can help me as I think/hope I am very close to having some workable code to detect if a patch has been applied!

Thanks in advance for any help!!!

THANKS FOR YOUR HELP!!

Attachments
MyError.jpg (628 views, 81.00 KB)
Edited
3/15/2013 by Superfreak3
Superfreak3
Superfreak3
Forum God
Forum God (678 reputation)Forum God (678 reputation)Forum God (678 reputation)Forum God (678 reputation)Forum God (678 reputation)Forum God (678 reputation)Forum God (678 reputation)Forum God (678 reputation)Forum God (678 reputation)

Group: Forum Members
Posts: 2, Visits: 4
Here's what we've come up with.  Seems to work, hope it helps someone out there...

Type t = Type.GetTypeFromProgID("WindowsInstaller.Installer");
                Installer iInstaller = (Installer)Activator.CreateInstance(t);

                string strPatchPath = null;
                string strPatchCode = null;
                string strProdCode = null;
                string strPatchXML = null;
                XmlDocument xmlMsiPatch = new XmlDocument();

               

                if (MinMsiVersion > Convert.ToDouble(iInstaller.Version.Substring(0, iInstaller.Version.IndexOf('.'))))
                {
                    MessageBox.Show("Minimum Windows Installer version " + MinMsiVersion + " required.  Current version is " + iInstaller.Version, "Windows Installer version problem...");
                }

                strPatchPath = "C:\\Program Files (x86)\\Synergis\\Adept80\\Client\\Install\\AdeptPatch.msp";
                strPatchXML = iInstaller.ExtractPatchXMLData(strPatchPath);

                xmlMsiPatch.LoadXml(strPatchXML);

                strPatchCode = xmlMsiPatch.DocumentElement.Attributes["PatchGUID"].Value;
                strProdCode = xmlMsiPatch.GetElementsByTagName("TargetProductCode").Item(0).InnerText;

                //Now check if patch is applied...

                int rtn = 0;
                dynamic ePatch = iInstaller.get_Patches(strProdCode);
 
                if (ePatch.count > 0)
                {
                    for (var i = 0; i < ePatch.count; i++)
                    {
                        if (ePatch[i] == strPatchCode)
                        {
                            MessageBox.Show("here");
                            rtn = 1;
                        }

                    }
                }



THANKS FOR YOUR HELP!!
GO


Similar Topics


Reading This Topic


Login
Existing Account
Email Address:


Password:


Social Logins

Select a Forum....

















A1VBCode Forums


Search