h41msh1c0r
Goto Top

Powershell: DB(MSI)-Tabelle auslesen

Servus,

Ziel:

Tabelle aus DB(im speziellen handelt es sich hier um eine MSI) auslesen und Inhalt in eine ArrayList schreiben um diese danach an das DataGrid ( aus meiner letzten Frage) zu übergeben.

Die Idee war gewesen via der folgenden Zeile erst den Count zu ermitteln.

$database.GetType().InvokeMember("OpenView", [System.Reflection.BindingFlags]::InvokeMethod, $null, $database, "SELECT Count(*) FROM Test")  

Danach mit diesem Counter die Tabelle "Test" erneut zu durchlaufen und die Werte in eine ArrayListe zu schreiben.
Leider wirft er mir bei dem ermitteln des Count bereits einen Fehler, das das Argument NULL sei und nicht übergeben werden kann.

$msiPath = 'c:\temp\setup.msi'  

# Create Installer instance
$installer = New-Object -comObject WindowsInstaller.Installer

# Call Installer.OpenDatabase(name, openMode)
$database = $installer.GetType().InvokeMember("OpenDatabase", [System.Reflection.BindingFlags]::InvokeMethod, $null, $installer, ($msiPath, 0))  

# Call Database.OpenView(sql)
$view = $database.GetType().InvokeMember("OpenView", [System.Reflection.BindingFlags]::InvokeMethod, $null, $database, "SELECT COUNT(*) FROM Property")  

# Call View.Execute()
$view.GetType().InvokeMember("Execute", [System.Reflection.BindingFlags]::InvokeMethod, $null, $view, $null)  

# Call View.Fetch()
$record = $view.GetType().InvokeMember("Fetch", [System.Reflection.BindingFlags]::InvokeMethod, $null, $view, $null)  

# Get Record.StringData(field)
$count = $record.GetType().InvokeMember("StringData", [System.Reflection.BindingFlags]::GetProperty, $null, $record, 1)  

Write-Host $count

Spezifiziere ich das SQL Statement kann ich mir einzelne Werte ausgeben, allerdings ist das unpraktikabel da ich den Inhalt einer ganzen Tabelle benötige.

Hat von den Spezialisten einer einen Hint?

Gruß

Content-ID: 222088

Url: https://administrator.de/forum/powershell-dbmsi-tabelle-auslesen-222088.html

Ausgedruckt am: 16.04.2025 um 10:04 Uhr

H41mSh1C0R
H41mSh1C0R 15.11.2013 aktualisiert um 13:24:59 Uhr
Goto Top
$msiPath = 'c:\temp\setup.msi'  
$MyArray = @("'ProductName'", "'ProductVersion'")  

# Create Installer instance
$installer = New-Object -comObject WindowsInstaller.Installer

# Call Installer.OpenDatabase(name, openMode)
$database = $installer.GetType().InvokeMember("OpenDatabase", [System.Reflection.BindingFlags]::InvokeMethod, $null, $installer, ($msiPath, 0))  

$Counter = 0
do {
    
    $SelectPropertyName = "SELECT Property FROM Property WHERE Property = " + $MyArray[$Counter]  
    $SelectPropertyValue = "SELECT Value FROM Property WHERE Property = " + $MyArray[$Counter]  
    
    $view = $database.GetType().InvokeMember("OpenView", [System.Reflection.BindingFlags]::InvokeMethod, $null, $database, "$SelectPropertyName")  
    $view.GetType().InvokeMember("Execute", [System.Reflection.BindingFlags]::InvokeMethod, $null, $view, $null)  
    $record = $view.GetType().InvokeMember("Fetch", [System.Reflection.BindingFlags]::InvokeMethod, $null, $view, $null)  
    $resultProperty = $record.GetType().InvokeMember("StringData", [System.Reflection.BindingFlags]::GetProperty, $null, $record, 1)  

    $view = $database.GetType().InvokeMember("OpenView", [System.Reflection.BindingFlags]::InvokeMethod, $null, $database, "$SelectPropertyValue")  
    $view.GetType().InvokeMember("Execute", [System.Reflection.BindingFlags]::InvokeMethod, $null, $view, $null)  
    $record = $view.GetType().InvokeMember("Fetch", [System.Reflection.BindingFlags]::InvokeMethod, $null, $view, $null)  
    $resultValue = $record.GetType().InvokeMember("StringData", [System.Reflection.BindingFlags]::GetProperty, $null, $record, 1)  

    Write-Host "Result: " $resultProperty " ------ " $resultValue  
    $Counter++
}
while ($Counter -le $MyArray.Count-1)

