Professional Documents
Culture Documents
The Power of The Shell: Learn Windows Powershell in A Month of Lunches
The Power of The Shell: Learn Windows Powershell in A Month of Lunches
PowerShell is a powerful tool for automating Windows administration. In this article from
Learn Windows PowerShell in a Month of Lunches, author Don Jones introduces
PowerShell and shows you how to handle a few typical admin tasks.
For source code, sample chapters, the Online Author Forum, and other resources, go to
http://www.manning.com/jones/
2
invest that hour, creating users in the future takes a few seconds. The problem with VBScript is that it wasn’t a
wholehearted effort on Microsoft’s part. Microsoft had to remember to make things VBScript-accessible and, when
they forgot (or didn’t have time), you were stuck. Want to change the IP address of a network adapter using
VBScript? Okay, you can. Want to check its link speed? You can’t because nobody remembered to hook that up in a
way that VBScript could get to it. Sorry! Jeffrey Snover, the architect of Windows PowerShell, calls this the last
mile: “You can do a lot with VBScript (and other, similar technologies), but it tends to always let you down at some
point, never getting you through that last mile to the finish line.”
Windows PowerShell is an express attempt on Microsoft’s part to do a better job and to get you through the last
mile.
For source code, sample chapters, the Online Author Forum, and other resources, go to
http://www.manning.com/jones/
3
Don’t get me wrong: you can get as complex as you need to with PowerShell. In fact, it supports the same kind
of usage patterns as VBScript and other scripting or programming languages. PowerShell gives you access to the
full underlying power of the .NET Framework. I’ve seen PowerShell scripts that were practically indistinguishable
from a C# program written in Visual Studio. PowerShell supports these different usage patterns because it’s
intended to be useful to a wide range of audiences. The point is that, just because it supports that level of
complexity, it doesn’t mean you have to use it at that level and it doesn’t mean you can’t be extremely effective
with less complexity.
Here’s an analogy: you probably drive a car. If you’re like me, changing the oil is the most complex mechanical
task you’ll ever do with your car. I’m just not a car geek, and I can’t rebuild the engine. I also can’t do those cool
high-speed J-turns that you see in the movies, and you’ll never see me driving a car on a closed course in a car
commercial. The fact that I’m not a professional stunt driver doesn’t stop me from being an extremely effective
driver—just at a less complex level. Someday, I might decide to take up stunt driving for a hobby. (I’m sure my
insurance company would be thrilled.) At that point, I’ll need to learn a bit more about how my car works, master
some new skills, and so on. That option is always there for me to grow into but, for now, I’m very happy with what
I can accomplish as just a regular driver.
For the purpose of this green paper, we’re going to stick with being just a regular PowerShell driver, operating
the shell at a lower level of complexity. Believe it or not, we’re actually the primary target audience for PowerShell
so you’ll find that there’s an awful lot of incredible stuff you can do. You just need to master the ability to run
commands within the shell and you’re on your way.
Opening PowerShell
This is a good time to get PowerShell up and running, if you haven’t done so already. You can use either the ISE or
the regular console host. You’ll find the icons for PowerShell and the ISE located on the Start menu, under
Accessories.
It’s very important that you run PowerShell as an administrator. On Windows Vista and later versions of
Windows, User Account Control (UAC) is enabled by default and prevents you from running programs as
administrator without taking a special step: right-click the program icon in the Start menu and select “Run as
Administrator” from the context menu. It’s very important that you do that every time you open the application.
You can also right-click the icon, select Properties, and modify the program’s properties to always run as
administrator. I find that to be more convenient because, from then on, I can just click the icon in the Start menu
to open the shell.
If you choose to use the ISE, you’ll find yourself looking at three panes within the window, as shown in figure 1.
The only two of these you care about for now are the command input pane and the output pane—you can ignore
the script editor pane. Consider arranging the panes so that only those two are showing—you’ll find buttons on the
right-most side of the toolbar that let you reconfigure the panes, and the panes can be resized by dragging the
separator in between them. Experiment with the pane arrangement until you’re happy with it.
For source code, sample chapters, the Online Author Forum, and other resources, go to
http://www.manning.com/jones/
4
Figure 1 The ISE defaults to a three-pane layout including command input, output, and script editing.
Change directories Cd
For source code, sample chapters, the Online Author Forum, and other resources, go to
http://www.manning.com/jones/
5
If you have some UNIX or Linux shell experience, you may have come up with some alternatives, such as Ls
for Dir, Cp for Copy, Rm instead of Del, or Cat rather than Type. Those are fine solutions, and you’ll find that
they all work within PowerShell, too.
At least, they work in most cases. If you tried using extra parameters with some of these, you realized that
these aren’t quite the same commands that you’re used to. For example, if you tried to run Dir /s to get a listing
of files and folders, including subdirectories, then you probably got an error message. That’s okay; it turns out that
this isn’t exactly the same Dir command you know and love, but it has the same capabilities. We’ll cover that in a
couple of sections.
Have you ever piped a long directory listing to more, in order to get a paged result? That same trick still works:
Dir | More.
A lot of administrators use the angle bracket to perform redirection. For example, dir > file.txt will
redirect the output of the Dir command into the text file File.txt. You can use the same technique in PowerShell.
You can even do the double-angle trick, where the content will be appended to the specified file: Dir >>
file.txt.
That’s really the gist of our discourse: you can run commands, and many of the same commands that you’ve
used in Cmd.exe exist, although they may work a bit differently.
Accuracy counts
PowerShell is incredibly picky about how you type commands. Command names never contain spaces; it’s always
Dir and never Di r. You must have a space after the command name, so that PowerShell knows that the
command name is done, and that whatever comes next is a parameter or value. Technically, Dir.. is incorrect
because it doesn’t include a space, and Dir .. is correct. In reality, PowerShell v2 catches the Dir.. error and
will do the right thing (move up one level in the directory hierarchy) because that’s such a commonly-typed
command, but that’s the only exception that PowerShell will catch that way for you.
Dir >> file.txt will redirect a directory to a file; Dir>>file.txt will generate an error because the shell
will think you’ve typed a single command name, not two commands connected by angle brackets. I can’t stress
enough how important it is to become a neat, careful typist when you’re using PowerShell.
For source code, sample chapters, the Online Author Forum, and other resources, go to
http://www.manning.com/jones/
6
Figure 2 PSDrive providers adapt different forms of storage to look like disk drives within PowerShell.
There are a few fun facts about PSDrives that you should keep in mind:
The shell always starts with the exact same PSDrives mapped. You can run the command Get-PSDrive to
see them. You’ll see one for the HKEY_CURRENT_USER (HKCU) and HKEY_LOCAL_MACHINE (HKLM) registry
hives, one for each local disk, one for environment variables, and one each for PowerShell’s function,
variable, and alias storage.
You can map new drives using the New-PSDrive command. Keep in mind that these are PowerShell Drives,
so you won’t see them in Explorer. They only exist within the shell, and whatever you map will un-map
automatically when you close the shell. You’ll learn how to overcome that shortcoming near the end of the
book.
Unlike the old MS-DOS-style drive names that were limited to a single letter, PSDrive names can have
longer names such as HKCU: and HKLM:. So, when you map drives, take the opportunity to make their
names more meaningful, like DEMO: or USER: or FILES: rather than X:, Y:, and Z:.
If you decide to map a new drive using New-PSDrive, you’ll have to specify a name for the drive (and, in
that instance, the name will not include the colon—it’ll just be DEMO or USER or FILES or whatever), the
PSDrive Provider that will handle the mapping (such as FileSystem), and the source for the mapping (which
might be a UNC). For example:
For source code, sample chapters, the Online Author Forum, and other resources, go to
http://www.manning.com/jones/
7
“If you already know how to do something, keep doing it that way. We’ll try to provide you with better and more
complete tools going forward, but what you already know will still work.” The reason there’s no Map-Drive
command within PowerShell is that Net Use already does a good job—so why not keep using it?
There are certainly instances where Microsoft has provided better tools than some of the existing, older ones.
For example, the native Test-Connection cmdlet provides more options and more flexible output than the old,
external Ping command. But, if you know how to use Ping, and it’s solving whatever need you have, then go
right on using it. It will work fine from within PowerShell.
Having said that, I do have to deliver a harsh truth: not every external command will work flawlessly from
PowerShell, at least not without a little tweaking on your part. That’s because PowerShell’s parser—the bit of the
shell that reads what you’ve typed and tries to figure out what you want the shell to do—doesn’t always guess
correctly. Sometimes, you’ll type an external command and PowerShell will really mess up, start spitting out
errors, and just generally not work.
For example, things can get really tricky when an external command has a lot of parameters; that’s where I see
PowerShell break the most. We’re not going to dive into the details of why it works, but here’s a way to make
almost any command and its parameters work properly:
$exe = "C:\Vmware\vcbMounter.exe"
$host = "server"
$user = "joe"
$password = "password"
$machine = "somepc"
$location = "somelocation"
$backupType = "incremental"
-r for a location
What I’ve done is put all the various elements—the executable path and name, as well as all of the parameter
values—into placeholders, which start with the $ character. That forces PowerShell to treat those values as single
units rather than trying to parse them to see if any of them contain commands or special characters or anything.
Last, I used the invocation operator again, passing it the executable name, all of the parameters, and the
parameters’ values. That pattern will work for almost any command-line utility that’s being grumpy about running
within PowerShell.
For source code, sample chapters, the Online Author Forum, and other resources, go to
http://www.manning.com/jones/
8
Move-Item (Move)
Rename-Item (Ren)
Remove-Item (Del, Rm, RmDir)
Copy-Item (Copy, Cp)
Get-Content (Type, Cat)
New-Item (MkDir)
Those cmdlet names are obviously longer, making them harder to type, and so Microsoft added those aliases as
a way of saving your fingers some wear and tear. Also, by selecting aliases that match the old Cmd.exe-style
names (as well as Linux and Unix names), the company gave you a way of jumping right into PowerShell and
performing basic tasks without having to spend too much up-front time learning new command names.
That explains why Dir /s doesn’t work: you’re not running the Dir command from your past, and Get-
ChildItem doesn’t support a /s parameter. Get-ChildItem can do the same thing as Dir /s, but you’ll have
to learn a new parameter name, which is –recurse. In fact, this is probably a good time to point out some
common characteristics about PowerShell cmdlets:
All PowerShell cmdlet names have a very strict naming convention. Cmdlet names start with a verb, like Get
or Copy, followed by a hyphen, and then a singular noun, such as Item or Content. The list of allowed verbs
is actually quite small—just a few dozen or so—and the number of verbs you use on a daily basis will
probably number less than a dozen. The idea is that you’ll gradually become used to those verb names and
be able to guess new cmdlet names.
Cmdlet names tend to be a little generic. Why Move-Item and not Move-File? Keep in mind that the cmdlet
has to operate in the registry, environment variables, and other storage systems as well as the file system.
Rather than having a separate Move-File and Move-RegistryKey, PowerShell just has a single, generic Move-
Item.
Parameter names (-recurse was one example) always start with a dash and, for parameters that accept a
value (like the –name DEMO example I showed you earlier), there’s always a space separating the
parameter name and the value. Dash, name, space, value.
Parameter names are used consistently throughout the shell. If one cmdlet has a –computerName
parameter, which is used for specifying a computer name, then most cmdlets that need a computer name
will also have a –computerName parameter.
Both parameter and cmdlet names are intended to be clear and meaningful. When you look at a cmdlet
name like Get-Content, you should be pretty clear that it’s getting some kind of content from something.
A parameter name like –credential doesn’t leave much to the imagination, either; you should be pretty
certain what that parameter is going to do.
Because “clear” can sometimes mean “lengthy,” Microsoft gives you shortcuts for cmdlet names and for
parameter names just to save you some typing. Cmdlet names can be given shorter aliases, which we’ve
already discussed. Parameter names don’t need to be typed in their entirety. For example, if –recurse is
the only parameter of Get-ChildItem that starts with the letter “r,” then you only have to type –r and
PowerShell will know what you meant. If a cmdlet has both a –computerName and –credential
parameter, typing –comp will probably be enough for PowerShell to figure out that you mean the –
computerName parameter.
This is another good place for me to remind you to be a neat, careful typist. Get-ChildItem-recurse is
incorrect because there’s no space between the end of the cmdlet name and the dash that starts the parameter
name. Get-ChildItem -recurse is correct, with that space in between those two elements. It’s very, very
important that you focus on those little typing details, because getting them wrong will generate sometimes-
confusing errors that will do nothing but slow you down.
PowerShell is all about consistency. That’s not to say it’s 100 percent consistent, because it is after all the
product of many human beings, who do tend to make mistakes sometimes. But it’s pretty consistent most of the
time. GUIs offer features to help you figure out what you can do with them: right-click menus, menus, tool tips,
For source code, sample chapters, the Online Author Forum, and other resources, go to
http://www.manning.com/jones/
9
and so forth. Programmers refer to those features as discoverability features because they literally help you
discover the tool’s capabilities. A command-line interface (CLI) like PowerShell lacks those kinds of graphical
discoverability features, but consistency can provide a kind of discoverability on its own.
For example, let’s say I told you that the cmdlet verb Get was used for all cmdlets that retrieve or display
something (as with Get-Content). You already know that cmdlet nouns are singular, and never plural. Most tasks
can be accomplished with one of two verbs: Get or New (table 2).
Task Cmdlet
Get-Service
Display a list of services
Get-Process
Display a list of running processes
Get-EventLog
Display the contents of an event log
New-Service
Create a new service
Get-Mailbox
Retrieve Exchange mailboxes
New-Mailbox
Create a new Exchange mailbox
The last two aren’t native to PowerShell, and you won’t be able to try them unless you have the Exchange Server
2007 (or 2010) add-in loaded. The point right now is just guessing the right cmdlet name. If you were able to do
that, then you’re well on your way to mastering the shell. More importantly, don’t ever be afraid to guess a cmdlet
name, and don’t be afraid to be wrong.
Summary
It’s easy to surmise that PowerShell is some kind of .NET Framework-based scripting or programming language.
Hundreds of PowerShell users began by simply running commands. That’s the gist of the PowerShell foundation: no
scripting, no programming—just running commands and command-line utilities.
For source code, sample chapters, the Online Author Forum, and other resources, go to
http://www.manning.com/jones/
10
Here are some other Manning titles you might be interested in:
PowerShell in Practice
Richard Siddaway
For source code, sample chapters, the Online Author Forum, and other resources, go to
http://www.manning.com/jones/