
separately from templates in the ./scripts/ directory. test_windows_agent.py updated. Formatting in windows_agent.py fixed. Tracing and error capturing added to Set-LocalUserPassword. Function Set-LocalUserPassword removed as it is implemented by workflow means. Scripts now stored in one common folder. Scripts updated from murano-deployment. Templates updated to reflect new script names. Workflow template can reference multiple script files. These script files will be concatinated and encrypted with base64. Change-Id: Icb3532d2fb724bbb711c06086cb906bde22a380f Fixed flake8 reported issues. Change-Id: Icb3532d2fb724bbb711c06086cb906bde22a380f Fixed test failure after reformatting. Change-Id: Icb3532d2fb724bbb711c06086cb906bde22a380f Fixed issues with test. Revert back path selection for scripts folder. It is reasonable to have an ability to use own folder for custom workflows so script path is relative to template location. Change-Id: Icb3532d2fb724bbb711c06086cb906bde22a380f
281 lines
8.7 KiB
PowerShell
281 lines
8.7 KiB
PowerShell
function New-Option ([string]$Name, [switch]$Switch, [switch]$Boolean, [switch]$String, [switch]$List, $Constraints=$null) {
|
|
<#
|
|
.SYNOPSIS
|
|
Creates Option object
|
|
|
|
.DESCRIPTION
|
|
Option object is a virtual object represtnting typed command line option. These objects encapsulate escaping and
|
|
validation matters.
|
|
|
|
One and only one of the switches 'Switch', 'Boolean', 'String' or 'List' should be provided.
|
|
|
|
.PARAMETER Name
|
|
Option name as it appears in the command line.
|
|
|
|
.PARAMETER Switch
|
|
Use this switch to create valueless option (a switch).
|
|
|
|
.PARAMETER Boolean
|
|
Use this switch to create boolean option. Its value is always converted to "1" or "0"
|
|
|
|
.PARAMETER String
|
|
Use this switch to create string option. Its value will be properly quoted if necessary.
|
|
|
|
.PARAMETER List
|
|
Use this switch to create option with list value. Values will be put into command line using valid value delemiter (a comma)
|
|
|
|
.PARAMETER Constraints
|
|
When this parameter is specified, option values are limited to options from that list.
|
|
|
|
#>
|
|
|
|
$Option = New-Object -TypeName PSObject
|
|
|
|
# Fields
|
|
$Option | Add-Member NoteProperty Type -value $null
|
|
$Option | Add-Member NoteProperty Name -value $null
|
|
$Option | Add-Member NoteProperty AllowedValues -value $null
|
|
|
|
# Init
|
|
|
|
$Option | Add-Member ScriptMethod __init__ {
|
|
param([string]$Name, $Switch, $Boolean, $String, $List)
|
|
|
|
$this.Name = $Name
|
|
|
|
# With respect for our developers we do not check for double type selected
|
|
if ($Switch) {
|
|
AugmentOptionSwitch($this)
|
|
} elseif ($Boolean) {
|
|
AugmentOptionBoolean($this)
|
|
} elseif ($String) {
|
|
AugmentOptionString($this)
|
|
} elseif ($List) {
|
|
AugmentOptionList($this)
|
|
} else {
|
|
throw "Switch, Boolean, String or List option type must be provided for option '$Name'"
|
|
}
|
|
}
|
|
|
|
$Option | Add-Member ScriptMethod __post_init__ {
|
|
param($Constraints=$null)
|
|
if ($Constraints -ne $null) {
|
|
$this.AllowedValues = @()
|
|
$this.AllowedValues = $this.AllowedValues + $Constraints
|
|
} else {
|
|
$Constraints = $null
|
|
}
|
|
}
|
|
|
|
# Methods
|
|
|
|
$Option | Add-Member -Force ScriptMethod Validate {
|
|
if ($this.AllowedValues -ne $null) {
|
|
if (-not($this.AllowedValues -contains $this.Value)) {
|
|
$Cts = $this.AllowedValues -join ','
|
|
throw "Option '$($this.Name)' may have values ($Cts) but not '$($this.Value)'"
|
|
}
|
|
}
|
|
}
|
|
|
|
$Option | Add-Member -Force ScriptMethod ToString {
|
|
return "/$($this.Name)"
|
|
}
|
|
|
|
# invoke constructor
|
|
|
|
$Option.__init__($Name, $Switch, $Boolean, $String, $List)
|
|
$Option.__post_init__($Constraints)
|
|
|
|
return $Option
|
|
}
|
|
|
|
function AugmentOptionSwitch($Option) {
|
|
}
|
|
|
|
function AugmentOptionBoolean($Option) {
|
|
# Fields
|
|
$Option | Add-Member NoteProperty Value -value $false
|
|
|
|
# Methods
|
|
|
|
$Option | Add-Member -Force ScriptMethod ToString {
|
|
if ($this.Value) {
|
|
return "/$($this.Name)=1"
|
|
} else {
|
|
return "/$($this.Name)=0"
|
|
}
|
|
}
|
|
}
|
|
|
|
function AugmentOptionString($Option) {
|
|
# Fields
|
|
$Option | Add-Member NoteProperty Value -value ""
|
|
|
|
# Methods
|
|
|
|
$Option | Add-Member -Force ScriptMethod ToString {
|
|
$v = "$($this.Value)"
|
|
if ($v -match '.* .*') {
|
|
# TODO: Escape double quote characters if possible
|
|
return "/$($this.Name)=`"$v`""
|
|
} else {
|
|
return "/$($this.Name)=$v"
|
|
}
|
|
}
|
|
}
|
|
|
|
function AugmentOptionList($Option) {
|
|
# Fields
|
|
$Option | Add-Member NoteProperty Value -value @()
|
|
|
|
# Methods
|
|
|
|
$Option | Add-Member -Force ScriptMethod Validate {
|
|
if ($this.AllowedValues -ne $null) {
|
|
foreach ($V in $this.Value) {
|
|
if (-not($this.AllowedValues -contains $V)) {
|
|
$Cts = $this.AllowedValues -join ','
|
|
throw "Option '$($this.Name)' may have values ($Cts) but not '$V'"
|
|
}
|
|
}
|
|
}
|
|
}
|
|
|
|
$Option | Add-Member -Force ScriptMethod ToString {
|
|
return "/$($this.Name)=$($this.Value -join ',')"
|
|
}
|
|
}
|
|
|
|
function New-OptionParser() {
|
|
<#
|
|
.SYNOPSIS
|
|
Creates OptionParser object.
|
|
|
|
.DESCRIPTION
|
|
OptionParser object leverages Option objects capabilities and builds valid command line using specified options.
|
|
An application may also be invoked with OptionParser.
|
|
|
|
#>
|
|
|
|
$OptionParser = New-Object -TypeName PSObject
|
|
|
|
# Fields
|
|
$OptionParser | Add-Member NoteProperty Options -value @{}
|
|
$OptionParser | Add-Member NoteProperty Defaults -value @{}
|
|
$OptionParser | Add-Member NoteProperty RequiredOptions -value @()
|
|
|
|
# Methods
|
|
|
|
$OptionParser | Add-Member ScriptMethod AddOption {
|
|
<#
|
|
.SYNOPSIS
|
|
Adds supported option into OptionParser.
|
|
|
|
.DESCRIPTION
|
|
OptionParser does not allow using unrecognized options. Use this method to fill OptionParser with recognized options
|
|
|
|
.PARAMETER Option
|
|
Option object
|
|
|
|
.PARAMETER Required
|
|
Required option switch
|
|
|
|
.PARAMETER Default
|
|
Option default value
|
|
#>
|
|
param($Option, [bool]$Required=$false, $Default=$null)
|
|
$this.Options.Add($Option.Name, $Option)
|
|
if ($Required) {
|
|
$this.RequiredOptions = $this.RequiredOptions + $Option.Name
|
|
if ($Option | Get-Member "Value") {
|
|
if ($Default) {
|
|
$this.Defaults.Add($Option.Name, $Default)
|
|
}
|
|
} else {
|
|
$this.Defaults.Add($Option.Name, $null)
|
|
}
|
|
}
|
|
}
|
|
|
|
$OptionParser | Add-Member ScriptMethod Parse {
|
|
<#
|
|
.SYNOPSIS
|
|
Parses supplied options and returns command line parameters array.
|
|
|
|
.DESCRIPTION
|
|
This method verifies that only supported options are provided, all mandatory options are in place,
|
|
all option meet constraints if any. Unspecified options with default values are added to command line.
|
|
So, mandatory option with default value never causes exception.
|
|
|
|
.PARAMETER Options
|
|
A hash map of options to parse. Option names should be mapped to corresponding values.
|
|
#>
|
|
param([hashtable]$Options)
|
|
|
|
$CommandLine = @()
|
|
foreach ($RequiredOptionName in $this.RequiredOptions) {
|
|
if (-not $Options.ContainsKey($RequiredOptionName)) {
|
|
$Default = $this.Defaults.Get_Item($RequiredOptionName)
|
|
if ($this.Defaults.ContainsKey($RequiredOptionName)) {
|
|
$Options.Add($RequiredOptionName, $this.Defaults.Get_Item($RequiredOptionName))
|
|
} else {
|
|
throw "Required option '$RequiredOptionName' is missing"
|
|
}
|
|
}
|
|
}
|
|
|
|
foreach ($OptionName in $($Options.keys)) {
|
|
$Option = $this.Options.Get_Item($OptionName)
|
|
if ($Option -eq $null) {
|
|
throw "Option '$OptionName' is not allowed"
|
|
}
|
|
if ($Option | Get-Member "Value") {
|
|
$Option.Value = $Options.Get_Item($OptionName)
|
|
}
|
|
$Option.Validate()
|
|
$CommandLine = $CommandLine + $Option.ToString()
|
|
}
|
|
return $CommandLine
|
|
}
|
|
|
|
$OptionParser | Add-Member ScriptMethod ExecuteBinary {
|
|
param($Binary, [hashtable]$Options = @{}, $CommandLineSuffix = @())
|
|
<#
|
|
.SYNOPSIS
|
|
Executes binary with a command line constructed from provided options. An arbitrary suffix may be
|
|
appended to the command line.
|
|
|
|
.DESCRIPTION
|
|
This method uses OptionParser.Parse method to construct command line. If there a command line suffix
|
|
was supplied, it is appended to the end of command line. Normally command line suffix should contain
|
|
leading space character.
|
|
|
|
Method waits for executable process to complete and returns its exit code.
|
|
|
|
.PARAMETER Binary
|
|
Full or relative path to the executable to run.
|
|
|
|
.PARAMETER Options
|
|
A hash map of options to pass to the executable.
|
|
|
|
.PARAMETER CommandLineSuffix
|
|
Arbitrary command line suffix. Normally it shoud have leading space character.
|
|
#>
|
|
|
|
$Binary = Get-Item $Binary
|
|
$CommandLine = $this.Parse($Options)
|
|
if ($CommandLineSuffix) {
|
|
$CommandLine = $CommandLine + $CommandLineSuffix
|
|
}
|
|
|
|
Write-Log "Executing: $($Binary.FullName) $($CommandLine -join ' ')"
|
|
$process = [System.Diagnostics.Process]::Start($Binary, $CommandLine)
|
|
$process.WaitForExit()
|
|
$process.Refresh()
|
|
return $process.ExitCode
|
|
}
|
|
|
|
return $OptionParser
|
|
}
|