• Aucun résultat trouvé

Filtering Objects Out of the Pipeline

Dans le document Copyright Copyright (Page 129-132)

---a--- 15.08.2007 08:44 307 history.csv -a--- 15.08.2007 09:35 8160 test.csv

In this example, the result of Dir is directly sorted by Sort-Object according to two properties, first by extension and then by name.

The result is that the groups are sorted alphabetically by name.

Filtering Pipeline Results

Pipeline filters allow only certain objects or object properties through the pipeline. That's practical, because often you will want all results that a command returns. Where-Object permits only those objects to pass through that meet certain criterion. Select-Object also allows only certain object properties to travel through the pipeline. You can use ForEach-Object to process all objects in the pipeline sequentially, enabling you to make your own filters. Finally, Get-Unique removes pipeline duplicates. Let's take a closer look at filters.

Filtering Objects Out of the Pipeline

If you're only interested in certain objects, assign Where-Object the task of closely examining all objects and allowing only those through that meet your criterion, which consists of object properties.

For example, if you don't want to view all services returned by Get-Service, but only currently running services, you'll first have to know which service object property reveals whether the service is running or not. You will need more detailed knowledge about the properties supported by an object.

You already know how to ferret out these properties. If you'll recall, Format-List neatly lists all of an object's properties when you use the asterisk character as an argument. You will only need an object example that you can examine with Format-List.

To do so, use the same command that you will want to use later in your pipeline, such as Get-Service and save its result to a variable. As commands return their results in arrays and store each object in it as array elements, you can take the first element you find out of the array and pass it to Format-List:

$result = Get-Service

$result[0] | Format-List *

Name : AeLookupSvc CanPauseAndContinue : False

CanShutdown : False

CanStop : True

Now, you can already see all of the object's properties and then its current values. It should be obvious right away that the information sought can be found in the Status property, so you only want to view the objects whose Status property contains the "running" value. You're now ready to use the pipeline filter:

Get-Service | Where-Object { $_.Status -eq "Running" } Status Name DisplayName

--- ----

---Running AeLookupSvc Applicationlookup

Running AgereModemAudio Agere Modem Call Progress Audio Running Appinfo Applicationinformation

Running AppMgmt Applicationmanagement Running Ati External Ev... Ati External Event Utility Running AudioEndpointBu... Windows-Audio-Endpoint-building Running Audiosrv Windows-Audio

Running BFE Basis Filter Engine

Running BITS Intelligent Background Transmiss...

(...)

In fact, it works just the way you want it to work so that now you can see only those services that are actually running. How does Where-Object function? The cmdlet expects you to type a PowerShell command in braces and evaluate the command for every pipeline object. The object that Where-Object was just examining can always be found in the variable $_. $_.Status returns the Status property content and needs only be compared to the value that you want to let through.

In reality, the instruction behind Where-Object works like a condition (see Chapter 7): if the

expression results in $true, the object will be let through. That's why you may formulate conditions as complex as you like, but you must only make sure that your instruction results in either $true or

$false.

The pipeline filter's principle may be applied to all object types and works in the same way everywhere. As an experienced administrator, you may be a little disappointed that the service objects returned by Get-Service contain relatively little information. If you want to list all services that would automatically start, but at the moment aren't running, you can leverage the built-in Windows Management Instrumentation (WMI) infrastructure as an information source to supply more data. You'll harvest much more information when you ask it about services:

$services = Get-WmiObject Win32_Service

$services[0] | Format-List *

Name : AeLookupSvc

__DERIVATION : {Win32_BaseService, CIM_Service, CIM_Logic alElement, CIM_ManagedSystemElement}

CreationClassName : Win32_Service

Description : Processes application compatibility cache

The information needed for your criteria are located in the Started and StartMode properties. And because the Where-Object pipeline filter is used very often, there exists a practical abbreviation for it: "?". Here is an example of what your pipeline filter could look like:

Get-WmiObject Win32_Service |

? {($_.Started -eq $false) -and ($_.StartMode -eq "Auto")} | Format-Table

0 WinDefend 0 Auto Stopped OK

If everything works properly, these lines shouldn't report any services at all because services in the

"auto" start-up mode are automatically started and, for this reason, should be running. If you're notified of services, you should verify whether these services are (no longer) running despite auto start. One cause could be that the service has completed its task and was then ended as scheduled.

Incidentally, because WMI objects are not on the internal PowerShell list, results are always displayed as lists. For this reason, at the end our above example, we set a table format using Format-Table, which is much clearer.

The internal WMI service will provide you with helpful information about your computer in response to almost any question. You'll find out exactly what it is in Chapter 18. If you use the -query parameter, you can pass SQL-type queries to this service so that the command will automatically return only the information sought and make pipeline filtering superfluous. You should always keep in mind when using any command that the pipeline filter is practical and easy to use, but not particularly economical. It limits results that are already available. It is better right at the beginning to ask only about the information needed, as it is not as easy to do for all commands as it is for Get-WmiObject:

Get-WmiObject -query "select * from win32_Service where ` Started=false and StartMode='Auto'" | Format-Table

ExitCode Name ProcessId StartMode State Status -- ---- --- --- --- 0 Automatic Li... 0 Auto Stopped OK 0 ehstart 0 Auto Stopped OK 0 LiveUpdate N... 0 Auto Stopped OK 0 WinDefend 0 Auto Stopped OK

Dans le document Copyright Copyright (Page 129-132)