2014-02-17 4 views
2

Я все еще изучаю сценарии PowerShell, и я работаю над скриптом для вычисления процента свободного места на моих файловых серверах и отправки уведомления по электронной почте, когда привод достигает 10% свободного места или меньше (это происходит примерно раз в месяц, и мне нужно знать, прежде чем я получаю по электронной почте от клиента, что больше нет места). На данный момент скрипт отлично работает и настроен для запуска каждое утро через Windows Task. Но текущее форматирование, которое у меня есть для вывода, выполняется вручную. Мне было интересно, есть ли способ передать переменные из информации, которая была собрана и рассчитана с помощью функции Get-WmiObject. Я попробовал Format-Table и попытался возиться с хэш-таблицами, но безрезультатно. Любые идеи были бы полезны. Благодарю.Создать таблицу с переменными в PowerShell

# Set Parameters 
$file = "c:\location\Lowdisk.txt" 
Clear-Content $file 

$emailTO = "[email protected]" 
$emailFrom = "[email protected]" 
$smtpServer = "smtpServer" 

$diskspace = "3" 
$computers = ("FSCN01","FSCN02","FSCN03","FSCN04") 
echo "Server Name  Drive  Drive Size  Free Space  % Free" >> $file 
$i = 0 

# Get Drive Data 
foreach($computer in $computers) 
{ 
$drives = Get-WmiObject -ComputerName $computer Win32_LogicalDisk | Where-Object {$_.DriveType -eq 3} 
foreach($drive in $drives) 
{ 
    $ID = $drive.DeviceID 
    $size1 = $drive.size/1GB 
    $size = "{0:N1}" -f $size1 
    $free1 = $drive.freespace/1GB 
    $free = "{0:N1}" -f $free1 
    $a = $free1/$size1 * 100 
    $b = "{0:N1}" -f $a 
     # Monitor for drive free space % under 10% 
     if ($b -lt 10) 
     { 
      echo "$computer   $ID   $size   $free   $b" >> $file 
      $i++ 
     } 
} 
} 
# Send notification if script finds more than 0 drives with less than 35% free space 
    if ($i -gt 0) 
    { 
     foreach ($user in $emailTo) 
      { 
     echo "Sending Email Notification to $user" 
     $smtp = New-Object Net.Mail.SmtpClient($smtpServer) 
     $subject = "Server with Low Disk Space" 
     foreach ($line in Get-Content $file) 
       { 
       $body += "$line `n" 
       } 
     Send-MailMessage -to $user -From $emailFrom -Attachments $file -SmtpServer $smtpServer -Subject $Subject -Body $body 
     $body = "" 
       } 
    } 

ответ

6

Format-Table работает лучше всего, когда у вас есть все данные, представляющие интерес в одном типе объекта. Я бы рекомендовал создавать пользовательские объекты для этого, например:

foreach($computer in $computers) 
{ 
    $drives = Get-WmiObject -ComputerName $computer Win32_LogicalDisk | Where-Object {$_.DriveType -eq 3} 
    foreach($drive in $drives) 
    { 
     $obj = new-object psobject -Property @{ 
        ComputerName = $computer 
        Drive = $drive.DeviceID 
        Size = $drive.size/1GB 
        Free = $drive.freespace/1GB 
        PercentFree = $drive.freespace/$drive.size * 100 
       } 
     if ($obj.PercentFree -lt 10) { 
      $obj | Format-Table ComputerName,Drive,Size,Free,PercentFree 
      $i++ 
     } 
    } 
} 

Если вы хотите изменить формат отображения, то в команде формат стола вы можете сделать это:

+0

Это именно то, что я хотел выполнить. Спасибо за вашу помощь!! – user3140412

1

Кит имеет оно охватывает, но так как мой ответ был наполовину написан, вот он. Моя версия не требует создания новых объектов и фильтрации в составе конвейера.

Как говорит Кейт, храните все как объект до последней минуты. Если вам нужно принудительно форматировать PowerShell, используйте «out-string».

Также обратите внимание на поддержку списков. Многие команды будут принимать список в качестве параметра (например, список имен компьютеров, получателей электронной почты) без необходимости для каждого цикла. Это может сделать код более кратким, но, возможно, менее читаемым, особенно для новичков. В любом случае, вот что я приготовил:

[email protected]("server1","server2","server3","server4") 
$smtpServer = "mail.mydomain.com" 
$toList = @("[email protected]","[email protected]") 
$minPercent = 10 

$tableSpec = @(
     @{label="Computer";expression={$_.SystemName}}, 
     @{label="Disk";expression={$_.DeviceID}}, 
     @{label="Size Gb";expression={[int]($_.size/1Gb)}}, 
     @{label="PercentFree";expression={[int]($_.FreeSpace/$_.Size * 100)}} 
    ) 

$report = (

    Get-WmiObject -ComputerName $comps -Class Win32_LogicalDisk | 
    Where-Object { ($_.DriveType -eq 3) -and ($_.FreeSpace -lt ($_.Size * $minPercent/100)) } | 
    Sort-Object SystemName, DeviceID | 
    ft -property $tableSpec -AutoSize | 
    Out-String 

    ) 

Send-MailMessage -Body $report -To $toList -Subject "Disk space report" -SmtpServer $smtpServer 
Смежные вопросы