Table of Contents
Azure Automation, Start-AutomationRunbook, parameters, & CliXml…
I’m not going to explain what Clixml is, or what it means, nor am I going to explain exactly why this issue is happening (mainly because I don’t have a clear answer for you).
I’ll give you the solution and a possible way to make this easier for you.
To prevent CliXml parameter input, embed it in double quotes "$ParameterInput"
Yes, that simple…
In stead of this:
$Variable = Get-Variable DebugPreference
$Params = @{"string3"=$Variable}
Start-AutomationRunbook -Name 'RunbookName' -Parameters $Params
Do this:
$Variable = Get-Variable DebugPreference
$Params = @{"string3"="$Variable"}
Start-AutomationRunbook -Name 'RunbookName' -Parameters $Params
The double quotes embedded $Variable
– "$Variable"
is the only difference…
To walk through it completely, I first show what happened and then we look at better solutions later
The function below is an example.
I request a variable and then I pass it in the -Parameters
parameter (which is a HashTable, also known as Dictionary) for Start-AutomationRunbook
(internal Azure Automation cmdlet).
$runbookName = 'Test2'
$Variable = Get-Variable DebugPreference
$Params = @{"string1"="ValueForPosition1";"string2"="ValueForPosition2";"string3"=$Variable}
Start-AutomationRunbook -Name $RunbookName -Parameters $Params
After I ran this, I see that the runbook has started, but when I open it I see CliXml in the String3 input.
This is the $Variable
object I passed in the String3 parameter.
Somewhere within Azure Automation it is converted to CliXml.
And when I open the input it gets even worse…
It looks like it’s JSON & XML. Fortunately, only the wrapper around it has become JSON and the property CliXml contains the input (unfortunately still CliXml).
{"CliXml":"<Objs Version=\"1.1.0.1\" xmlns=\"http://schemas.microsoft.com/powershell/2004/04\">\r\n <Obj RefId=\"0\">\r\n <TN RefId=\"0\">\r\n <T>System.Management.Automation.PSVariable</T>\r\n <T>System.Object</T>\r\n </TN>\r\n <ToString>System.Management.Automation.PSVariable</ToString>\r\n <Props>\r\n <S N=\"Name\">DebugPreference</S>\r\n <S N=\"Description\">Dictates the action taken when a Debug message is delivered</S>\r\n <S N=\"Value\">SilentlyContinue</S>\r\n <S N=\"Visibility\">Public</S>\r\n <Nil N=\"Module\" />\r\n <S N=\"ModuleName\"></S>\r\n <S N=\"Options\">None</S>\r\n <Obj N=\"Attributes\" RefId=\"1\">\r\n <TN RefId=\"1\">\r\n <T>System.Management.Automation.PSVariableAttributeCollection</T>\r\n <T>System.Collections.ObjectModel.Collection`1[[System.Attribute, System.Private.CoreLib, Version=5.0.0.0, Culture=neutral, PublicKeyToken=7cec85d7bea7798e]]</T>\r\n <T>System.Object</T>\r\n </TN>\r\n <LST>\r\n <S>System.Management.Automation.ArgumentTypeConverterAttribute</S>\r\n </LST>\r\n </Obj>\r\n </Props>\r\n </Obj>\r\n</Objs>"}
Let’s take a look at the runbook that is started
The runbook’s content and output:
param (
$string1,
$string2,
$string3
)
Write-Output $String1
Write-Output $string2
Write-Output $String3
ValueForPosition1
ValueForPosition2
CliXml
------
<Objs Version="1.1.0.1" xmlns="http://schemas.microsoft.com/powershell/2004/04">...
Besides the fact that we can convert the XML to a PSObject ourselves, we can do little else here.
In addition, converting Xml to a PSObject is difficult. I wouldn’t burn my fingers on it (unless the XML is always the same)
So, what’s causing the CliXml?
But then why is this happening? At first I thought I had a semi answer, but unfortunately it is not correct because it also occurs in PS5.
I assumed that something went wrong while converting the parameters to an object because PS7 is built on dotnet core.
I’m guessing there’s still something wrong here, but unfortunately I can’t put my finger on it.
Parameters as JSON is a good substitute!
The maximum parameters for Runbooks is 50 parameters.
Maximum runbook parameters | 50 | If you reach the 50-parameter limit, you can pass a JSON or XML string to a parameter and parse it with the runbook. |
Now, of course, you’re almost never going to reach this, but I don’t like limitations.
The solution for this is 1 parameter that contains JSON which you then pars in your runbook to a PSObject.
Take a look at the example below:
$runbookName = 'Test2'
$Variable = Get-Variable DebugPreference
$JsonString = @{
String1 = 'String1'
String2 = 'String2'
String3 = $Variable
} | ConvertTo-Json -Compress
$Params = @{"Json"="$JsonString"}
Start-AutomationRunbook -Name $RunbookName -Parameters $Params
Instead of adding 3 parameter values I have 1 JsonString, which I converted to JSON with ConvertTo-Json
.
then I pass this in the -Json
parameter, and then it’s up to the runbook you call to parse the JSON to a PSObject.
See below the runbook that is called and the result:
param (
$Json
)
$Content = ($Json) | ConvertFrom-Json
Write-Output $Content
String1 String3
------- -------
String1 @{Name=DebugPreference; Description=Dictates the action taken when a D…