Powershell Pipeline

Hello,
I’m reading the “Learn Windows Powershell in a Month of Lunches” book, and i’m currently on chapter 9. There is a Lab that wants you to use parameter binding to retrieve a list of running process for every computer in AD.

This works:
Get-ADComputer -filter * | Select-Object @{n=‘computername’ ; e={$_.name}} | Get-Process

This does not work:

Get-ADComputer -filter * -Searchbase ‘ou=A, ou=B,dc=x,dc=y,dc=z’ |
Select-Object @{n=‘computername’ ; e={$_.name}} | Get-Process

I’ve looked and both return an ADComputer object and both have a Name property. Was wondering if someone could point out why it is not working.

Thanks

You said it doesn’t work, is there an error message when you run the command that describes the problem?

Unfortunately I can’t test Get-ADComputer on my computer but the only difference between 2 examples is parameter -Searchbase, which is likely the issue here.

What is the output (or error message) of the following command?

Get-ADComputer -filter * -Searchbase 'ou=A, ou=B,dc=x,dc=y,dc=z'

One thing which is obvious is the extra space in Searchbase string.

Try also this (space free version), does it work?

Get-ADComputer -filter * -Searchbase 'ou=A,ou=B,dc=x,dc=y,dc=z'

If this works, remove extra space from your second book example and try again.

With or without the spaces, it gives me a list of all computers in that OU, with one of the properties being Name.

I can’t think of any reason it wouldn’t work. I don’t necessarily need it now, but there are times where it would be useful to be able to pull information from a certain OU, and not every computer in the domain.

I think just “Computer name” is not enough for Get-Process to connect remotely, you may also need to specify -Credential

for example, following modified version of your second example might work:

Get-ADComputer -filter * -Searchbase ‘ou=A,ou=B,dc=x,dc=y,dc=z’ |
Select-Object @{n=‘computername’ ; e={$_.name}} | ForEach-Object {
         $Cred = Get-Credential -Username $_.UserPrincipalName `
                -Message "Credentials are required to access '$($_.Name)'"
         Get-Process -ComputerName $_.Name -Credential $Cred
}

Would that not also be the case for the command that does work? It’s getting the same information, just from an OU instead of the whole domain. Unless that changes something else behind the scenes.

I don’t know, likely it does, you can run 2 commands without Get-Process portion, and see if the first one produces some additional information that Get-Process accepts on pipeline.

Does my example make any difference? does it return list of processes if you enter valid credentials?

Sounds like it’s erroring out on one of the computers. Try adding -ErrorAction SilentlyContinue to Get-Process

Doesn’t change either error unfortunately

Doesn’t change either error unfortunately

First, you only showed one error originally, from get-process. Second, this vague response doesn’t help anyone help you. What are either error? What did you actually run? You should show what new code you tried (after your changes) and the new errors those provide. Otherwise it’s just a time-wasting guessing game.

Try this code, it will show you which computers are not able to be queried remotely. In the end the variable $processesfromsuccessfulqueries will contain all the processes that were successfully returned. What you’ll see on the screen is just feedback for you to know what happened.

$computerlist = Get-ADComputer -filter * -Searchbase 'ou=A, ou=B,dc=x,dc=y,dc=z' | Select-Object @{n='computername' ; e={$_.name}}

$processesfromsuccessfulqueries = foreach($computer in $computerlist){
    Write-Host Querying processes on $computer.computername -ForegroundColor Cyan

    try{
        $computer | Get-Process -ErrorAction Stop
        Write-Host Successfully queried $computer.computername -ForegroundColor Green
    }
    catch{
        Write-Warning "Error getting processes from $($computer.Computername)"
    }
}

I posted two screenshots. One was from my original post, and one was using the modification that was suggested above. Adding the -ErrorAction SilentlyContinue to the ending Get-Process didn’t change either error.

Working:
Get-ADComputer -filter * | Select-Object @{n=‘computername’ ; e={$_.name}} | Get-Process

Not Working:
Get-ADComputer -filter * -Searchbase ‘ou=A, ou=B,dc=x,dc=y,dc=z’ |
Select-Object @{n=‘computername’ ; e={$_.name}} | Get-Process

What changed?
-Searchbase ‘ou=A, ou=B,dc=x,dc=y,dc=z’

Below is the result of your suggestion:
tempsnip

There were no successful queries.

The original question was why it would work if i was just using get-adcomputer -filter *
but not working when i would add in the searchbase. The information gathering should be the same, but using a narrower scope.

Please when you post code use the preformatted text option. Simply click the little </> icon and paste your code.

Your issue is you can’t query those computers remotely regardless of anything else. Forget the pipeline for now. You can confirm this by changing the test removing the limited scope.

$computerlist = Get-ADComputer -filter *  | Select-Object @{n='computername' ; e={$_.name}}

$processesfromsuccessfulqueries = foreach($computer in $computerlist){
    Write-Host Querying processes on $computer.computername -ForegroundColor Cyan

    try{
        $computer | Get-Process -ErrorAction Stop
        Write-Host Successfully queried $computer.computername -ForegroundColor Green
    }
    catch{
        Write-Warning "Error getting processes from $($computer.Computername)"
    }
}

Or you can try manually querying one of those failing computers.

Get-Process -ComputerName <Name of failing computer(s)>
1 Like