Windows PowerShell supports the use of three types of variables: PowerShell built-in variables, Windows environment variables, and user-defined variables. Learn how to access and use the prefilled built-in and prefilled environment variables. Also learn how to create and fill your own variables.
Variables are virtual suitcases that you can use to store and transport data in your Power- Shell code. Sometimes, the suitcases come prepacked. For instance, PowerShell’s built-in variables and Windows environment variables come with data already assigned to them. Other times, you need to pack the suitcases yourself. Although these userdefined variables take a bit more work to use, they contain exactly what you need. But before you can start using built-in, environment, and user-defined variables, you need to understand the basics.
PowerShell supports many built-in variables that provide such information as the PowerShell home folder ($PSHOME) and current working folder ($PWD). To retrieve a list of not only the built-in but also the user-defined variables available in the current session, you can run the statement
dir variable: | sort nameThis statement starts by using the dir alias to reference the Get-ChildItem cmdlet, which takes variable: as its argument. This argument is referring to the Variable drive, one of several drives supported by PowerShell. As you might have guessed, this drive provides access to built-in and user-defined PowerShell variables and their values.
After the Get-ChildItem cmdlet retrieves the variables and their values, they’re piped to the Sort-Object cmdlet (represented by the sort alias), which sorts the output by the variables’ names. If you don’t sort by name, the variables will be displayed in the order they’re retrieved.
Figure 1 shows part of a sorted variable list. Such a list can prove invaluable as long as you’re aware of an important caveat: When you reference built-in and user-defined variables in your PowerShell code, you typically need to precede the variable name with a dollar sign ($). Unfortunately, this list doesn’t include the dollar signs in the names. The dollar sign makes it easy to distinguish variables from other code elements. For example, the dollar sign lets you easily distinguish between the pwd alias and the $PWD built-in variable. There are a few cases in which you don’t precede the variable name with a dollar sign, which I’ll discuss later.
If you want to retrieve the value of just one built-in variable, you can simply enter the variable’s name. For example, if you run
you’ll receive the path to the PowerShell home folder.
As with any variable in PowerShell, you can use built-in variables in statements. For example, the following statement uses the $PSHOME variable to retrieve a list of the .dll files in the PowerShell home folder:
dir $pshome -filter *.dll
PowerShell supports two types of built-in variables: preference (e.g., $MaximumErrorCount) and automatic (e.g., $PSHOME).
You can change the values of preference variables but not automatic variables. If you try to modify an automatic variable’s value, you’ll receive an error. For a list of preference variables, see the about_preference_ variables Help file. (If this file isn’t available on your system, you can view it at technet.microsoft.com/en-us/library/ bb978529.aspx.) For a list of automatic variables, see the about_automatic_variable Help file. You can find additional information about built-in variables by viewing the about_shell_variable Help file.
To change the value of a preference variable, you simply use the assignment (=) operator to assign a new value. Take, for example, the preference variable of $MaximumErrorCount, which specifies how many errors to save in the error history log for the current session. If you want to change this variable’s value from the default of 256 to 260, you’d run
$maximumerrorcount = 260The new value is used until you reassign a value or end your session.
In PowerShell, you use the Env drive to access Windows environment variables. For example, the following statement uses this drive to retrieve the Windows environment variables and their values, then uses the Sort-Object cmdlet to sort the output by the variables’ names:
dir env: | sort name
Like the built-in and user-defined variable list, the environment variable list doesn’t show the prefix you need to include when you reference environment variables in PowerShell code. However, unlike builtin and user-defined variables, which you preface with $, you need to preface an environment variable’s name with $env: when you reference it. For example, the following statement retrieves the windir environment variable’s value, which is the path to the Windows home folder:
$env:windirTo retrieve a list of the .dll files in the Windows home folder, you’d run
dir $env:windir -filter *.dllYou can change the values of environment variables. For example, suppose you want to change the HOMEPATH environment variable’s value from \Documents and Settings\administrator to \Documents and Settings\administrator\home. You can use the + operator discussed in Lesson 3 to append the string \home to the HOMEPATH environment variable’s value:
$env:homepath + "\home"
Continue on Page 2
User-Defined Variables U
nlike some scripting languages, Power- Shell doesn’t require you to explicitly declare a variable before you use it. You simply assign it a value. For example, the following statement assigns the string one two to the $var1 variable:
$var1 = "one two"
When you define a variable in this way, you’re actually calling the New-Variable cmdlet and providing two arguments to it: the variable’s name and value. For example, the following statement achieves the same results as the preceding statement:
New-Variable var1 "one two"In this statement, note that the variable’s name isn’t preceded with a dollar sign. When a variable’s name is an argument to the New-Variable cmdlet or to the Set-Variable, Clear-Variable, or Remove-Variable cmdlet (all of which I’ll cover shortly), you don’t include the dollar sign.
One advantage of using the New-Variable cmdlet to create a variable is that you can use other cmdlet parameters. For example, you can use the -option parameter to define the variable as read-only: New-Variable var1 "one two" `
-option ReadOnlyIn this case, I’ve specified ReadOnly as an argument to the -option parameter. You can also specify other values as arguments to this parameter. If you specify more than one argument, you need to use commas to separate them. For a complete list of acceptable arguments, see the New-Variable Help file.
When you set a variable as read-only, you can’t change the variable’s value unless you force the change. However, before I get into the details of how to do that, let’s first take a look at how to update a variable. Typically, the simplest way to change a variable’s value is to use the = operator to assign the new value:
$var1 = "three"You can achieve the same result by using the Set- Variable cmdlet:
Set-Variable var1 "three"Both these statements will reset the value, but only if the variable is not defined as read-only. If it is read-only, you’ll receive an error and you won’t be able to update the value. The way to work around this issue is to use the -force parameter:
Set-Variable var1 “three” -forceNow the variable will be assigned the new value. As you saw with the New-Variable cmdlet, the advantage to using the Set-Variable cmdlet is that you can use additional parameters.
Now let’s take a look at how to clear a variable’s value. One approach you can take is to set the value to null by using the $null built-in variable:
$var1 = $nullOr, you can use the Clear- Variable cmdlet to achieve the same result:
Clear-Variable var1However, as before, if the variable is defined as readonly, both these commands will fail. Once again, the workaround is to add the -force parameter:
Remove-Variable var1Not surprisingly, this command will return an error if the variable is read-only. However, the Remove-Variable cmdlet also supports the -force parameter:
Remove-Variable var1 -forceIn most cases, you’ll probably find that you can simply use the = operator to create, change, and clear variables. However, if you want to use the New-Variable, Set-Variable, Clear-Variable, and Remove-Variable cmdlets, you can find more information about them in their respective Help files.
Continue on Page 3
Different Data Types
Now let’s take a look at some other considerations when using user-defined variables. But first, create $var1 again with the statement
$var1 = "one two"
because you just used the Remove-Variable cmdlet to delete it. As with built-in variable values, user-defined variable values can be retrieved by entering the variable’s name:
$var1Because you assigned a string value to $var1, PowerShell stores the value as a string object. To verify the object type, you can use the GetType() method:
$var1.gettype()Figure 2 shows the results of all three of these statements.
You’re not limited to string values when you create a variable. You can just as easily assign an integer:
$var1 = 123; $var1.gettype()PowerShell automatically stores the value as the correct type, which is Int32, as Figure 3 shows. Notice that this code includes multiple statements. As I discussed in Lesson 2, you can use a semicolon to manually terminate a statement. So, provided you use semicolons, you can put multiple statements on one line. In this case, I’ve included two statements: the first assigns the numeric value, and the second retrieves its type.
Also note that this code assigns a value to the same variable used in the previous set of examples. I did this to demonstrate that the process of creating and updating a variable is the same.
Besides strings and integers, you can assign other types of values, such as
$var1 = 12.34; $var1.gettype()
$var1 = get-date; $var1.gettype()The first line stores the value as type Double, whereas the second line stores the value as type Date- Time, as Figure 3 shows.
To append text to an existing string value in a user-defined variable, you can follow the same approach I outlined for appending text to an existing string value in an environment variable. For example, the following code assigns a string value to $var1, then appends the string four to it:
$var1 = "one two three"; $var1
$var1 = $var1 + " four"; $var1Figure 4 shows the results.
Now let’s try a similar operation with numerical values:
$var1 = 123; $var1
$var1 = $var1 + 4; $var1In this case, PowerShell doesn’t append the number 4, but instead adds 4 to the total amount, as shown in Figure 4. You can, however, define the number as a string by enclosing it in quotes:
$var1 = "123"; $var1
$var1 = $var1 + 4; $var1The number 4 is now appended to the original value. In fact, you can take this approach with any string:
$var1 = "one two three"; $var1
$var1 = $var1 + 4; $var1In this case, the results shown in Figure 4 might seem odd, but PowerShell has done exactly what you’ve told it to do.
Although you can append text or a number to a string value, you can’t append text to a numeric value. For example, if you attempt to append the string four to the number 123
$var1 = 123; $var1
$var1 = $var1 + "four"; $var1you’ll receive an error, as seen in Figure 4. You can append values to an existing value only when the types are compatible. The important point to remember is that PowerShell tries to do the right thing by letting you assign any type of data to a variable as long as it can be converted to the correct type.
Continue on Page 4
Referencing Variables in Strings
In PowerShell, you can use variables in string values. However, the way in which variables are treated at runtime depends on whether you use single or double quotes. When you use single quotes, PowerShell outputs the variable’s name as entered. When you use double quotes, PowerShell outputs the variable’s value.
For example, let’s assign the value eventlog to a string variable named $svc:
$svc = “eventlog”You can now use that variable in your strings. You just type the variable’s name as you would any other word:
Write-Output "The service is $svc."When PowerShell sees the dollar sign, it interprets the word as a variable because the string is enclosed in double quotes. PowerShell then inserts the variable’s value in place of its name, giving the result: The service is eventlog.
Now let’s use single quotes:
Write-Output 'The service is $svc.'This time, PowerShell treats the variable as a literal value and outputs the variable’s name, giving the result: The service is $svc.
If you want to include both the variable’s name and value in a string, you can use double quotes (but not single quotes) and escape the variable you want to keep as a literal value with a backtick (`):
"The value of `$svc is $svc."
If you try to use single quotes
'The value of `$svc is $svc.'
Using a Variable Alone as an Argument
In the preceding examples, you saw how to include a variable in a string value that was passed as an argument to the Write- Output cmdlet. However, in some cases, you might want to use a variable as a cmdlet argument without it being part of a string. In that case, you can simply use the variable as the argument. For example, the following command uses the $svc variable as an argument for the name of the service: Get-Service $svc If you were to enclose the argument in double quotes, as in
Get-Service "$svc"you would receive the same result because, as you saw earlier, PowerShell retrieves the variable’s value when it’s enclosed in double quotes. Also as you saw earlier, if the variable appears in single quotes, PowerShell will interpret the variable name literally. As a result, the statement
Get-Service '$svc'will fail because PowerShell will interpret the service name as '$svc'.
Variables play a vital role in effective scripting, whether they’re built-in, environment, or user-defined. You’ll find them a useful tool at the command line and in scripts. Be sure to review the PowerShell Help files for more information on variables, and practice creating and using them. Use the Get-Member cmdlet to retrieve methods and properties and try them out. As you move into more complex code, you’ll find that you’ll be using variables—as well as their methods and properties—in a wide range of scripting solutions.