Implementing Your Own Runbook Input Parameter Validation Checking

Implementing Your Own Runbook Input Parameter Validation Checking

  • Comments 4
  • Likes

Using the “Initialize Data” activity at the beginning of a runbook allows you to provide input parameters to any runbook. This greatly enhances the flexibility of a runbook by allowing it to be called by another runbook or via the web service, and the input parameters supplied to vary the data being used inside the runbook. However, the Initialize Data activity doesn’t allow you to specify whether parameters are required or optional and doesn’t provide any value checking to validate the data being passed in before it’s used by the runbook. Here’s where the power of PowerShell can come in handy!

In PowerShell, you can define function parameters with lots of different validation options. When using PowerShell in the Run .NET Script activity, you can use this validation to your advantage by essentially creating a function header that defines how you want to validate your runbook input parameters. You can use nearly all of the validation options in the Run .NET Script activity. The only ones that won’t apply are the ones that have to do with null values and collections (since all the input parameters will be strings or numbers).

(Note: For more info about function parameters and validation, see the TechNet documentation.)

Here’s a list of the validation types you can use (I’ll show some examples below):

[AllowEmptyString()]
[ValidateCount(1,5)]
[ValidateLength(1,10)]
[ValidatePattern("[0-9][0-9][0-9][0-9]")]
[ValidateRange(0,10)]
[ValidateScript({$_ -ge (get-date)})]
[ValidateSet("Low", "Average", "High")]
[ValidateNotNullOrEmpty()]

You can also use the Mandatory=$true|$false and ParameterSetName options on the Parameter attribute to define whether parameters are optional or not and whether they are grouped into different parametersets.Of course, I thought about creating a custom activity that would allow specifying parameter names, validation type and specific validation for each parameter, but I thought that would end up being kind of clunky. Sometimes, it’s easier just writing a script for what you need. So I came back around to the Run .NET Script activity and wrote a custom PowerShell function with parameters to validate the runbook input parameters.

In the example below, the Run .NET Script activity has a custom function checks four parameters: “ComputerName”, “ComputerOwner”, “IPAddress” and “FloorNumber”. In this hypothetical example,

image

The function validates that either a computer name or IP address was entered (one or the other is required). If a computer name is entered, an optional user name can be entered, but it must be one of three specific names. Optionally, the user can enter a floor number, but it must be a number between 2 and 15..

function Validate-Parameters
{
    [CmdletBinding()]
    param(
        [parameter(Mandatory=$true, ParameterSetName="Computer")]
        [ValidateNotNullOrEmpty()]
        [String] $ComputerName,

        [parameter(Mandatory=$false, ParameterSetName="Computer")]
        [ValidateSet("Bob", "Mary", "Joe")]
        [String] $ComputerOwner = "",

        [parameter(Mandatory=$true, ParameterSetName="IP")]
        [ValidatePattern("(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\.(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\.(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\.(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)")]
        [String] $IPAddress,

        [parameter(Mandatory=$false)]
        [ValidateRange(2,15)]
        [Int] $FloorNumber
            
    )
    Write-Output "Validation succeeded"
}

$cmd = "Validate-Parameters "
if ($computerName -ne "")
{
    $cmd += ' -ComputerName $($computerName)'
}
if ($computerOwner -ne "")
{
    $cmd += ' -computerOwner $($computerOwner )'
}
if ($IPAddress -ne "")
{
    $cmd += ' -IPAddress $($IPAddress)'
}
if ($FloorNumber -ne "")
{
    $cmd += ' -FloorNumber $($FloorNumber)'
}
$Output = iex -Command $cmd

Now you just add the input parameters from the previous activity as PowerShell variables:

image

If the parameters fail validation, PowerShell will throw an exception, causing the activity to fail. If the Run .NET Script activity fails, the link conditions will cause the Send Platform Event activity to run. That activity is configured like this:

image

When you pull in the Error summary text, you get a good error message that tells you how the parameter validation failed.

image

So there you have it… you can take this and cut and paste it into any runbook and simply modify the parameter validation to suit your own runbook’s parameters. Now you have a good way to validate runbook parameters using potentially complex rules by using the power of PowerShell!

Your comment has been posted.   Close
Thank you, your comment requires moderation so it may take a while to appear.   Close
Leave a Comment
  • Just getting started with Orchestrator, so forgive me if this is a dumb question.

    Would it be possible/practical/useful to take a page from PS remoting, and pass Powershell objects through the data bus by serializing them to xml?

  • Yes, you could serialize PS objects to XML in order to pass them on the data bus. However, if you intend on using them as PS Objects by de-serializing them later, it might be more efficient (especially with PS 3.0) to simply keep a session open and pass them behing the scenes in the runspace using variable names.

  • Using disconnected sessions in V3 will obviously change some things.

    Something I found very awkward was the the granular mapping of Orchestrator variable names to script parameters. Originally I was considering using XML as a mechanism to simply that, but have since found what I think is a better approach.

    In your Initialize Data activity, you create discrete variables for each parameter of the script the data is being fed to, and then subscribe to all of those variables in the .Net script activity, mapping the script variable names to the subscribed Orchestrator variables.  

    If you use the Initialize Data activity to create Parameter = Value pair strings, in your script you can just insert the published data into a here-string, run that through convertfrom-stringdata and that gives you a hash table you can splat to your command.  You can also pass $null and boolean $true and $false values for e.g. switch parameters this way.  If you're reading the input from a file, you can use get-lines, and then flatten the data and separate with line breaks and that goes into the here-string very nicely.

    Just my .02

  • "Now you just add the input parameters from the previous activity as PowerShell variables:"

    add them where? at the top of the script in the Run .Net Script activitiy? or the bottom?