Adding Methods to a PowerShell 5 Class


Summary: Ed Wilson, Microsoft Scripting Guy, talks about adding methods to a Windows PowerShell 5.0 class in Windows 10.

Microsoft Scripting Guy, Ed Wilson, is here. Having a bunch of properties, although cool, is in the end, rather unsatisfying. I remember trying to teach VBScript and WMI in the old days. Although it was possible to glean lots of information, there were few things that actually did anything.

I could easily find the name and the driver of the sound card, but I could not disable the sound card. I could find the screen resolution, but I could not change the screen resolution. I could find the currently logged on user, but I could not log the user out…and so on.

It became very frustrating because in the end, it comes down to needing to actually do something. I mean I can describe all I want, but what can I really do? It is sort of the difference between reading a literary novel where nothing happens and reading a thriller where every page contains action. I prefer action—most of the time.

In Windows PowerShell classes, it is the methods that actually do something. Properties describe things. So, how do I add a method?

There are two types of methods I am going to add. For the first method, I simply call it, and it works. For the second method, I need to supply some information for the method to work. I am not adding any constraints or anything else. The point is to show you how to implement the methods. I will conclude the post by showing three ways of calling the methods after they are implemented.

   Note  This is the fifth post in a series about creating classes in Windows PowerShell 5.0. You should read the earlier
   posts prior to reading today's post:

   Another Note  I talked about enums last week. If you need to review enums, you should read:

The first method I want to add does not require any input parameters. I simply call the method and it works. For an example, and to have easier to read code, I am going back to the basic Car class (without the enums):

Class Car

{

    [String]$vin

    static [int]$numberOfWheels = 4

    [int]$numberOfDoors

    [datetime]$year

    [String]$model

}

To add a method to the class, I simply go to the bottom of the class, and add the name of my method. I then use () to designate that it is a method, and I add my script block (surrounded by curly braces) that contains the code I want to call when I call the method.

The first method I will add is called the SoundHorn method. When I call this method, it will sound a beep for a few seconds. The method is shown here:

SoundHorn () {[console]::beep(800,900)}

The next method I want to add is the Accelerate method. When I accelerate, I need to know how fast I am going, so I need to be able to pass a value to the method. The input will be contained in the $arg variable. I will then use this value to determine how fast my car will go.

What the method is actually doing is starting at a relatively low beep, and increasing the frequency of the beep a certain number of times. This is determined by my speed supplied to the $arg variable. I do not have any error checking or parameter input validation, and so you should probably keep your speed less than 50 mph or so.

Here is the method that accepts an input parameter:

Accelerate ($arg)

        {300..($arg * 100) |

         Foreach {[console]::beep($_,150)}}

The complete  class with the two new methods is shown here:

Class Car

{

    [String]$vin

    static [int]$numberOfWheels = 4

    [int]$numberOfDoors

    [datetime]$year

    [String]$model

    SoundHorn () {[console]::beep(800,900)}

    Accelerate ($arg)

        {300..($arg * 100) |

         Foreach {[console]::beep($_,150)}}

}

I run my script and I can test my methods. The first way I can call my method, is to create an instance of the car (a new Car object), store the returned object in a variable, and then call the method. This is shown here:

PS C:\> $a = New-Object car

PS C:\> $a.SoundHorn()

The second way to call the method is to call the New static method, and then call the method from that object:

PS C:\> [car]::new().SoundHorn()

A third way to call the method uses New-Object, and it is what I call the "group and dot." This is shown here:

PS C:\> (New-Object car).SoundHorn()

PS C:\> 

To call the accelerate method, I can use the same techniques:

PS C:\> $a = New-Object car

PS C:\> $a.Accelerate(25)

PS C:\> [car]::new().Accelerate(50)

PS C:\> (New-Object car).Accelerate(50)

Here is the script and the associated calling of the methods:

Image of command output

That is all there is to adding methods to a PowerShell 5.0 class. Windows PowerShell Classes Week will continue tomorrow when I will recap the class design and implementation.

I invite you to follow me on Twitter and Facebook. If you have any questions, send email to me at scripter@microsoft.com, or post your questions on the Official Scripting Guys Forum. See you tomorrow. Until then, peace.

Ed Wilson, Microsoft Scripting Guy

Comments (3)

  1. Mark Ince says:

    Great blog post! I have tried to add a method to do Write-Output of text, but it is not working.

    Below is the code

    Class Car
    {
    [string]$vin
    static[int]$numberOfWheels = 4
    [int]$numberOfDoors
    [datetime]$year
    [string]$model
    SoundHorn () {[console]::beep(800,900)}
    ShowDirection () {Write-Output "North"}
    Accelerate ($arg)

    {300..($arg * 100) |

    Foreach {[console]::beep($_,150)}}
    }

    $chrysler = New-Object car
    $chrysler.ShowDirection()

    doesn’t output North, nothing is returned.

    However, if I add
    [string]$direction
    to the class
    and change the method to
    ShowDirection() {$this.direction = "North"}

    the direction property on the object is updated to North. Am I just missing something simple?

  2. LEWIS says:

    Hi Mark, I’m not sure why this happens to be honest, I could have a wild guess but it would be exactly that, wild. An explanation would be great. I’d also love to get an example of imposing constraints for things like this. As an example: another property
    of the Car could be velocity. Well, if a car has velocity, it must have direction so how can I impose that restriction?

    Anyhoo, your question has a multitude of answers depending on what you really want to achieve:

    [string] ShowDirection() {
    Return "North"
    }

    [void] ShowDirection() {
    [Console]::Write("North")
    }

    Or create the property as you have done and…
    [void] ShowDirection() {
    [Console]::Write($this.direction)
    }

  3. Amor says:

    Hello,
    how to add static method and calling it ?

Skip to main content