Building a PowerShell Console Menu Revisited, Part 1


Today, I want to revisit a topic that pops up frequently and that’s building a menuing system in PowerShell. Typically the request is to create a script that presents a simple menu, and the operator merely selects an item from the list to execute. Going through this process might take a few articles so that I don’t overwhelm you, but let’s walk through this process.

You can most likely stop anywhere along the way and build your own meaning tool, but if you stick with it, I might have something worth waiting for. And as always, hopefully you’ll learn a little PowerShell along the way. Let’s begin.

For my demonstration, I’m not focusing on the PowerShell commands to actually perform the menu items, but rather how to display and use the menu. To that end, I’m going to define a here-string, which will represent the menu.

A here-string is an easy way to create a multi-line string without having to resort to concatenation. Simply type the text you want, including tabs. The only thing to watch is that the closing characters (“@) can’t have any whitespace before them. I typically make sure all of the text in a here-string is left justified. My menu variable looks like this:

A sample PowerShell menu (Image Credit: Jeff Hicks)
A sample PowerShell menu (Image Credit: Jeff Hicks)

To prompt the user to enter something, we can use Read-Host. The first part of a script might look like this:

To decide what command to execute, all we have to do is figure out what $r is equal to. You could use a series of If and ElseIf statements, but I find that a bit cumbersome. Instead, this is a great place to use a switch construct.

In the script, it might look like this:

In a switch statement, you tell PowerShell to do a comparison on some expression. In this case, it is the value of $r. So if $r is equal to “1”, PowerShell will execute the code in the scriptblock. Because Read-Host writes strings to the pipeline, I’m putting the numbers in quotes. In this situation, PowerShell is not case-sensitive, so it would process both lower and upper case versions of “Q”. The default scriptblock is optional, but I elected to insert one. Putting it all together, we get an experience like this.

Running a menu based script (Image Credit: Jeff Hicks)
Running a menu based script (Image Credit: Jeff Hicks)

The only thing missing is the PowerShell code within each switch scriptblock to accomplish the task. I created a very basic function called MyMenu with the commands I talked about. Here’s a more complete function for displaying a menu.

I’ve added parameters to display a title, as well as clear the screen. To use it, I can run code like this in a script to keep looping and displaying the menu until the user selects Q.

The Return key word terminates the pipeline and ends the loop. Here’s what it looks like without clearing the screen between activities.

Using Invoke-Menu (Image Credit: Jeff Hicks)
Using Invoke-Menu (Image Credit: Jeff Hicks)

At this point, all I need to do is build a script that loads the Invoke-Menu function and defines a Do loop. But I want to find an even easier way to work with console menus, which we’ll look at that next time.

Related Topics:

  • PowerShell

    Don't have a login but want to join the conversation? Sign up for a Petri Account