Count the number of objects in folders on remote servers

@Olaf I have the id of any of the specified processes in $ nid. Even if there is only one worker process, its id is passed into a variable, then a verbose tells me that it is ending this process and then waits for that process to finish.
If there are no running processes, I get a null value, which is processed by the condition, and if the condition tells me that it has a null value, then I can be sure that there are no running processes and move on to another script block to clean up folders.
something is wrong?
The only thing is, when I tested on a test server, verbose says it stop the process and wait-process throws an error that it cannot find the process.
otherwise everything seems to be going as it should.

VERBOSE: Performing the operation “Stop-Process” on target “notepad (15812)”.
VERBOSE: Performing the operation “Stop-Process” on target “notepad (36936)”.
Cannot find a process with the process identifier 15812.
+ CategoryInfo : ObjectNotFound: (15812:Int32) [Wait-Process], ProcessCommandException
+ FullyQualifiedErrorId : NoProcessFoundForGivenId,Microsoft.PowerShell.Commands.WaitProcessCommand
+ PSComputerName : server1

Cannot find a process with the process identifier 36936.
+ CategoryInfo : ObjectNotFound: (36936:Int32) [Wait-Process], ProcessCommandException
+ FullyQualifiedErrorId : NoProcessFoundForGivenId,Microsoft.PowerShell.Commands.WaitProcessCommand
+ PSComputerName : server1

What do you get in return when you run this code having both processes started?

$nid = (Get-Process @('notepad', 'pdf24') -ErrorAction SilentlyContinue).id
Get-CimInstance Win32_Process | Where-Object { $_.ParentProcessId -eq $nid }

if you just run this piece, nothing will happen. Maybe I didn’t understand you

both processes now work, if i run your code then nothing happens, no output

That’s my point. So the command in your function

Get-CimInstance Win32_Process | Where-Object { $_.ParentProcessId -eq $nid } | ForEach-Object { Kill-Tree $_.ProcessId}

cannot work if you provided more than one process. :wink:

yes you are right checked the function separately and it does not work. rejoiced early.

@Olaf

$nid = (Get-Process 'notepad', 'pdf24').id

if($nid -eq $null)
    {Write-Host 'No running processes'}
    else{
    Stop-Process -Id $nid -Verbose -force
    Wait-Process -Id $nid
    }

Probably the easiest option is to do it like this

there’s always a little bit room for improvement … :wink:

Stop-Process -Id $nid -force | Wait-Process
1 Like

@Olaf Hi.
the script that we have made with you, for some reason, does not work correctly. I have a condition - we terminate the processes and wait for their completion. then, after completion, the process of cleaning the folders begins, but for some reason the folders began to be cleaned even before all processes were stopped. the script started flooding with access denied errors. I went to the server and saw that indeed some processes have not yet completed. I do not understand what is the reason. folders had to be cleared only after all processes were stopped. help me please.

$Date = Get-Date -Format dd-MM-yyyy-hh-mm
Start-Transcript -Path C:\temp\Cleaning1C_$Date.txt

$ServiceStopScriptBlock = {
# Stopping the Service
$services1C = Get-WmiObject win32_service | ? { $_.Name -like '*' } |
Select Name, DisplayName, State, PathName | 
Where-Object { $_.PathName -Like "*ragent.exe*" };

$Server_Name = gwmi Win32_ComputerSystem | %{$_.DNSHostName}
Write-Host "start: $Server_Name" -ForegroundColor Magenta

$services1C | % {
    $serviceInfo = $_
    $serviceName = $serviceInfo.Name

# Stop the 1С service
    Write-Host "Stopping the service: $serviceName" -ForegroundColor yellow
    Stop-Service -Name $serviceName -NoWait -Force
    #$svc.WaitForStatus('Stopped')
    Write-Host "Pause for 15 seconds" -foregroundColor yellow
    Start-Sleep 15
    $svc = Get-Service $serviceName
    Write-Host "service $serviceName "$svc.Status""

};

# Stopping processes

$Error.Clear()
$nid = (Get-Process @('ragent', 'rmngr', 'rphost') -ErrorAction SilentlyContinue).id


if($nid -eq $null)
    {Write-Host 'not running "ragent", "rmngr", "rphost"'}
    else{
        Stop-Process -Id $nid -Verbose -Force
        Wait-Process -Id $nid -ErrorAction SilentlyContinue
        }
            
    Write-Host "Pause for 20 seconds" -foregroundColor yellow
    Start-Sleep 20

# Clearning the data
        
        Write-Host 'Clear the directory: "C:\Users\srv\AppData\Local\1C\1cv8\"' -ForegroundColor yellow
        Remove-item -Path "C:\Users\srv\AppData\Local\1C\1cv8\*" -Force -Recurse
        
        Write-Host 'Clear the directory: "C:\Users\srv\AppData\Local\Temp\"' -ForegroundColor yellow
        Remove-item -Path "C:\Users\srv\AppData\Local\Temp\*" -Force -Recurse

        Write-Host 'Clear the directory: "C:\Users\srv\AppData\Roaming\1C\1cv8\"' -ForegroundColor yellow
        Remove-item -Path "C:\Users\srv\AppData\Roaming\1C\1cv8\*" -Force -Recurse

}


