Powershell:将SQL查询中的列与WMI结果合并

问题描述 投票:0回答:2

脚本的第一步从SQL表中提取3个字段。第二步获取服务器名称,并遍历服务器名称以获取更多信息。我的目标是将SQL表中的其他2列与从WMI输出中收集的信息结合起来。

  #SQL Variables
  $SQLServer = 'remoteservername'
  $Database = 'Dbname'
  #Create a SQL Query function
  Function SQL_Query ($Query) {
$SqlConnection = New-Object System.Data.SqlClient.SqlConnection 
$SqlConnection.ConnectionString = "Server=$SQLServer;Database=$Database;Integrated Security=True"
$SqlCmd = New-Object System.Data.SqlClient.SqlCommand 
$SqlCmd.Connection = $SqlConnection 
$SqlCmd.CommandText = $Query 
$SqlAdapter = New-Object System.Data.SqlClient.SqlDataAdapter 
$SqlAdapter.SelectCommand = $SqlCmd 
$DataSet = New-Object System.Data.DataSet 
$a = $SqlAdapter.Fill($DataSet) 
$SqlConnection.Close() 
$DataSet.Tables[0] 
                        } #End SQL Query Function
$Servers = SQL_Query "SELECT 
                               Servername, Status, Purpose
                        FROM tablename "

 $Results = $Servers | Select-Object -ExpandProperty ServerName

        #loop through servers
        $Output = @()
        $Output =Foreach ($Server in $Results) 
        {

                $Servers # This variable stores Servername, Status, and Purpose information. I want the Status and Purpose fields to show up in the loop below. The idea is if the Servername from $servers matches $server,add the extra 2 fields from #Servers
                $BootTime = GET-WmiObject win32_Operatingsystem -ComputerName $server -EA STOP | select @{n='ServerName';e={$_.csname}},@{n='LastBootUpTime';e={$_.ConverttoDateTime($_.lastbootuptime)}}`
                ,@{n='LocalTime';e={$_.ConverttoDateTime($_.LocalDateTime)}} ,@{n='UpTime';e={"Uptime:" + ((GET-DAte) - $_.ConverttoDateTime($_.lastbootuptime)).Days + " Days " +`
                        ((GET-DAte) - $_.ConverttoDateTime($_.lastbootuptime)).Hours + " Hours " + ((GET-DAte) - $_.ConverttoDateTime($_.lastbootuptime)).Minutes + " Minutes "}},@{n='OS';e={$_.caption}}


        }
        #Display Out here
        $Boottime | Select ServerName,LastBootUpTime,Uptime,Status,Purpose |Out-GridView
powershell variables
2个回答
0
投票

您可以使用$ Servers代替$ Results进行循环,并将$ server数据添加到选择中

@ {n ='状态'; e = {$ Server.Status}},@ {n =“目的”; e = {$ Server.Purpose}}

结果代码将如下所示:

#SQL Variables
$SQLServer = 'remoteservername'
$Database = 'Dbname'
#Create a SQL Query function
Function SQL_Query ($Query) {
    $SqlConnection = New-Object System.Data.SqlClient.SqlConnection 
    $SqlConnection.ConnectionString = "Server=$SQLServer;Database=$Database;Integrated Security=True"
    $SqlCmd = New-Object System.Data.SqlClient.SqlCommand 
    $SqlCmd.Connection = $SqlConnection 
    $SqlCmd.CommandText = $Query 
    $SqlAdapter = New-Object System.Data.SqlClient.SqlDataAdapter 
    $SqlAdapter.SelectCommand = $SqlCmd 
    $DataSet = New-Object System.Data.DataSet 
    $a = $SqlAdapter.Fill($DataSet) 
    $SqlConnection.Close() 
    $DataSet.Tables[0] 
} #End SQL Query Function
= SQL_Query "SELECT 
                               Servername, Status, Purpose
                        FROM tablename "

#dont need this
#$Results = $Servers | Select-Object -ExpandProperty ServerName