So bekomme ich zwar nach der Methode "von hinten durch die Brust durchs Auge" die Daten raus wie ich oben das MyArray befülle, aber das ist ja noch nicht ganz das was ich suche. Mal weiter gucken wie ich den Count ermittelt bekomme.

Wenn einer einen Tipp hat immer posten, danke.

Gruß
colinardo
colinardo 15.11.2013, aktualisiert am 20.01.2014 um 22:03:51 Uhr
Goto Top
Hi,
check this out:
$msiPath = "c:\temp\setup.msi"  
$installer = New-Object -ComObject WindowsInstaller.Installer
$database = $installer.GetType().InvokeMember("OpenDatabase", [System.Reflection.BindingFlags]::InvokeMethod, $null, $installer, ($msiPath, 0))   
$view = $database.getType().InvokeMember("OpenView",[System.Reflection.BindingFlags]::InvokeMethod,$null,$database,"SELECT * FROM Property")  
$view.getType().InvokeMember("Execute",[System.Reflection.BindingFlags]::InvokeMethod,$null,$view,$null)  
$r = $view.getType().InvokeMember("Fetch",[System.Reflection.BindingFlags]::InvokeMethod,$null,$view,$null)  
$arr = @()
while($r -ne $null) {
        $arr += New-Object PSObject -Property @{Property=$r.getType().InvokeMember("StringData",[System.Reflection.BindingFlags]::GetProperty,$null,$r,1);Value=$r.getType().InvokeMember("StringData",[System.Reflection.BindingFlags]::GetProperty,$null,$r,2)}  
        $r = $view.getType().InvokeMember("Fetch",[System.Reflection.BindingFlags]::InvokeMethod,$null,$view,$null)  
	}
$view.getType().InvokeMember("Close",[System.Reflection.BindingFlags]::InvokeMethod,$null,$view,$null)  

$arr | sort -Property Property | select Property,Value

Oder alles zusammengefasst inkl. Anzeige deiner Form
$msiPath =  "c:\temp\setup.msi"  
$installer = New-Object -ComObject WindowsInstaller.Installer
$database = $installer.GetType().InvokeMember("OpenDatabase", [System.Reflection.BindingFlags]::InvokeMethod, $null, $installer, ($msiPath, 0))   
$view = $database.getType().InvokeMember("OpenView",[System.Reflection.BindingFlags]::InvokeMethod,$null,$database,"SELECT * FROM Property")  
$view.getType().InvokeMember("Execute",[System.Reflection.BindingFlags]::InvokeMethod,$null,$view,$null)  
$r = $view.getType().InvokeMember("Fetch",[System.Reflection.BindingFlags]::InvokeMethod,$null,$view,$null)  
$arr = @()
while($r -ne $null) {
        $arr += New-Object PSObject -Property @{Property=$r.getType().InvokeMember("StringData",[System.Reflection.BindingFlags]::GetProperty,$null,$r,1);Value=$r.getType().InvokeMember("StringData",[System.Reflection.BindingFlags]::GetProperty,$null,$r,2)}  
        $r = $view.getType().InvokeMember("Fetch",[System.Reflection.BindingFlags]::InvokeMethod,$null,$view,$null)  
	}
$view.getType().InvokeMember("Close",[System.Reflection.BindingFlags]::InvokeMethod,$null,$view,$null)  

$sortedArray = $arr |sort -Property Property | select Property,Value
$list = [System.collections.ArrayList]$sortedArray

# ---Create Form ---
Add-Type -AssemblyName "System.Windows.Forms"  
$form = New-Object System.Windows.Forms.Form
$form.Size = New-Object System.Drawing.Size(900,600)
$dataGridView = New-Object System.Windows.Forms.DataGridView -Property @{
    Size=New-Object System.Drawing.Size(900,600)
    ColumnHeadersVisible = $true
    DataSource = $list
    AutoSizeColumnsMode = 16
    Dock = 5
}

$form.Controls.Add($dataGridView)
$form.ShowDialog()

Grüße Uwe
H41mSh1C0R
H41mSh1C0R 15.11.2013 um 20:03:58 Uhr
Goto Top
Hallo Uwe,

schonmal danke für deine Mühe.
Ich baue am Montag weiter, wenn ich wieder in der Nähe von der Powershell bin.

Gruß