Skip to content

Instantly share code, notes, and snippets.

@FriedrichWeinmann
Created May 25, 2021 08:48
Show Gist options
  • Star 1 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save FriedrichWeinmann/12e4bda4e52c7d8d4c78903800346fdf to your computer and use it in GitHub Desktop.
Save FriedrichWeinmann/12e4bda4e52c7d8d4c78903800346fdf to your computer and use it in GitHub Desktop.
Get userinput and validate it
function Get-UserInput {
<#
.SYNOPSIS
Asks for user input, then validates response.
.DESCRIPTION
Asks for user input, then validates response.
.PARAMETER Prompt
The message to show to the user as input prompt.
.PARAMETER ErrorMessage
A customized error message to show.
Used with ValidatePattern and ValidateScript.
Uses the format operator - use "{0}" inside the string (without quotes) to reference the user input.
.PARAMETER ValidatePattern
A regex pattern the user input must match.
.PARAMETER ValidateSet
A list of legal values the user may provide.
.PARAMETER ValidateScript
A scriptblock that must return $true in order to validate user input.
Within the scriptblock, $args[0] is the user input.
.PARAMETER Terminate
Whether the input prompt should terminate with a terminating exception if the user provides an invalid answer.
.EXAMPLE
PS C:\> Get-UserInput -Prompt "User: " -ValidatePattern '^\S+$' -ErrorMessage "Input may not contain a whitespace. Value provided: {0}"
Asks for user input, ensuring no whitespace was offered.
#>
[CmdletBinding()]
param (
[string]
$Prompt = " ",
[string]
$ErrorMessage,
[string]
$ValidatePattern,
[string[]]
$ValidateSet,
[ScriptBlock]
$ValidateScript,
[switch]
$Terminate
)
while ($true) {
$answer = Read-Host -Prompt $Prompt
#region Validate Pattern
if ($ValidatePattern -and $answer -notmatch $ValidatePattern) {
if ($ErrorMessage) {
Write-Warning ($ErrorMessage -f $answer)
if ($Terminate) { throw ($ErrorMessage -f $answer) }
}
else {
Write-Warning "Invalid input: $answer does not match $ValidatePattern"
if ($Terminate) { throw "Invalid input: $answer does not match $ValidatePattern" }
}
continue
}
#endregion Validate Pattern
#region Validate Set
if ($ValidateSet -and $answer -notin $ValidateSet) {
Write-Warning "Invalid input: $answer is not one of $($ValidateSet -join ",")"
if ($Terminate) { throw "Invalid input: $answer is not one of $($ValidateSet -join ",")" }
continue
}
#endregion Validate Set
#region Validate Script
try { $testResult = & $ValidateScript $answer }
catch {
Write-Warning "Error testing answer: $_"
if ($Terminate) { throw }
continue
}
if (-not $testResult) {
$message = "Error validating $answer - test script did not return true: $ValidateScript"
if ($ErrorMessage) { $message = $ErrorMessage -f $answer }
Write-Warning $message
if ($Terminate) { throw $message }
continue
}
#endregion Validate Script
return $answer
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment