MSI Analysis Reporting Tool






Here is a tool I have written that generates a report on all of the variables used for each entry during an MSI installation. I wrote this script to make customizing the installation of MSI files much easier and quicker. The way this script works is that it will install the MSI file and then come back and uninstall it. It will produce a verbose text file which the script will read from to produce the report.

To use this script, just copy it to the same location as the MSI and execute it. If there is more than one MSI within the directory, you will be prompted on which one to execute. The script will then pop up a blank notepad file. This is to populate with all of your test responses during the setup. For each box you type a text entry into, copy and paste that into the notepad file making a single line entry for each text box. 

If you see a folder window, click change and then copy the directory listed. This will then report the variable associated with the folder.

For radio button boxes, you can enter part of the name of the button, or the entire name. Some radio buttons have the ampersand within the name. It is does, this will not detect it, therefor you will need to enter part of the name. 

The features will be automatically detected, so there is no need to enter those into the text file. The selected features will be read from the log file.

In the end, the report will be published on the screen and to the report.txt file. The following data will be in the report: Product Name, Product Code, MSI Filename, Properties, Features, and Buttons.

NOTE: If you are going to execute the script from a command prompt, make sure the command prompt is also residing in the same directory as the script.

Here is an example report.txt file of packaging InterAction



This was the text input file used during the installation that helped generate the above report:
You can download the script from here.


