I currently have a script that runs daily and sends me a HTML file of the servers and their disk space that is available.

I would like to make some changes to it, but I am far from a Powershell God.

I would like to be able to check across two domains that do not have trust (I have the credentials, obviously) and if possible some PC’s that we have on a workgroup.

I would also like it to show the server in red if the available space is below 15%.

And lastly, if possible, I’d like it to check for the html reports older than 7 days and delete them.

The script is below;

# Custom HTML Report Formatting
$html = "<style>"
$html = $html + "BODY{background-color:White;}"
$html = $html + "TABLE{border-width: 1px;border-style: solid;border-color: black;border-collapse: collapse;}"
$html = $html + "TH{border-width: 1px;padding: 0px;border-style: solid;border-color: LightGrey;background-color:#F0E68C}"
$html = $html + "TD{border-width: 1px;padding: 0px;border-style: solid;border-color: LightGrey;background-color:#FAFAD2}"
$html = $html + "</style>"

# Script Variables
$Servers = (gc "d:\diskspace\servers.txt")
$ErrorActionPreference = "SilentlyContinue"
$SizeInGB=@{Name="Size(GB)"; Expression={"{0:N2}" -f ($_.Size/1GB)}}
$FreespaceInGB=@{Name="Freespace(GB)"; Expression={"{0:N2}" -f ($_.Freespace/1GB)}}
$PercentFree=@{name="PercentFree(%)";Expression={[int](($_.FreeSpace/$_.Size)*100)}}

#Script Body
Write-Output "Gathering Disk Usage Information..."
gwmi -query "SELECT SystemName,Caption,VolumeName,Size,Freespace FROM win32_logicaldisk WHERE DriveType=3" -computer $Servers |
Select-Object SystemName,Caption,VolumeName,$SizeInGB,$FreespaceInGB,$PercentFree |
sort-object "SystemName" |
ConvertTo-Html -as table -head $html -body "<H2>Server Disk Space Report $(( get-date ).ToString('dd/MM/yyyy'))</H2>"|
Out-File "d:\diskspace\reports\ServerDiskSpaceReport--$(( get-date ).ToString('yyyyMMdd')).html"

Is anything that I am asking possible?

Thanks.

3 Spice ups