$ServerListStop = @('Server1', 'Server2')

$SessionListStop = $ServerListStop | Foreach-Object -Process  { New-PSSession -ComputerName $_ }

$SessionListStop | Foreach-Object -Process {
    Invoke-Command -Session $_ -ScriptBlock $ServiceStopScriptBlock
}
    Write-Host "All servers are stopped" -foregroundColor Green


Stop-Transcript

I have a magazine like this

INFO: Start: Server1
INFO: Stopping the service: 1C:Enterprise 8.3 Server Agent (x86-64)
INFO: Pause for 15 seconds
INFO: service 1C:Enterprise 8.3 Server Agent (x86-64) Stopped
INFO: Pause for 20 seconds
INFO: Clear the directory: "C:\Users\srv\AppData\Local\1C\1cv8"
INFO: Clear the directory: "C:\Users\srv\AppData\Local\Temp"
Cannot remove item C:\Users\srv\AppData\Local\Temp\v8_33E9_10bf.tmp: Access to the path ‘C:\Users\srv
AppData\Local\Temp\v8_33E9_10bf.tmp’ is denied.
+ CategoryInfo : PermissionDenied: (C:\Users\srv…8_33E9_10bf.tmp:FileInfo) [Remove-Item], Unauthorized
AccessException
+ FullyQualifiedErrorId : RemoveFileSystemItemUnAuthorizedAccess,Microsoft.PowerShell.Commands.RemoveItemCommand
+ PSComputerName : Server1

Your script looks way to convoluted to me. I’d try to focus on the core function first and add some eye candy later on if the core function works robustly.

Basically that’s all you need:

$ServerList = 'Server1', 'Server2'
$PSSessionList = New-PSSession -ComputerName $ServerList
Invoke-Command -Session $PSSessionList -ScriptBlock {
    Stop-Process -Name 'ragent', 'rmngr', 'rphost' | Wait-Process 
    Remove-item -Path 'C:\Users\srv\AppData\Local\1C\1cv8\*' -Recurse -Force
    Remove-item -Path 'C:\Users\srv\AppData\Local\Temp\*' -Recurse -Force
    Remove-item -Path 'C:\Users\srv\AppData\Roaming\1C\1cv8\*' -Recurse -Force
    Start-Process -FilePath '... ragent.exe'
    Start-Process -FilePath '...  rmngr.exe'
    Start-Process -FilePath '... rphost.exe'
}

Try it with one server first, plan a downtime, open the folders in separate explorer windows and watch what happens. If that worked add another server and so on …

Hi.
the problem is that the cleaning of folders starts without waiting for the process to stop.

can after Wait-Process add some kind of cycle to check that all processes are completed?

You can do what ever you think is needed but for me it sounds more and more that you rather should contact the vendor of the software you’re dealing with. It shouldn’t be necessary to cleanup temporary folders regularily.

I just noticed now that you also stop some service in your script. I actually missed that before. You may add the needed Stop-Service commands to your script if needed and try again. But you should keep in mind that some services do get restarted when they get stopped.

yes, the services are stopped and after that the worker processes remain. therefore, these processes are terminated forcibly. And then the folders should be cleaned up.
Unfortunately, we need to do this every day, because without these actions, the cluster starts to work incorrectly. for now, we can’t do without cleaning up temp folders on a daily basis.
still don’t understand why folders start to be cleaned up before stopping processes if Wait-Process is specified?

Does it work when you do it manually? How do you run the script then? With the same account you do it manually?

@Olaf I run the script from a remote PC, there are no problems with running the script. He works on my behalf, and I am the administrator of these servers.
other employees do it manually at night, go to each server, stop the services, then close the remaining processes, then clear the specified folders, and then start the services again.

Wait … what? Does it work when you run the script manually? So what’s the actual issue?

1 Like

@Olaf the script works, but on one server out of 5, folders are cleaned up before all processes are stopped. Since the processes are still there, the folder on this server is busy and does not allow for cleanup. because of this, we will have to manually clean. This is the question, why does the folder start to be cleaned without waiting for | Wait-Process
the only problem remained with this.

So you don’t have a PowerShell issue or a script issue - you have an issue with this server I’d say. :wink:
I don’t know if it’s possible to help you troublesooting with this particular issue.

@Olaf Okay, I’ll try to add a couple of loops that will check all processes for completion and that the folders are empty.
but the problem is not with the server, but that the script does not wait for the processes to finish, although I tell it to wait.