#loop through servers
$Output = @()
$Output = Foreach ($Server in $Servers) {
    #set this variable to be used in the ComputerName param
    $serverName = $Server.Servername

    #dont need this
    #$Servers # This variable stores Servername, Status, and Purpose information. I want the Status and Purpose fields to show up in the loop below. The idea is if the Servername from $servers matches $server,add the extra 2 fields from #Servers
    GET-WmiObject win32_Operatingsystem -ComputerName $serverName -EA STOP | select @{n = 'ServerName'; e = { $_.csname } }, @{n = 'LastBootUpTime'; e = { $_.ConverttoDateTime($_.lastbootuptime) } }`
        , @{n = 'LocalTime'; e = { $_.ConverttoDateTime($_.LocalDateTime) } } , @{n = 'UpTime'; e = { "Uptime:" + ((GET-DAte) - $_.ConverttoDateTime($_.lastbootuptime)).Days + " Days " + `
            ((GET-DAte) - $_.ConverttoDateTime($_.lastbootuptime)).Hours + " Hours " + ((GET-DAte) - $_.ConverttoDateTime($_.lastbootuptime)).Minutes + " Minutes " }
    }, @{n = 'OS'; e = { $_.caption } }, @{n = 'Status'; e = { $Server.Status } }, @{n = 'Purpose'; e = { $Server.Purpose } }
    #see the added columns above Status and Purpose
}
#Display Out here
$Output | Select ServerName, LastBootUpTime, Uptime, Status, Purpose | Out-GridView

0
投票

对于更简洁的代码,我在这里不使用具有计算属性的Select-Object,而是让循环直接发出PsCustomObject

#loop through servers
$result = foreach ($server in $Servers) {
    try {
        $os = Get-WmiObject Win32_Operatingsystem -ComputerName $server.ServerName -ErrorAction Stop

        $lastBoot  = $os.ConverttoDateTime($os.LastBootUpTime)
        $localTime = $os.ConverttoDateTime($os.LocalDateTime)
        $upTime    = (Get-Date) - $lastBoot

        # output a PsObject
        [PsCustomObject]@{
            'ServerName'     = $os.CSName
            'LastBootUpTime' = $lastBoot
            'LocalTime'      = $localTime
            'UpTime'         = '{0} Days {1} Hours {2} Minutes' -f $upTime.Days, $upTime.Hours, $upTime.Minutes
            'OS'             = $os.Caption
            'Status'         = $server.Status
            'Purpose'        = $server.Purpose
        }
    }
    catch {
        Write-Warning "WMI Query failed on computer '$($server.ServerName)'"
    }
}

# Display the result here
$result | Out-GridView

如果您具有PowerShell版本3.0或更高版本,则可以更改代码以使用Get-CimInstance来代替Get-WmiObject,以获得更好的性能。参见Get-CIMInstance Vs Get-WMIObject

这样做,也意味着您不必转换LastBootUpTimeLocalDateTime属性,因为它们已经是真实的DateTime对象。

该代码将显示为:

#loop through servers
$result = foreach ($server in $Servers) {
    try {
        $os = Get-CimInstance -ClassName Win32_Operatingsystem -ComputerName $server.ServerName -ErrorAction Stop
        $upTime = (Get-Date) - $os.LastBootUpTime

        # output a PsObject
        [PsCustomObject]@{
            'ServerName'     = $os.CSName
            'LastBootUpTime' = $os.LastBootUpTime
            'LocalTime'      = $os.LocalDateTime
            'UpTime'         = '{0} Days {1} Hours {2} Minutes' -f $upTime.Days, $upTime.Hours, $upTime.Minutes
            'OS'             = $os.Caption
            'Status'         = $server.Status
            'Purpose'        = $server.Purpose
        }
    }
    catch {
        Write-Warning "WMI Query failed on computer '$($server.ServerName)'"
    }
}

# Display the result here
$result | Out-GridView
© www.soinside.com 2019 - 2024. All rights reserved.