Human Readable File Sizes in PowerShell

2 min reading time

With PowerShell you can easily get the file size of a file or folder. When you use the Get-ChildItem command the Length property is the size of the item.

Measuring Files

> Get-ChildItem .\README.md | Select Length

Length
------
  1432

The Measure-Object command can also calculate the sum for the Length property.

> Get-ChildItem .\README.md | Measure-Object -Property Length -sum

Count             : 1
Average           :
Sum               : 1432
Maximum           :
Minimum           :
StandardDeviation :
Property          : Length

Also, Measure-Object can already do the summation for us when selecting multiple files.

> Get-ChildItem *.md | Measure-Object -Property Length -Sum

Count             : 2
Average           :
Sum               : 2187
Maximum           :
Minimum           :
StandardDeviation :
Property          : Length

These numbers are in bytes and now I want to know what that is when the bytes is 1928394. PowerShell has a great built in math format to divide the bytes into KB, MB, GB, TB.

> 1928394 / 1MB

1.83905982971191

Making it more human readable

We’re getting closer! Now I wanted to add the size of whether this was now in kilobytes or gigabytes and do a string manipulation. Luckily we can do that and format the byte conversion to a readable format like 1.84 MB. Here’s a helper function to complete this.

function DisplayFileSize {
    param (
        $bytecount
    )
    
    switch -Regex ([math]::truncate([math]::log($bytecount,1024))) {
        '^0' {"$bytecount Bytes"}
        '^1' {"{0:n2} KB" -f ($bytecount / 1KB)}    
        '^2' {"{0:n2} MB" -f ($bytecount / 1MB)}
        '^3' {"{0:n2} GB" -f ($bytecount / 1GB)}
        '^4' {"{0:n2} TB" -f ($bytecount / 1TB)}
        Default {"{0:n2} Bytes" -f ($bytecount / 1KB)}
    }
}

> DisplayFileSize 1928394

1.84 MB

This function takes the input as bytes and outputs it in the proper size format of KiloBytes up to TerraBytes.

Generating reports of folders

I used this process to read a folder and calculate the file size of the subfolders. This was helpful to identify which folders were the largest in a directory.

$startFolder = "C:\git"

$report = Get-ChildItem $startFolder -Directory | Sort-Object | ForEach-Object {
    $subFolderItems = Get-ChildItem $_.FullName -recurse -force -File | `
                        Measure-Object -property Length -sum | Select-Object Sum
    $finalSize = DisplayFileSize -bytecount $subFolderItems.sum
    
    [PSCustomObject]@{
        Path = $_.FullName
        Size = $finalSize
    } 
}

$report | Format-Table -AutoSize

This process looks at a top folder and calculates the size of the folders with in it. For each directory, we then recursively find all the files and sum the Length property, then pass it into our DisplayFileSize function to humanize the output.

Path                                 Size
----                                 ----
C:\git\personal-website\.cache       28.55 MB
C:\git\personal-website\.frontmatter 456 Bytes
C:\git\personal-website\.mattrbld    5.98 KB
C:\git\personal-website\.vercel      608 Bytes
C:\git\personal-website\config       13.73 KB
C:\git\personal-website\dist         58.15 MB
C:\git\personal-website\node_modules 143.45 MB
C:\git\personal-website\src          51.43 MB
C:\git\personal-website\ssl          2.97 KB
C:\git\personal-website\tools        7.98 KB

Conclusion

This was helpful in seeing which folder was the largest within a subdirectory of photos or other large files for example to see if that made sense or not and take action accordingly. Also a general reporting tool to see which folders are the largest or smallest.


I'm publishing this as part of 100 Days To Offload. You can join in yourself by visiting 100DaysToOffload.com.


Reply via email | Edit this page on Codeberg