Yes, all that is possible. There are scripts shared here in SW, and this one ( https://community.spiceworks.com/scripts/show/2235-delete-files-based-on-3-different-date-options ) will give you the information needed to write your ‘delete files older than’ part of your script.

1 Spice up

Also, please use the Insert Code button when posting code. It makes it much easier to read.

codebutton_small.png

(Taken from Neally)

2 Spice ups

In order for PowerShell to reach from one pc to another, 2 things will have to be enabled on each remote machine. 1 would be setting the execution policy ( ITPro Today: IT News, How-Tos, Trends, Case Studies, Career Tips, More step 2 explains the options) and 2 would be allowing remoting which may or may not be needed, depending on what you are trying to run on the remote machines ( https://4sysops.com/archives/enable-powershell-remoting/ ). Here’s a decent write-up on running commands on remote machines ( https://4sysops.com/archives/use-powershell-invoke-command-to-run-scripts-on-remote-computers/ ).

As to changing the background color of a cell based on the percent of remaining space - without seeing how you are adding that information into your table itself - just before the code that puts that information into a cell, I’d run a simple if()

if ($PercentFree -lt 15)
{ <td style = "background-color: red"> }
else
{ <td> }
1 Spice up

Powershell is a great tool. Why not use a proper tool like the spiceworks network monitor, or some other the onsite spiceworks install with the inventory section. You can create alerts, run reports etc. You would not need to run a scheduled or on demand task and would gain more information.

1 Spice up

You would use Get-Credential to create a credential object and then pass that object to Get-WmiObject. I would also break out the computer list into separate variables for each different credential. Here’s an example of how this would look ( untested ).

$Domain1Servers = @(
    'Server1'
    'Server2'
    )

$Domain2Servers = @(
    'Server3'
    'Server4'
    )

$WorkGroupServers = @(
    'Server5'
    'Server6'
    )

$Domain1Cred   = Get-Credential -Credential 'domain1\user1'
$Domain2Cred   = Get-Credential -Credential 'domain2\user2'
$WorkGroupCred = Get-Credential -Credential 'user3'

$WMIQuery = "SELECT SystemName,Caption,VolumeName,Size,Freespace FROM win32_logicaldisk WHERE DriveType=3"

$Domain1Disk   = Get-WmiObject -Query $WMIQuery -ComputerName $Domain1Servers -Credential $Domain1Cred
$Domain2Disk   = Get-WmiObject -Query $WMIQuery -ComputerName $Domain2Servers -Credential $Domain2Cred
$WorkGroupDisk = Get-WmiObject -Query $WMIQuery -ComputerName $WorkGroupServers -Credential $WorkGroupCred

( $Domain1Disk + $Domain2Disk + $WorkGroupDisk ) |
    Select-Object -Property SystemName,Caption,VolumeName,$SizeInGB,$FreespaceInGB,$PercentFree

Take a look at @martin9700 's Set-CellColor function.

https://community.spiceworks.com/scripts/show/2450

You could do something like this:

Get-ChildItem -Path 'D:\DiskSpace\Reports' |
    Where-Object { $_.CreationTime -lt ( Get-Date ).Date.AddDays(-7) } |
    Remove-Item
1 Spice up

The script in my OP is the entire thing.

I am unsure were to add the colour change part. The other link to a script, that seems a bit long winded?

Ok, this script does most of what I want it to now, except the colours.

# Custom HTML Report Formatting
$html = "<style>"
$html = $html + "BODY{background-color:#b0c4de;}"
$html = $html + "TABLE{border-width: 1px;border-style: solid;border-color: black;border-collapse: collapse;}"
$html = $html + "TH{border-width: 1px;padding: 3px;border-style: solid;border-color: black;background-color:#778899}"
$html = $html + "TD{border-width: 1px;padding: 3px;border-style: solid;border-color: black;}"
$html = $html + "tr:nth-child(odd) { background-color:#d3d3d3;}" 
$html = $html + "tr:nth-child(even) { background-color:white;}"  
$html = $html + "</style>"
 
# Script Variables
$ErrorActionPreference = "SilentlyContinue"
$SizeInGB=@{Name="Size(GB)"; Expression={"{0:N2}" -f ($_.Size/1GB)}}
$FreespaceInGB=@{Name="Freespace(GB)"; Expression={"{0:N2}" -f ($_.Freespace/1GB)}}
$PercentFree=@{name="PercentFree(%)";Expression={[int](($_.FreeSpace/$_.Size)*100)}}
 
# Script Body
Write-Output "Gathering Disk Usage Information..."
$Domain1Servers = @(
    'server1'
    'server2'
    )

$Domain2Servers = @(
    'server3'
    'server4'
    )

$WorkGroupServers = @(
    'Server5'
    'Server6'
    )

$AdminName1 = "domain1\user"
$AdminName2 = "domain2\user"
$AdminName3 = "workgroupuser"

$Domain1 = Get-Content "d:\diskspace\d1.txt" | ConvertTo-SecureString
$cred1 = new-object -typename System.Management.Automation.PSCredential -argumentlist $AdminName1, $Domain1
$Domain2 = Get-Content "d:\diskspace\d2.txt" | ConvertTo-SecureString
$cred2 = new-object -typename System.Management.Automation.PSCredential -argumentlist $AdminName2, $Domain2
$Domain3 = Get-Content "d:\diskspace\d3.txt" | ConvertTo-SecureString
$cred3 = new-object -typename System.Management.Automation.PSCredential -argumentlist $AdminName3, $Domain3

$WMIQuery = "SELECT SystemName,Caption,VolumeName,Size,Freespace FROM win32_logicaldisk WHERE DriveType=3"

$Domain1Disk   = Get-WmiObject -Query $WMIQuery -ComputerName $Domain1Servers -Credential $cred1
$Domain2Disk   = Get-WmiObject -Query $WMIQuery -ComputerName $Domain2Servers -Credential $cred2
$WorkGroupDisk = Get-WmiObject -Query $WMIQuery -ComputerName $WorkGroupServers -Credential $cred3

( $Domain1Disk + $Domain2Disk + $WorkGroupDisk ) |
Select-Object -Property SystemName,Caption,VolumeName,$SizeInGB,$FreespaceInGB,$PercentFree |
sort-object "SystemName" |
ConvertTo-Html -as table -head $html -body "<H2>Server Disk Space Report $(( get-date ).ToString('dd/MM/yyyy'))</H2>"|
Out-File "d:\diskspace\reports\ServerDiskSpaceReport--$(( get-date ).ToString('yyyyMMdd')).html"

I just don’t know where to put the row colour for the less than 15% variable.

Running a tool would be great except that we are not allowed to implement 3rd party software on clients systems, so this is the middle ground.

What happened to the post above by M Boyle?

Ah, I see now. You only have the header of the file within the tags then. The information gathered from the servers is just text appended after the header table with all saved as a .html file, yes? In that case, I’m not sure how to change the background color of that one. If the output is different than I’ve guessed, and is actually fully formed html, then you could probably add the commands to read the file back into a variable, then once past the header information, check each line for a number < 15 and edit the tag with the style and resave it. That’s pretty cludgy, though. Anyone else have an idea?

1 Spice up

This is what it outputs. TBH if making a line red is difficult then they will just need to be vigilant when they receive the emailed HTML attachment with all of the information in!diskspace.jpg

Something like this seems to work. I’m not terribly great with HTML, so there may be a neater way to go about it.

$Data = ( $Domain1Disk + $Domain2Disk + $WorkGroupDisk ) |
    Select-Object -Property SystemName,Caption,VolumeName,$SizeInGB,$FreespaceInGB,$PercentFree |
    sort-object "SystemName" |
    ConvertTo-Html -as table -head $html -body "<H2>Server Disk Space Report $(( get-date ).ToString('dd/MM/yyyy'))</H2>"
    
$Index = ( ( $Data | Where-Object { $_ -like '*PercentFree(%)*' } ) -split '</th><th>' -replace '^<tr><th>|</th></tr>$' ).IndexOf('PercentFree(%)')

$Colored = foreach( $Row in $Data ){
    if( $Row -match '^<tr><td>' ){
        $FreeSpace = ( $Row -split '</td><td>' )[$Index] -replace '[</tdr>]'
        if( [int]$FreeSpace -lt 25 ){
            $Row -replace '<td>', '<td style="background-color:red">'
            }
        else{
            $Row
            }
        }
    else{
        $Row
        }
    }  
    
$Colored |
    Out-File "d:\diskspace\reports\ServerDiskSpaceReport--$(( get-date ).ToString('yyyyMMdd')).html"
1 Spice up