Refactored - Top Rated Cloud Training

View Original

Building PowerShell Functions

*If you're just joining us, this post is part of a series on Getting Started with PowerShell. If you'd like to catch up (or skip ahead), click on the appropriate post below.

Getting Started with PowerShell
Windows PowerShell, PowerShell Core and PowerShell: Huh?
Installing PowerShell and Visual Studio Code
Running PowerShell Commands and Getting Help
Working with the PowerShell Pipeline
Writing your First PowerShell Script
Understanding Loops in PowerShell
Using PowerShell Modules
Connecting to Azure
PowerShell Error Handling

Seasoned software developers will tell you to build code like Legos. They'll tell you, in no uncertain terms, to not repeat yourself. Practice the DRY method. Build snippets of code as blocks. If you need to perform more advanced tasks, don't write the snippet again. Use the block you created earlier.

Writing PowerShell code as blocks and using those blocks to create more advanced scripts saves time and makes code more more manageable.

Those blocks are functions.

You can think of functions as blocks of code to perform a single task like starting a server, moving a file or retrieving a registry key value. You've been using "function-like" commands for a while now using cmdlets.

At this point in your PowerShell learning, you can think of cmdlets the same as functions. They are both commands built for a specific purpose that perform a single task.

When to Build a Function

The best way to learn functions is to build a function based on a real example. Let's use connecting to Azure as an example.

In the a previous post in this series , you learned how to connect to Azure interactively or via a service principal. In that post, you learned about a cmdlet that checks what Azure subscription you've authenticated to (if any) called Get-AzContext. You also learned about a cmdlet to authenticate to Azure called Connect-AzAccount.

You only need to run Connect-AzAccount once to connect to Azure but you find yourself forgetting and constantly running the command over and over again wasting time. Let's build a function so you don't waste your time.

Writing Your First Function

Open up a Visual Studio Code window, save a script as Connect-MyAzAccount.ps1 and let's get started!

First, type up a function scaffold. Below you'll see the bare bones of a function called Connect-MyAzAccount. What you see here is a function framework, if you will. You should start every function you create like this. You'll fill in the blanks in a minute.

function Connect-MyAzAccount {
    [CmdletBinding()]
    param()
}

Save the script now and let's try it out. To use a function, you must first load it into a PowerShell session. There are a few ways to do that. You could copy and paste the code directly into a PowerShell window and hit Enter. That method would work for learning but it's not much good for actual work.

Dot Sourcing

Instead of just copying and pasting the function into the console, let's dot source the function. Dot sourcing is a term that refers to "loading" code from a PowerShell script into memory.

You've executed a script before in a previous post <link here>. When you ran the script, the code inside ran and did something. Dot sourcing, on the other hand, "loads" the code into the session but doesn't execute any code.

To dot source the Connect-MyAzAccount.ps1 script you just created, act like you're going to execute a script like .\\Connect-MyAzAccount.ps1. But, add a period (dot) at the beginning and hit Enter.

. .\Connect-MyAzAccount.ps1

Notice nothing happens even though there's code in the script. This happens because PowerShell saw a function. It loaded the function into memory and is now ready for you to run the function yourself.

Calling the Function

To run the function, execute it just like you would any cmdlet - Connect-MyAzAccount. Nothing happens. Why? Because you haven't added any code to the function yet but you were able to call the function now. Step one complete and onto step two.

Adding Code

Once you have the function framework built out and you know how to call the function, you now need to start adding code to make it do something.

For this example, you'd like a function to first check if you're currently authenticated to Azure. If you're not connected to Azure, then try to connect. Otherwise, just send yourself a message.

To create a function, you should first test the code and verify it's behavior. Let's break this down.

  • Check if you're currently authenticated

  • If connected, write a message to the console

  • If not connected, attempt to connect

First, write the code to verify you're connected with the Get-AzContext command. Be sure to monitor the behavior both when you're connected and when not.

With some testing, you've confirmed that Get-AzContext returns nothing when you're not connected and information about the connection when you are. Perfect. You have a condition to test on using an if/then statement.

Below you can see some code to test whether or not you're connected.

if (-not (Get-AzContext)) {

}    else {

}

Now fill in the blanks providing what to do when you are connected and when you're not.

function Connect-MyAzAccount {
    [CmdletBinding()]
    param()

    if (-not (Get-AzContext)) {
        Connect-AzAccount
    }    else {
        Write-Host 'You are already connected, dummy!'
    }
}

You've now created a function that actually does something! Now, dot source it again to load the fresh copy into the session. Run the function and depending on if you're connected or not, it will accommodate.

You now have a custom function that solves a simple problem. This is the whole concept of functions. They are "blocks" made of code that act like shortcuts to perform various tasks.

We did not cover parameters in this tutorial. If you'd like to learn about using parameters in functions, check out PowerShell Parameters: Everything You Ever Wanted to Know.

Conclusion

Functions are the building blocks of PowerShell. Try to start recognizing opportunities to create functions. Create a function whenever you notice repetition in scripts then call the function in a single line instead of recreating the wheel.