In one of my servers we have an program that we need to update each month, this program is running on a terminal server.
My basic script is working (it's very simple):
Get-SmbOpenFile |where {$_.Path -eq "D:\Shares\Programs\test.exe"} |select ClientUserName, path |ft -autosize
pause
But i'am trying to make it more "smarter" so I've tried to use the IF statement:
First test:
$open = Get-SmbOpenFile |where {$_.Path -eq "D:\Shares\Programs\test.exe"} |`
select ClientUserName, path |ft -autosize
if ($open -eq "true")
{ write-host "showing open files"
}
elseif ($open -eq "false")
{ "All cloesd"
}
pause
Second test:
$open = Get-SmbOpenFile |where {$_.Path -eq "D:\Shares\Programs\test.exe"} |`
select ClientUserName, path |ft -autosize
if ($open -eq $true)
{
write-host "showing open files"
}
elseif ($open -eq $false)
{
"All cloesd"
}
I've also tried to define the variable in that way:
$open = Get-SmbOpenFile |where {$_.Path -eq "D:\Shares\Programs\test.exe"}
I'am not getting actually any output at all when i use the IF statement.
Thanks a lot for your help !
Only ever use Format-*
cmdlets such as ft
(Format-Table
) for display formatting; never use them if data must be programmatically processed.
Format-*
cmdlets output formatting instructions, not data - see this answer.
Even with | ft -autosize
removed, you shouldn't compare $open
to $true
or $false
, because such an explicit comparison will not generally work as intended if the LHS isn't already a Boolean (type [bool]
)[1]; instead, take advantage of PowerShell's implicit to-Boolean conversion - see the bottom section of this answer.
Your if
branch doesn't actually output $open
; it only outputs a Write-Host
status message to the display.
To put it all together:
$open = Get-SmbOpenFile |
Where-Object {$_.Path -eq "D:\Shares\Programs\test.exe"} |
Select-Object ClientUserName, Path
if ($open) {
Write-Host "showing open files"
$open # output the result
}
else {
Write-Host "all closed"
}
Select-Object
returns either:
a [pscustomobject]
instance[2] (a custom object with properties .ClientUserName
and .Path
)
[pscustomobject]
instance - regardless of its structure - evaluates to $true
in a Boolean context.or "nothing" (technically, [System.Management.Automation.Internal.AutomationNull]::Value
), if the Where-Object
cmdlet didn't find the specified path in Get-SmbOpenFile
's output.
$false
in a Boolean context.Again, see the bottom section of this answer for the complete set of rules of implicit to-Boolean conversion.
[1] Notably, a non-primitive object as the LHS always yields $false
when compared to $true
(though not with the operands reversed); e.g., (Get-Item /) -eq $true
; also, any nonzero number that isn't exactly 1
will indicate $false
; e.g.: 2 -eq $true
. Additionally, with an array-valued LHS, -eq
acts as filter, returns the subarray of matching items (e.g., (1, 2, 1) -eq $true
returns 1, 1
.
[2] In general, Select-Object
can return multiple objects, in which case $open
would receive an[object[]]
-typed array of [pscustomobject]
instances. An array with 2 or more elements is always $true
in a Boolean context.