PowerShell with a Purpose Blog

Pipeline Parameter Binding: ByValue

One of the most flexible and powerful techniques you can learn in Windows PowerShell is pipeline parameter binding. With it, you can perform a number of extremely complex tasks simply by stringing together the right commands - rather than having to write a complicated script. Let's start by looking at the first of two pipeline parameter binding techniques: ByValue.

Pull up the help file for Get-Service. Be sure to read the FULL help - that is, run "Help Get-Service -full" and page down to the -Name parameter. Notice that the parameter has an attribute called "Accepts pipeline input," and for the -Name parameter that attribute says "ByValue." It also says "ByPropertyName," but let's ignore that for now. Also notice the type of data that the -Name parameter accepts: . The can be ignored; the [] tells you that the parameter can accept one value, or many values.

The practical upshot of this is that if you pipe a string to the Get-Service cmdlet, PowerShell will attach that string to the -Name parameter. Why? Because you piped in a STRING, and because the -Name parameter binds that kind of value - that's what ByValue means. Notice that no other parameter accepting a String binds pipeline input ByValue? That's the deal: Only one parameter can attach itself ByValue to a given value type.

So you could do this:

"BITS" | Get-Service
That's not a huge timesaver, but you could also pipe in an array of strings. PowerShell treats any comma-separated list as an array, so this will work:

"TrustedInstaller","BITS","WinRM" | Get-Service

You could also start with any command that generates an array of strings. For example, suppose you have a text file that lists one service name per line. You could do this:

Get-Content services.txt | Get-Service

Any way you have of getting simple string values into the cmdlet will work: They will always bind to the -Name parameter. If you start reviewing the help file for cmdlets that you frequently use, you'll notice that a lot of them support binding ByValue (you have to read the -full help to see this fact). Who cares? Well, all of the above examples are easier to understand than:

Get-Content services.txt | ForEach-Object { Get-Service -Name $_ }

Which is what a lot of folks do when they're not aware of parameter binding. Or even worse:

$services = Get-Content services.txt
ForEach ($service in $services) {
 Get-Service -Name $service

Which is a very VBScript-like approach to the problem - and a heck of a lot more typing. Pipeline binding becomes even more useful when you use the ByPropertyName technique - and I'll cover that in a future article. Stay tuned.
Hide comments


  • Allowed HTML tags: <em> <strong> <blockquote> <br> <p>

Plain text

  • No HTML tags allowed.
  • Web page addresses and e-mail addresses turn into links automatically.
  • Lines and paragraphs break automatically.