---
title: "Creating a Real-World Module: Creating Functions"
description: "Learn how to create PowerShell functions that gather memory, storage, and processor information from remote systems, transforming raw output into readable formats."
canonical: "https://adamtheautomator.com/powershell-functions-module/"
---

# Creating a Real-World Module: Creating Functions

> Learn how to create PowerShell functions that gather memory, storage, and processor information from remote systems, transforming raw output into readable formats.

Source: https://adamtheautomator.com/powershell-functions-module/

---

ATA Learning

Tap to hide

[

ATA Learning

](/)

*   [Home](/)
*   [Tutorials](/tutorials/)
*   [Instructors](/author/)
*   [Advertising](/advertising/)
*   [Recommended Resources](/resources/)
*   [About Adam](/about-adam/)

Search for:  

*   [](https://twitter.com/adbertram)
*   [](https://github.com/Adam-the-Automator)
*   [](https://www.linkedin.com/company/adam-the-automator-llc)
*   [](/feed/)

![Creating a Real-World Module: Creating Functions](https://adamtheautomator.com/wp-content/uploads/2025/03/featured-image.webp)

# Creating a Real-World Module: Creating Functions

[![](https://secure.gravatar.com/avatar/d0b9d42e21e5622713f8b693aa5c0f9244d5f7dd200ed29b8398f52dee5de337?s=192&d=mm&r=g)Adam Bertram](https://adamtheautomator.com/author/adam-bertram/)20 March 20252 min. read

Categories: [IT Ops](/category/it-ops/)

Tags:[PowerShell](/tag/powershell/)

Table of Contents

*   [Building Functions for Extracting Information](#building-functions-for-extracting-information)
*   [Transforming Output](#transforming-output)
*   [Handling Byte Values](#handling-byte-values)
*   [Conclusion](#conclusion)

Managing systems can feel like juggling too many balls at once. One minute, you’re troubleshooting a storage issue; the next, you’re hunting down processor specs or checking memory capacity. Doing so manually is not only tedious but prone to mistakes. If you’re stuck in this cycle, it’s time to stop the madness. Automation is your answer!

In this guide, you’ll learn how to build PowerShell functions so you can streamline your workflows and focus on what really matters.

Enjoy a set of powerful scripts in your toolkit, saving you time and helping you operate like a pro!

### Building Functions for Extracting Information

As we build on the module, we’ll populate the `Info` property with hardware information using the `Get-CimInstance` cmdlet. This approach allows us to standardize and reuse code effectively.

The following functions gather memory, storage, and processor information from a remote session:

```powershell
function Get-MemoryInfo {
    [CmdletBinding()]
    param(
        [Parameter(Mandatory)]
        [System.Management.Automation.Runspaces.PSSession]$Session
    )

    $outObject = @{
        'ComputerName'      = $Session.ComputerName
        'HardwareCategory'  = 'Memory'
        'Info'              = $null
    }

    $scriptBlock = {
        Get-CimInstance -ClassName Win32_PhysicalMemory
    }
    $result = Invoke-Command -Session $Session -ScriptBlock $scriptBlock

    $outObject['Info'] = $result
    [pscustomobject]$outObject
}

function Get-StorageInfo {
    [CmdletBinding()]
    param(
        [Parameter(Mandatory)]
        [System.Management.Automation.Runspaces.PSSession]$Session
    )

    $outObject = @{
        'ComputerName'      = $Session.ComputerName
        'HardwareCategory'  = 'Storage'
        'Info'              = $null
    }

    $scriptBlock = {
        Get-CimInstance -ClassName Win32_LogicalDisk
    }
    $result = Invoke-Command -Session $Session -ScriptBlock $scriptBlock

    $outObject['Info'] = $result
    [pscustomobject]$outObject
}

function Get-ProcessorInfo {
    [CmdletBinding()]
    param(
        [Parameter(Mandatory)]
        [System.Management.Automation.Runspaces.PSSession]$Session
    )

    $outObject = @{
        'ComputerName'      = $Session.ComputerName
        'HardwareCategory'  = 'Processor'
        'Info'              = $null
    }

    $scriptBlock = {
        Get-CimInstance -ClassName Win32_Processor
    }
    $result = Invoke-Command -Session $Session -ScriptBlock $scriptBlock

    $outObject['Info'] = $result
    [pscustomobject]$outObject
}
```

### Transforming Output

The raw data retrieved from system queries often includes more details than necessary, making it cumbersome to interpret. This situation can lead to inefficiencies when focusing on specific, actionable attributes.

To standardize the data, you can transform the output from `Get-CimInstance` into a custom object.

Here’s an updated version:

```powershell
function Get-MemoryInfo {
    [CmdletBinding()]
    param(
        [Parameter(Mandatory)]
        [System.Management.Automation.Runspaces.PSSession]$Session
    )

    $outObject = @{
        'ComputerName'      = $Session.ComputerName
        'HardwareCategory'  = 'Memory'
        'Info'              = $null
    }

    $scriptBlock = {
        Get-CimInstance -ClassName Win32_PhysicalMemory
    }
    $result = Invoke-Command -Session $Session -ScriptBlock $scriptBlock

    $info = $result | ForEach-Object {
        [pscustomobject]@{
            'LocatorId' = $_.DeviceLocator
            'Capacity'  = $_.Capacity
        }
    }

    $outObject['Info'] = $info
    [pscustomobject]$outObject
}

function Get-StorageInfo {
    [CmdletBinding()]
    param(
        [Parameter(Mandatory)]
        [System.Management.Automation.Runspaces.PSSession]$Session
    )

    $outObject = @{
        'ComputerName'      = $Session.ComputerName
        'HardwareCategory'  = 'Storage'
        'Info'              = $null
    }

    $scriptBlock = {
        Get-CimInstance -ClassName Win32_LogicalDisk
    }
    $result = Invoke-Command -Session $Session -ScriptBlock $scriptBlock

    $info = $result | ForEach-Object {
        [pscustomobject]@{
            'VolumeName'      = $_.VolumeName
            'VolumeLetter'    = $_.DeviceId
            'VolumeCapacity'  = $_.Size
            'VolumeFreeSpace' = $_.FreeSpace
        }
    }

    $outObject['Info'] = $info
    [pscustomobject]$outObject
}
```

### Handling Byte Values

Hardware information often includes numerical values like memory or storage capacity in bytes. While technically accurate, these values could be more practical for quick interpretation. Converting them to gigabytes provides a more intuitive understanding of hardware metrics.

For better readability, the helper function `ConvertTo-Gb` makes this process efficient:

```powershell
function ConvertTo-Gb {
    [CmdletBinding()]
    param(
        [Parameter(Mandatory)]
        [string]$Bytes
    )

    $numberGb = $Bytes / 1GB
    [math]::Round($numberGb, 2)
}

function Get-MemoryInfo {
    [CmdletBinding()]
    param(
        [Parameter(Mandatory)]
        [System.Management.Automation.Runspaces.PSSession]$Session
    )

    $outObject = @{
        'ComputerName'      = $Session.ComputerName
        'HardwareCategory'  = 'Memory'
        'Info'              = $null
    }

    $scriptBlock = {
        Get-CimInstance -ClassName Win32_PhysicalMemory
    }
    $result = Invoke-Command -Session $Session -ScriptBlock $scriptBlock

    $info = $result | ForEach-Object {
        [pscustomobject]@{
            'LocatorId' = $_.DeviceLocator
            'Capacity'  = (ConvertTo-Gb -Bytes $_.Capacity)
        }
    }

    $outObject['Info'] = $info
    [pscustomobject]$outObject
}
```

This approach improves the functionality and readability of the data returned by these functions. Future updates or changes become more manageable by centralizing repetitive logic into helper functions like `ConvertTo-Gb`.

### Conclusion

You’ve learned how to create PowerShell functions using the steps outlined in this guide. Be it gathering hardware information from remote systems, transforming raw outputs into structured custom objects, or making data more readable.

Now that you’ve mastered these techniques, consider how you can expand on this foundation. For instance, you could add more hardware categories to your module, such as network adapters or GPU information. You might also integrate these functions into larger automation workflows, like system health monitoring or inventory management.

The possibilities are endless, and you’re well on your way to building a robust toolset for confidently managing your systems.

Share this article

[Share on X](https://twitter.com/intent/tweet?url=https%3A%2F%2Fadamtheautomator.com%2Fpowershell-functions-module%2F&text=Creating%20a%20Real-World%20Module%3A%20Creating%20Functions)[Share on Facebook](https://www.facebook.com/sharer/sharer.php?u=https%3A%2F%2Fadamtheautomator.com%2Fpowershell-functions-module%2F)[Share on LinkedIn](https://www.linkedin.com/sharing/share-offsite/?url=https%3A%2F%2Fadamtheautomator.com%2Fpowershell-functions-module%2F)

## Related Posts

![](https://adamtheautomator.com/wp-content/uploads/2026/06/26995-troubleshoot-dns-issues-powershell-codex.webp)

### [Troubleshoot DNS Issues with PowerShell](/troubleshoot-dns-issues-powershell/)

Troubleshoot DNS issues with PowerShell by testing name resolution, DNS client settings, cache entries, and network connectivity in a repeatable workflow.

![](https://adamtheautomator.com/wp-content/uploads/2025/10/image_2025-10-24_095322075.png)

### [Migrating from PowerShell 6 to 7.5: Breaking Changes/New Features](/migrating-powershell-6-to-7-5/)

Migrate from PowerShell Core 6 to 7.5: breaking changes, features, and testing tips.

![](https://adamtheautomator.com/wp-content/uploads/2025/06/featured-image-6.png)

### [How to Add Timeouts to Pester Tests with PowerShell Runspaces](/pester-test-timeout-runspaces/)

Prevent Pester tests from hanging indefinitely using PowerShell runspaces. Learn to handle variable scoping, module loading, TestDrive access, and stream capture challenges with timeout protection.

## Categories

*   [IT Ops](/category/it-ops/)
*   [Cloud](/category/cloud/)
*   [DevOps](/category/devops/)
*   [Home Ops](/category/home-ops/)
*   [Information Security](/category/infosec/)
*   [Software Development](/category/software-development/)

## Site

*   [Home](/)
*   [Tutorials](/tutorials/)
*   [Instructors](/author/)
*   [Advertising](/advertising/)
*   [Recommended Resources](/resources/)
*   [About Adam](/about-adam/)

Copyright 2026© ATA Learning | [Privacy Policy](/privacy/)
