First rule of PowerShell scoping rules…

powershell scoping soap

… never talk about PowerShell scoping rules.

Judging from the posts, emails and questions we get about variable scope in PowerShell Studio forms, PowerShell scoping rules are shrouded in mystery. When you read about_scopes you get a lot of information. When you come from any other scripting language, for example VBScript, you are used to two scopes; global and local. The default scope of a variable in VBScript depends on its first use or its declaration. So if you want a variable to have a specific scope you just declare it with a DIM statement.

image

This code sample illustrates the simple scoping rules in VBScript. A variable is global or local and yes, a local variable can shadow a global one with the same name.

The output is very much what you expect:

image

 

Now let’s do that in PowerShell:

image

And the result is:

image

The keen observer will immediately notice that $globalvariable never produces any output. That is because a variable in PowerShell is not global unless you specifically says so by using $global:globalvariable. Always. At every use. So what is the scope of $globalvariable in our example? It’s ‘local’, local to the global scope to be precise. Unless specified otherwise nothing is ever global.

So how do you set a variable from a child context?

1. You can use a return value of a function

image

2. You can pass  the variable as a parameter reference

image

Note that you cannot just assign a value to $globalvariable, that would just create a local variable of that name shadowing the parameter. You are passing a reference object, so you have to use the value property.

3. Use $global: or $script: to modify the scope of the variable.

If you are five levels removed from the definition or in a completely different context, for example in the event handler for a button in a Windows form, this might be the simplest solution.

image

 

One last final remark and we will not talk about this anymore. Read the about article on scope. Try the examples. You will need it.