1:  <#       
2: .NOTES
3: ===========================================================================
4: Created with: SAPIEN Technologies, Inc., PowerShell Studio 2015 v4.2.90
5: Created on: 27 July 2015 9:24 AM
6: Created by: Mick Pletcher
7: Organization:
8: Filename: MSIAnalyzer.ps1
9: ===========================================================================
10: .DESCRIPTION
11: This script will uninstall all previous versions of SCCM Client,
12: including the execution of the ccmclean.exe to rid the system of
13: any remnants of the previous client. It will then install the new
14: client and wait until the client is installed and is communicating
15: with the SCCM server.
16:
17: #>
18:
19: #Declare Global Variables
20: Set-Variable -Name ApplicationName -Scope Global -Force
21: Set-Variable -Name MSI -Scope Global -Force
22: Set-Variable -Name ProductCode -Scope Global -Force
23:
24: function Get-RelativePath {
25: #Declare Local Variables
26: Set-Variable -Name RelativePath -Scope Local -Force
27:
28: $RelativePath = (split-path $SCRIPT:MyInvocation.MyCommand.Path -parent) + "\"
29: Return $RelativePath
30:
31: #Cleanup Local Variables
32: Remove-Variable -Name RelativePath -Scope Local -Force
33: }
34:
35: function Get-Architecture {
36: #Declare Local Variables
37: Set-Variable -Name Architecture -Scope Local -Force
38:
39: $Architecture = Get-WmiObject -Class Win32_OperatingSystem | Select-Object OSArchitecture
40: $Architecture = $Global:Architecture.OSArchitecture
41: Return $Architecture
42:
43: #Cleanup Local Variables
44: Remove-Variable -Name Architecture -Scope Local -Force
45: }
46:
47: function ProcessTextFiles {
48: #Declare Local Variables
49: Set-Variable -Name RelativePath -Scope Local -Force
50:
51: If ((Test-Path -Path $RelativePath"Installer.log") -eq $true) {
52: Remove-Item -Path $RelativePath"Installer.log" -Force
53: }
54: If ((Test-Path -Path $RelativePath"UserInput.txt") -eq $true) {
55: Remove-Item -Path $RelativePath"UserInput.txt" -Force
56: }
57: If ((Test-Path -Path $RelativePath"Report.txt") -eq $true) {
58: Remove-Item -Path $RelativePath"Report.txt" -Force
59: }
60:
61: #Cleanup Local Variables
62: Remove-Variable -Name RelativePath -Scope Local -Force
63: }
64:
65: function Get-MSIFile {
66: #Declare Local Variables
67: Set-Variable -Name FileCount -Value 1 -Scope Local -Force
68: Set-Variable -Name MSIFile -Scope Local -Force
69: Set-Variable -Name RelativePath -Scope Local -Force
70:
71: $RelativePath = Get-RelativePath
72: $MSIFile = Get-ChildItem $RelativePath -Filter *.msi
73: Write-Host $MSIFile.Count
74: If ($MSIFile.Count -eq 1) {
75: Return $MSIFile
76: } else {
77: Do {
78: Clear-Host
79: $FileCount = 1
80: Write-Host "Select MSI to process:"
81: foreach ($MSI in $MSIFile) {
82: Write-Host $FileCount" - "$MSI
83: $FileCount++
84: }
85: Write-Host
86: Write-Host "Selection:"
87: [int]$input = Read-Host
88: } while (($input -eq $null) -or ($input -eq "") -or ($input -gt $MSIFile.Count) -or (!($input -as [int] -is [int])))
89: $input = $input - 1
90: $MSIFile = $MSIFile[$input]
91: $global:MSI = $RelativePath + $MSIFile
92: }
93:
94: #Cleanup Local Variables
95: Remove-Variable -Name FileCount -Scope Local -Force
96: Remove-Variable -Name MSIFile -Scope Local -Force
97: Remove-Variable -Name RelativePath -Scope Local -Force
98: }
99:
100: function Get-MSIFileInfo {
101: param (
102: [parameter(Mandatory = $true)][IO.FileInfo]
103: $Path,
104: [parameter(Mandatory = $true)][ValidateSet("ProductCode", "ProductVersion", "ProductName")][string]
105: $Property
106: )
107:
108: #Declare Local Variables
109: Set-Variable -Name MSIDatabase -Scope Local -Force
110: Set-Variable -Name Query -Scope Local -Force
111: Set-Variable -Name Record -Scope Local -Force
112: Set-Variable -Name Value -Scope Local -Force
113: Set-Variable -Name View -Scope Local -Force
114: Set-Variable -Name WindowsInstaller -Scope Local -Force
115:
116: try {
117: $WindowsInstaller = New-Object -ComObject WindowsInstaller.Installer
118: $MSIDatabase = $WindowsInstaller.GetType().InvokeMember("OpenDatabase", "InvokeMethod", $Null, $WindowsInstaller, @($Path.FullName, 0))
119: $Query = "SELECT Value FROM Property WHERE Property = '$($Property)'"
120: $View = $MSIDatabase.GetType().InvokeMember("OpenView", "InvokeMethod", $null, $MSIDatabase, ($Query))
121: $View.GetType().InvokeMember("Execute", "InvokeMethod", $null, $View, $null)
122: $Record = $View.GetType().InvokeMember("Fetch", "InvokeMethod", $null, $View, $null)
123: $Value = $Record.GetType().InvokeMember("StringData", "GetProperty", $null, $Record, 1)
124: return $Value
125: } catch {
126: Write-Output $_.Exception.Message
127: }
128:
129: #Declare Local Variables
130: Remove-Variable -Name MSIDatabase -Scope Local -Force
131: Remove-Variable -Name Query -Scope Local -Force
132: Remove-Variable -Name Record -Scope Local -Force
133: Remove-Variable -Name Value -Scope Local -Force
134: Remove-Variable -Name View -Scope Local -Force
135: Remove-Variable -Name WindowsInstaller -Scope Local -Force
136: }
137:
138: function New-UserInputFile {
139: #Declare Local Variables
140: Set-Variable -Name ErrCode -Scope Local -Force
141: Set-Variable -Name RelativePath -Scope Local -Force
142:
143: $RelativePath = Get-RelativePath
144: If ((Test-Path -Path $RelativePath"UserInput.txt") -eq $true) {
145: Remove-Item -Path $RelativePath"UserInput.txt" -Force
146: }
147: Write-Host "Creating UserInput.txt File....." -NoNewline
148: $ErrCode = New-Item -Path $RelativePath"UserInput.txt" -Type File -Force
149: If ((Test-Path -Path $RelativePath"UserInput.txt") -eq $true) {
150: Write-Host "Success" -ForegroundColor Yellow
151: } else {
152: Write-Host "Failed" -ForegroundColor Red
153: }
154:
155: #Cleanup Local Variables
156: Remove-Variable -Name ErrCode -Scope Local -Force
157: Remove-Variable -Name RelativePath -Scope Local -Force
158:
159: }
160:
161: function Install-MSI {
162: #Declare Local Variables
163: Set-Variable -Name ErrCode -Scope Local -Force
164: Set-Variable -Name Executable -Scope Local -Force
165: Set-Variable -Name MSI -Scope Local -Force
166: Set-Variable -Name Parameters -Scope Local -Force
167: Set-Variable -Name RelativePath -Scope Local -Force
168: Set-Variable -Name Switches -Scope Local -Force
169:
170: $RelativePath = Get-RelativePath
171: $Global:ApplicationName = Get-MSIFileInfo -Path $global:MSI -Property 'ProductName'
172: $Global:ProductCode = Get-MSIFileInfo -Path $global:MSI -Property 'ProductCode'
173: If ((Test-Path -Path $RelativePath"Installer.log") -eq $true) {
174: Remove-Item -Path $RelativePath"Installer.log" -Force
175: }
176: $Executable = $Env:windir + "\system32\msiexec.exe"
177: $Switches = "/qb- /norestart"
178: $Parameters = "/x" + [char]32 + $Global:ProductCode + [char]32 + $Switches
179: $ErrCode = (Start-Process -FilePath $Executable -ArgumentList $Parameters -Wait -Passthru).ExitCode
180: Write-Host "Uninstalling"$Global:ApplicationName"....." -NoNewline
181: if (($ErrCode -eq 0) -or ($ErrCode -eq 3010)) {
182: Write-Host "Success" -ForegroundColor Yellow
183: } else {
184: Write-Host "Failed with error code "$ErrCode -ForegroundColor Red
185: }
186: $Notepad = $env:windir + "\notepad.exe"
187: $Parameters = $RelativePath + "UserInput.txt"
188: $ErrCode = (Start-Process -FilePath $Notepad -ArgumentList $Parameters -PassThru).ExitCode
189: $Switches = "/norestart"
190: $Parameters = "/i " + [char]34 + $Global:MSI + [char]34 + [char]32 + $Switches + [char]32 + "/lvx " + [char]34 + $RelativePath + "Installer.log" + [char]34
191: Write-Host $Parameters
192: Write-Host "Installing"$Global:ApplicationName"....." -NoNewline
193: $ErrCode = (Start-Process -FilePath $Executable -ArgumentList $Parameters -Wait -Passthru).ExitCode
194: if (($ErrCode -eq 0) -or ($ErrCode -eq 3010)) {
195: Write-Host "Success" -ForegroundColor Yellow
196: } else {
197: Write-Host "Failed with error code "$ErrCode -ForegroundColor Red
198: }
199: Write-Host "Creating Log File....." -NoNewline
200: If ((Test-Path $RelativePath"Installer.log") -eq $true) {
201: Write-Host "Success" -ForegroundColor Yellow
202: } else {
203: Write-Host "Failed" -ForegroundColor Red
204: }
205:
206: #Cleanup Local Variables
207: Remove-Variable -Name ErrCode -Scope Local -Force
208: Remove-Variable -Name Executable -Scope Local -Force
209: Remove-Variable -Name MSI -Scope Local -Force
210: Remove-Variable -Name Parameters -Scope Local -Force
211: Remove-Variable -Name RelativePath -Scope Local -Force
212: Remove-Variable -Name Switches -Scope Local -Force
213: }
214:
215: function Uninstall-MSI {
216: #Declare Local Variables
217: Set-Variable -Name ErrCode -Scope Local -Force
218: Set-Variable -Name Executable -Scope Local -Force
219: Set-Variable -Name Line -Scope Local -Force
220: Set-Variable -Name LogFile -Scope Local -Force
221: Set-Variable -Name MSI -Scope Local -Force
222: Set-Variable -Name Parameters -Scope Local -Force
223: Set-Variable -Name Process -Scope Local -Force
224: Set-Variable -Name RelativePath -Scope Local -Force
225: Set-Variable -Name Switches -Scope Local -Force
226:
227: $RelativePath = Get-RelativePath
228: $Process = Get-Process -Name notepad -ErrorAction SilentlyContinue
229: If ($Process -ne $null) {
230: Stop-Process -Name notepad -ErrorAction SilentlyContinue -Force
231: }
232: $Executable = $Env:windir + "\system32\msiexec.exe"
233: $Switches = "/qb- /norestart"
234: $Parameters = "/x" + [char]32 + $Global:ProductCode + [char]32 + $Switches
235: Write-Host "Uninstalling"$Global:ApplicationName"....." -NoNewline
236: $ErrCode = (Start-Process -FilePath $Executable -ArgumentList $Parameters -Wait -Passthru).ExitCode
237: if (($ErrCode -eq 0) -or ($ErrCode -eq 3010)) {
238: Write-Host "Success" -ForegroundColor Yellow
239: } else {
240: Write-Host "Failed with error code "$ErrCode -ForegroundColor Red
241: }
242:
243: #Cleanup Local Variables
244: Remove-Variable -Name ErrCode -Scope Local -Force
245: Remove-Variable -Name Executable -Scope Local -Force
246: Remove-Variable -Name Line -Scope Local -Force
247: Remove-Variable -Name LogFile -Scope Local -Force
248: Remove-Variable -Name MSI -Scope Local -Force
249: Remove-Variable -Name Parameters -Scope Local -Force
250: Remove-Variable -Name Process -Scope Local -Force
251: Remove-Variable -Name RelativePath -Scope Local -Force
252: Remove-Variable -Name Switches -Scope Local -Force
253: }
254:
255: function Get-ProductName {
256: #Declare Local Variables
257: Set-Variable -Name Database -Scope Local -Force
258: Set-Variable -Name MSIFileName -Scope Local -Force
259: Set-Variable -Name Output -Scope Local -Force
260: Set-Variable -Name OutputFile -Scope Local -Force
261: Set-Variable -Name PropertyName -Scope Local -Force
262: Set-Variable -Name PropertyValue -Scope Local -Force
263: Set-Variable -Name Record -Scope Local -Force
264: Set-Variable -Name RelativePath -Scope Local -Force
265: Set-Variable -Name View -Scope Local -Force
266: Set-Variable -Name WindowsInstaller -Scope Local -Force
267:
268: $RelativePath = Get-RelativePath
269: $MSIFileName = $global:MSI
270: $OutputFile = $RelativePath + "Report.txt"
271: $Output = [char]13
272: Write-Host $Output
273: Out-File -FilePath $OutputFile -InputObject $Output -Append -Force
274: $Output = "Product Name"
275: Write-Host $Output
276: Out-File -FilePath $OutputFile -InputObject $Output -Append -Force
277: $Output = "------------"
278: Write-Host $Output
279: Out-File -FilePath $OutputFile -InputObject $Output -Append -Force
280: $WindowsInstaller = New-Object -com WindowsInstaller.Installer
281: $Database = $WindowsInstaller.GetType().InvokeMember("OpenDatabase", "InvokeMethod", $Null, $WindowsInstaller, @($MSIFileName, 0))
282: $View = $Database.GetType().InvokeMember("OpenView", "InvokeMethod", $Null, $Database, ("SELECT * FROM Property"))
283: $View.GetType().InvokeMember("Execute", "InvokeMethod", $Null, $View, $Null)
284: $Record = $View.GetType().InvokeMember("Fetch", "InvokeMethod", $Null, $View, $Null)
285: while ($Record -ne $Null) {
286: $PropertyName = $Record.GetType().InvokeMember("StringData", "GetProperty", $Null, $Record, 1)
287: [string]$PropertyValue = $Record.GetType().InvokeMember("StringData", "GetProperty", $Null, $Record, 2)
288: IF ($PropertyName -like "*ProductName*") {
289: $Output = $PropertyValue
290: Write-Host $Output
291: Out-File -FilePath $OutputFile -InputObject $Output -Append -Force
292: }
293: $Record = $View.GetType().InvokeMember("Fetch", "InvokeMethod", $Null, $View, $Null)
294: }
295:
296: #Cleanup Local Variables
297: Remove-Variable -Name Database -Scope Local -Force
298: Remove-Variable -Name MSIFileName -Scope Local -Force
299: Remove-Variable -Name Output -Scope Local -Force
300: Remove-Variable -Name OutputFile -Scope Local -Force
301: Remove-Variable -Name PropertyName -Scope Local -Force
302: Remove-Variable -Name PropertyValue -Scope Local -Force
303: Remove-Variable -Name Record -Scope Local -Force
304: Remove-Variable -Name RelativePath -Scope Local -Force
305: Remove-Variable -Name View -Scope Local -Force
306: Remove-Variable -Name WindowsInstaller -Scope Local -Force
307: }
308:
309: function Get-ProductCode {
310: #Declare Local Variables
311: Set-Variable -Name Database -Scope Local -Force
312: Set-Variable -Name MSIFileName -Scope Local -Force
313: Set-Variable -Name Output -Scope Local -Force
314: Set-Variable -Name OutputFile -Scope Local -Force
315: Set-Variable -Name PropertyName -Scope Local -Force
316: Set-Variable -Name PropertyValue -Scope Local -Force
317: Set-Variable -Name Record -Scope Local -Force
318: Set-Variable -Name RelativePath -Scope Local -Force
319: Set-Variable -Name View -Scope Local -Force
320: Set-Variable -Name WindowsInstaller -Scope Local -Force
321:
322: $RelativePath = Get-RelativePath
323: $MSIFileName = $global:MSI
324: $OutputFile = $RelativePath + "Report.txt"
325: $Output = [char]13
326: Write-Host $Output
327: Out-File -FilePath $OutputFile -InputObject $Output -Append -Force
328: $Output = "Product Code"
329: Write-Host $Output
330: Out-File -FilePath $OutputFile -InputObject $Output -Append -Force
331: $Output = "------------"
332: Write-Host $Output
333: Out-File -FilePath $OutputFile -InputObject $Output -Append -Force
334: $WindowsInstaller = New-Object -com WindowsInstaller.Installer
335: $Database = $WindowsInstaller.GetType().InvokeMember("OpenDatabase", "InvokeMethod", $Null, $WindowsInstaller, @($MSIFileName, 0))
336: $View = $Database.GetType().InvokeMember("OpenView", "InvokeMethod", $Null, $Database, ("SELECT * FROM Property"))
337: $View.GetType().InvokeMember("Execute", "InvokeMethod", $Null, $View, $Null)
338: $Record = $View.GetType().InvokeMember("Fetch", "InvokeMethod", $Null, $View, $Null)
339: while ($Record -ne $Null) {
340: $PropertyName = $Record.GetType().InvokeMember("StringData", "GetProperty", $Null, $Record, 1)
341: [string]$PropertyValue = $Record.GetType().InvokeMember("StringData", "GetProperty", $Null, $Record, 2)
342: IF ($PropertyName -like "*ProductCode*") {
343: $Output = $PropertyValue
344: Write-Host $Output
345: Out-File -FilePath $OutputFile -InputObject $Output -Append -Force
346: }
347: $Record = $View.GetType().InvokeMember("Fetch", "InvokeMethod", $Null, $View, $Null)
348: }
349:
350: #Cleanup Local Variables
351: Remove-Variable -Name Database -Scope Local -Force
352: Remove-Variable -Name MSIFileName -Scope Local -Force
353: Remove-Variable -Name Output -Scope Local -Force
354: Remove-Variable -Name OutputFile -Scope Local -Force
355: Remove-Variable -Name PropertyName -Scope Local -Force
356: Remove-Variable -Name PropertyValue -Scope Local -Force
357: Remove-Variable -Name Record -Scope Local -Force
358: Remove-Variable -Name RelativePath -Scope Local -Force
359: Remove-Variable -Name View -Scope Local -Force
360: Remove-Variable -Name WindowsInstaller -Scope Local -Force
361: }
362:
363: function Get-MSIFileName {
364: #Declare Local Variables
365: Set-Variable -Name Output -Scope Local -Force
366: Set-Variable -Name OutputFile -Scope Local -Force
367:
368: $OutputFile = $RelativePath + "Report.txt"
369: $Output = [char]13
370: Write-Host $Output
371: Out-File -FilePath $OutputFile -InputObject $Output -Append -Force
372: $Output = "MSI Filename"
373: Write-Host $Output
374: Out-File -FilePath $OutputFile -InputObject $Output -Append -Force
375: $Output = "------------"
376: Write-Host $Output
377: Out-File -FilePath $OutputFile -InputObject $Output -Append -Force
378: $Output = $global:MSI
379: Write-Host $Output
380: Out-File -FilePath $OutputFile -InputObject $Output -Append -Force
381:
382: #Cleanup Local Variables
383: Remove-Variable -Name Output -Scope Local -Force
384: Remove-Variable -Name OutputFile -Scope Local -Force
385:
386: }
387:
388: function Get-Properties {
389: #Declare Local Variables
390: Set-Variable -Name Entries -Scope Local -Force
391: Set-Variable -Name Entry -Scope Local -Force
392: Set-Variable -Name File -Scope Local -Force
393: Set-Variable -Name FormattedEntry -Scope Local -Force
394: Set-Variable -Name Line -Scope Local -Force
395: Set-Variable -Name Output -Scope Local -Force
396: Set-Variable -Name OutputFile -Scope Local -Force
397: Set-Variable -Name Position -Scope Local -Force
398: Set-Variable -Name Property -Scope Local -Force
399: Set-Variable -Name RelativePath -Scope Local -Force
400: Set-Variable -Name Value -Scope Local -Force
401:
402: $OutputArray = @()
403: $RelativePath = Get-RelativePath
404: $File = Get-Content -Path $RelativePath"Installer.log"
405: $OutputFile = $RelativePath+"Report.txt"
406: $Entries = Get-Content -Path $RelativePath"UserInput.txt"
407: $Output = [char]13
408: Write-Host $Output
409: Out-File -FilePath $OutputFile -InputObject $Output -Append -Force
410: $Output = "Properties"
411: Write-Host $Output
412: Out-File -FilePath $OutputFile -InputObject $Output -Append -Force
413: $Output = "----------"
414: Write-Host $Output
415: Out-File -FilePath $OutputFile -InputObject $Output -Append -Force
416: If ($Entries -ne $null) {
417: foreach ($Line in $File) {
418: If ($Line -like "*PROPERTY CHANGE: Adding*") {
419: foreach ($Entry in $Entries) {
420: $FormattedEntry = [char]42 + [char]39 + $Entry + [char]39 + [char]42
421: If ($Line -like $FormattedEntry) {
422: $Property = $Line
423: $Value = $Line
424: $Property = $Property.split(':')[-1]
425: If ($Property[0] -eq "\") {
426: $Property = $Line
427: $Property = $Property.split(':')[-2]
428: }
429: $Property = $Property.Trim()
430: $Property = $Property.Trim("Adding")
431: $Property = $Property.Trim()
432: $Property = $Property.Trim(" ")
433: $Position = $Property.IndexOf(" ")
434: If ($Property -notlike "*:\*") {
435: $Property = $Property.Substring(0, $Position)
436: }
437: $Output = $Property + ": " + $Entry
438: $OutputArray += $Output
439: }
440: }
441: }
442: }
443: $OutputArray = $OutputArray | select -Unique
444: $OutputArray = $OutputArray | Sort
445: foreach ($Item in $OutputArray) {
446: Write-Host $Item
447: If ($Item -ne $null) {
448: Out-File -FilePath $OutputFile -InputObject $Item -Append -Force
449: }
450: }
451: } else {
452: $Output = "No User Input Properties Exist"
453: Write-Host $Output
454: Out-File -FilePath $OutputFile -InputObject $Output -Append -Force
455: }
456:
457: #Cleanup Local Variables
458: Remove-Variable -Name Entries -Scope Local -Force
459: Remove-Variable -Name Entry -Scope Local -Force
460: Remove-Variable -Name File -Scope Local -Force
461: Remove-Variable -Name FormattedEntry -Scope Local -Force
462: Remove-Variable -Name Line -Scope Local -Force
463: Remove-Variable -Name Output -Scope Local -Force
464: Remove-Variable -Name OutputFile -Scope Local -Force
465: Remove-Variable -Name Position -Scope Local -Force
466: Remove-Variable -Name Property -Scope Local -Force
467: Remove-Variable -Name RelativePath -Scope Local -Force
468: Remove-Variable -Name Value -Scope Local -Force
469: }
470:
471: function Get-Features {
472: #Declare Local Variables
473: Set-Variable -Name Entries -Scope Local -Force
474: Set-Variable -Name File -Scope Local -Force
475: Set-Variable -Name Line -Scope Local -Force
476: Set-Variable -Name Output -Scope Local -Force
477: Set-Variable -Name OutputFile -Scope Local -Force
478: Set-Variable -Name RelativePath -Scope Local -Force
479: Set-Variable -Name Value -Scope Local -Force
480: Set-Variable -Name Values -Scope Local -Force
481:
482: $RelativePath = Get-RelativePath
483: $OutputFile = $RelativePath + "Report.txt"
484: $Entries = Get-Content -Path $RelativePath"UserInput.txt"
485: $Output = [char]13
486: Write-Host $Output
487: Out-File -FilePath $OutputFile -InputObject $Output -Append -Force
488: $Output = "Features"
489: Write-Host $Output
490: Out-File -FilePath $OutputFile -InputObject $Output -Append -Force
491: $Output = "--------"
492: Write-Host $Output
493: Out-File -FilePath $OutputFile -InputObject $Output -Append -Force
494: If ($Entries -ne $null) {
495: $File = Get-Content -Path $global:RelativePath"Installer.log"
496: foreach ($Line in $File) {
497: If ($Line -like "*ADDLOCAL*") {
498: $Value = $Line.split(' ')[-1]
499: $Value = $Value -replace '''', ''
500: $Value = $Value.SubString(0, $Value.Length - 1)
501: $Values = $Value.Split(",")
502: foreach ($Value in $Values) {
503: Write-Host $Value
504: Out-File -FilePath $OutputFile -InputObject $Value -Append -Force
505: }
506: }
507: }
508: } else {
509: $Output = "No User Input Features Exist"
510: Write-Host $Output
511: Out-File -FilePath $OutputFile -InputObject $Output -Append -Force
512: }
513:
514: #Cleanup Local Variables
515: Remove-Variable -Name Entries -Scope Local -Force
516: Remove-Variable -Name File -Scope Local -Force
517: Remove-Variable -Name Line -Scope Local -Force
518: Remove-Variable -Name Output -Scope Local -Force
519: Remove-Variable -Name OutputFile -Scope Local -Force
520: Remove-Variable -Name RelativePath -Scope Local -Force
521: Remove-Variable -Name Value -Scope Local -Force
522: Remove-Variable -Name Values -Scope Local -Force
523: }
524:
525: function Get-Buttons {
526: #Declare Local Variables
527: Set-Variable -Name Database -Scope Local -Force
528: Set-Variable -Name Entries -Scope Local -Force
529: Set-Variable -Name Entry -Scope Local -Force
530: Set-Variable -Name MSIFileName -Scope Local -Force
531: Set-Variable -Name Output -Scope Local -Force
532: Set-Variable -Name OutputFile -Scope Local -Force
533: Set-Variable -Name PropertyName -Scope Local -Force
534: Set-Variable -Name PropertyValue -Scope Local -Force
535: Set-Variable -Name Record -Scope Local -Force
536: Set-Variable -Name RelativePath -Scope Local -Force
537: Set-Variable -Name View -Scope Local -Force
538: Set-Variable -Name WindowsInstaller -Scope Local -Force
539:
540: $RelativePath = Get-RelativePath
541: $MSIFileName = $global:MSI
542: $Entries = Get-Content -Path $RelativePath"UserInput.txt"
543: $OutputFile = $RelativePath + "Report.txt"
544: $Output = [char]13
545: Write-Host $Output
546: Out-File -FilePath $OutputFile -InputObject $Output -Append -Force
547: $Output = "Buttons"
548: Write-Host $Output
549: Out-File -FilePath $OutputFile -InputObject $Output -Append -Force
550: $Output = "--------"
551: Write-Host $Output
552: Out-File -FilePath $OutputFile -InputObject $Output -Append -Force
553: foreach ($Entry in $Entries) {
554: $WindowsInstaller = New-Object -com WindowsInstaller.Installer
555: $Database = $WindowsInstaller.GetType().InvokeMember("OpenDatabase", "InvokeMethod", $Null, $WindowsInstaller, @($MSIFileName, 0))
556: $View = $Database.GetType().InvokeMember("OpenView", "InvokeMethod", $Null, $Database, ("SELECT * FROM RadioButton"))
557: $View.GetType().InvokeMember("Execute", "InvokeMethod", $Null, $View, $Null)
558: $Record = $View.GetType().InvokeMember("Fetch", "InvokeMethod", $Null, $View, $Null)
559: $Entry = "*" + $Entry + "*"
560: while ($Record -ne $Null) {
561: $PropertyName = $Record.GetType().InvokeMember("StringData", "GetProperty", $Null, $Record, 1)
562: if (-not ($PropertyName -cmatch "[a-z]")) {
563: [string]$PropertyValue = $Record.GetType().InvokeMember("StringData", "GetProperty", $Null, $Record, 8)
564: IF ($PropertyValue -like $Entry) {
565: $Output = $PropertyName + " = " + $PropertyValue
566: Write-Host $Output
567: Out-File -FilePath $OutputFile -InputObject $Output -Append -Force
568: #Write-Host ($PropertyName + " = " + $PropertyValue)
569: }
570: }
571: $Record = $View.GetType().InvokeMember("Fetch", "InvokeMethod", $Null, $View, $Null)
572: }
573: }
574:
575: #Cleanup Local Variables
576: Remove-Variable -Name Database -Scope Local -Force
577: Remove-Variable -Name Entries -Scope Local -Force
578: Remove-Variable -Name Entry -Scope Local -Force
579: Remove-Variable -Name MSIFileName -Scope Local -Force
580: Remove-Variable -Name Output -Scope Local -Force
581: Remove-Variable -Name OutputFile -Scope Local -Force
582: Remove-Variable -Name PropertyName -Scope Local -Force
583: Remove-Variable -Name PropertyValue -Scope Local -Force
584: Remove-Variable -Name Record -Scope Local -Force
585: Remove-Variable -Name RelativePath -Scope Local -Force
586: Remove-Variable -Name View -Scope Local -Force
587: Remove-Variable -Name WindowsInstaller -Scope Local -Force
588: }
589:
590: Clear-Host
591: ProcessTextFiles
592: Get-MSIFile
593: New-UserInputFile
594: Install-MSI
595: Uninstall-MSI
596: Get-ProductName
597: Get-ProductCode
598: Get-MSIFileName
599: Get-Properties
600: Get-Features
601: Get-Buttons
602:
603: #Cleanup Global Variables
604: Remove-Variable -Name ApplicationName -Scope Global -Force
605: Remove-Variable -Name MSI -Scope Global -Force
606: Remove-Variable -Name ProductCode -Scope Global -Force

0 Response to "MSI Analysis Reporting Tool"

Post a Comment