PortMan
PortMan

Reputation: 4523

How to powershell to give warning or error when using an undefined variable?

In a powershell script, if I try to use an undefined variable, it continues on its way, not indicating by any warning or error that I did so.

For example, the following script

echo "a"
echo $nonexistent_variable
echo "c"

gives the output

a
c

Is there any way to get powerShell to let me know that the variable I'm trying to use is undefined?

Upvotes: 15

Views: 3468

Answers (4)

mklement0
mklement0

Reputation: 437197

Using Set-StrictMode -Version 1 or higher makes PowerShell report a by default statement-terminating error whenever a nonexistent variable is referenced at runtime.

Note that this means that execution continues by default, unless $ErrorActionPreference = 'Stop' is in effect or - for code inside an advanced function or script - if -ErrorAction Stop was passed to it, in which case any error results in a script-terminating (runspace-terminating) error.

Note:

  • PowerShell's dynamic scoping makes it impossible to detect references to nonexistent variables at parse time; thus, errors only surface at runtime.

  • -Version 2 and above include additional strictness checks, whose ramifications must be considered; -Version Latest is best avoided in scripts, given that in case additional strictness checks are added in the future, existing code may then break.

  • Caveat:

    • The specified script mode affects the calling scope and its descendent scopes, which requires careful management of when the desired mode is in effect, possibly selectively reverting to no strict mode with Set-StrictMode -Off

    • Specifically, third-party PowerShell code that is invoked while a strict mode is in effect can break if it wasn't designed with that mode in mind. De facto, much existing code relies on no script mode being in effect (without explicitly turning it off) and instead relying on references to nonexistent variables to default to $null.

Upvotes: 0

Pxtl
Pxtl

Reputation: 964

While PowerShell does have Set-PSDebug and Set-StrictMode, fundamentally it is a bad language and is not parsing scripts properly before executing them. It will gladly ignore code that is invalid that it has not run. There is no way to validate Powershell code without executing it.

Set-PSDebug -strict
Set-StrictMode -version latest
$ErrorActionPreference = 'Stop'

if($false)
{
  Write-Output $fnord #undeclared variable
}

#powershell should halt because of an error and not get here.
write-output "this language is clownshoes"

yields

this language is clownshoes

Contrast this to parse errors, which behave reasonably:

Set-PSDebug -strict
Set-StrictMode -version latest
$ErrorActionPreference = 'Stop'

if($false)
{
  () #parseerror
}

#powershell should halt because of an error and not get here.
write-output "this text will not show"

yields

At line:9 char:4
+   () #parseerror
+    ~
An expression was expected after '('.
    + CategoryInfo          : ParserError: (:) [], ParentContainsErrorRecordException
    + FullyQualifiedErrorId : ExpectedExpression

So, in short, while you can have powershell error out when it attempts to read from an undeclared variable, there is no way to have powershell properly check your script for undeclared variables at parse-time.

Upvotes: 1

Harald F.
Harald F.

Reputation: 4743

You could consider using the strict mode:

Set-strictmode -version latest

This will give you warning and errors if you do common mistakes (such as using an undeclared variable etc).

You could also use PSDebug -Strict

Set-PSDebug -Strict

Upvotes: 16

Frode F.
Frode F.

Reputation: 54871

Use Set-PSDebug's -Strict switch:

-Strict

Specifies that the interpreter should throw an exception if a variable is referenced before a value is assigned to the variable

#I belong in your PowerShell (ISE)-profile
Set-PSDebug -Strict

Upvotes: 2

Related Questions