super1337 Posted January 2, 2015 Share Posted January 2, 2015 There are certain values I would like to get out of an MSI such as Product Name, Publisher, and Version number. Manually these values can be gathered using ORCA... but is there a way to do it programatically using AutoIT? Link to comment Share on other sites More sharing options...
Moderators Solution JLogan3o13 Posted January 2, 2015 Moderators Solution Share Posted January 2, 2015 Try something like this. It returns all properties, but you could easily have it check only for the ones you want: $sMSI = FileOpenDialog("MSI Properties", @ScriptDir, "Windows Installer Files (*.msi)") $oInstaller = ObjCreate("WindowsInstaller.Installer") $oDB = $oInstaller.OpenDataBase($sMSI, 0) $oView = $oDB.OpenView("SELECT Property,Value FROM Property") $oView.Execute() $oCount = 0 While @error = 0 $oRecords = $oView.Fetch $oPropValue = $oRecords.StringData(2) $oPropName = $oRecords.StringData(1) If $oPropName <> "" Then $oCount += 1 ConsoleWrite($oPropName & " = " & $oPropValue & @CRLF) EndIf WEnd mLipok 1 "Profanity is the last vestige of the feeble mind. For the man who cannot express himself forcibly through intellect must do so through shock and awe" - Spencer W. Kimball How to get your question answered on this forum! Link to comment Share on other sites More sharing options...
super1337 Posted January 6, 2015 Author Share Posted January 6, 2015 (edited) Nice stuff... much simplier than I would have guessed. I made some modifications that might be useful to others for getting a specific MSI Property. $sMSI = FileOpenDialog("MSI Properties", @ScriptDir, "Windows Installer Files (*.msi)") MsgBox(0,0,'ProductName: ' & Execute_MSI_Query($sMSI,'ProductName')) MsgBox(0,0,'Manufacturer: ' & Execute_MSI_Query($sMSI,'Manufacturer')) MsgBox(0,0,'ProductVersion: ' & Execute_MSI_Query($sMSI,'ProductVersion')) Func Execute_MSI_Query($MSIPath, $PropertyName) If FileExists($MSIPath) And $PropertyName <> '' Then Local $Query = "SELECT Value FROM Property WHERE Property = '" & $PropertyName & "'" $oInstaller = ObjCreate("WindowsInstaller.Installer") $oDB = $oInstaller.OpenDataBase($MSIPath, 0) $oView = $oDB.OpenView($Query) $oView.Execute() $oRecords = $oView.Fetch $oPropValue = $oRecords.StringData(1) If $oPropValue <> "" Then Return $oPropValue EndIf EndIf Return "" EndFunc Edited January 6, 2015 by super1337 Link to comment Share on other sites More sharing options...
ur Posted March 21, 2017 Share Posted March 21, 2017 On 1/3/2015 at 2:58 AM, JLogan3o13 said: Try something like this. It returns all properties, but you could easily have it check only for the ones you want: $sMSI = FileOpenDialog("MSI Properties", @ScriptDir, "Windows Installer Files (*.msi)") $oInstaller = ObjCreate("WindowsInstaller.Installer") $oDB = $oInstaller.OpenDataBase($sMSI, 0) $oView = $oDB.OpenView("SELECT Property,Value FROM Property") $oView.Execute() $oCount = 0 While @error = 0 $oRecords = $oView.Fetch $oPropValue = $oRecords.StringData(2) $oPropName = $oRecords.StringData(1) If $oPropName <> "" Then $oCount += 1 ConsoleWrite($oPropName & " = " & $oPropValue & @CRLF) EndIf WEnd I am getting error as below, when I execute this code for last record. "C:\Users\ukreddy\Desktop\test.au3" (19) : ==> The requested action with this object has failed.: $oPropValue = $oRecords.StringData(2) $oPropValue = $oRecords^ ERROR ->14:59:31 AutoIt3.exe ended.rc:1 +>14:59:31 AutoIt3Wrapper Finished. But the @error is 0 for it. Link to comment Share on other sites More sharing options...
Moderators JLogan3o13 Posted March 21, 2017 Moderators Share Posted March 21, 2017 @ur Is it failing on a particular property? Have you tried it on multiple MSIs to ensure it is not something specific to the Property table of the one file? "Profanity is the last vestige of the feeble mind. For the man who cannot express himself forcibly through intellect must do so through shock and awe" - Spencer W. Kimball How to get your question answered on this forum! Link to comment Share on other sites More sharing options...
ur Posted March 21, 2017 Share Posted March 21, 2017 Yeah @JLogan3o13, I tried on multiple msi files. It is failing for the last value in the table. Maybe the @error = 0 is not the valid one to check the end of table. Link to comment Share on other sites More sharing options...
Moderators JLogan3o13 Posted March 21, 2017 Moderators Share Posted March 21, 2017 Perhaps not, it has been a long time since I posted that. I will take a look when I get a few moments to see what may have changed. "Profanity is the last vestige of the feeble mind. For the man who cannot express himself forcibly through intellect must do so through shock and awe" - Spencer W. Kimball How to get your question answered on this forum! Link to comment Share on other sites More sharing options...
Moderators JLogan3o13 Posted March 21, 2017 Moderators Share Posted March 21, 2017 I am looking for a graceful "end of table" marker. But as a workaround you could just check to see if the object exists: $sMSI = FileOpenDialog("MSI Properties", @ScriptDir, "Windows Installer Files (*.msi)") $oInstaller = ObjCreate("WindowsInstaller.Installer") $oDB = $oInstaller.OpenDataBase($sMSI, 0) $oView = $oDB.OpenView("SELECT Property,Value FROM Property") $oView.Execute() $oCount = 0 While @error = 0 $oRecords = $oView.Fetch If Not (IsObj($oRecords)) Then ExitLoop ;<====== $oPropValue = $oRecords.StringData(2) $oPropName = $oRecords.StringData(1) If $oPropName <> "" Then $oCount += 1 ConsoleWrite($oPropName & " = " & $oPropValue & @CRLF) EndIf WEnd "Profanity is the last vestige of the feeble mind. For the man who cannot express himself forcibly through intellect must do so through shock and awe" - Spencer W. Kimball How to get your question answered on this forum! Link to comment Share on other sites More sharing options...
ur Posted March 21, 2017 Share Posted March 21, 2017 Thanks @JLogan3o13.. Link to comment Share on other sites More sharing options...
Moderators JLogan3o13 Posted March 21, 2017 Moderators Share Posted March 21, 2017 In fact, since I am playing around with it (I had completely forgotten doing this one), I would probably do something like this, rather than a ConsoleWrite. Hindsight #include <Array.au3> Local $aProperties[1][2] = [["Name", "Value"]] Local $oRecords, $oPropName, $oPropValue, $iCount = 0 Local $sMSI = FileOpenDialog("MSI Properties", @ScriptDir, "Windows Installer Files (*.msi)") Local $oInstaller = ObjCreate("WindowsInstaller.Installer") Local $oDB = $oInstaller.OpenDataBase($sMSI, 0) Local $oView = $oDB.OpenView("SELECT * FROM Property") $oView.Execute() While @error = 0 $oRecords = $oView.Fetch If Not (IsObj($oRecords)) Then ExitLoop $oPropName = $oRecords.StringData(1) $oPropValue = $oRecords.StringData(2) If $oPropName <> "" Then $iCount += 1 _ArrayAdd($aProperties, $oPropName & "|" & $oPropValue) EndIf WEnd _ArraySort($aProperties, 0, 1) _ArrayDisplay($aProperties) Subz 1 "Profanity is the last vestige of the feeble mind. For the man who cannot express himself forcibly through intellect must do so through shock and awe" - Spencer W. Kimball How to get your question answered on this forum! Link to comment Share on other sites More sharing options...
ur Posted March 21, 2017 Share Posted March 21, 2017 (edited) Hi @JLogan3o13 The program is not executing when the below query is executed. Any idea? $fname = "Complete" Local $oView = $oDB.OpenView("SELECT Component_,Directory FROM FeatureComponents,Component where FeatureComponents.Component_=Component.Component AND Feature_ = '"&$fname&"'") $oView.Execute() Edited March 22, 2017 by ur Link to comment Share on other sites More sharing options...
Recommended Posts
Create an account or sign in to comment
You need to be a member in order to leave a comment
Create an account
Sign up for a new account in our community. It's easy!
Register a new accountSign in
Already have an account? Sign in here.
Sign In Now