Can not compare Values of Variable with strings in Powershell

390 Views Asked by At

I am trying to get info about an iSCSI-Targets Connectionstate.

Ideally I want to have a variable with a value that is True or False for connected or not connected, so that i can run commands to connect or disconnect as needed.

If i set the Variable directly it's working fine. Setting the Variable with the output of a cmdlet seems to work but comparing the Values False or True with IF is always resulting in True. For me the question is: where is the difference between setting the Variable directly to True and using the output of the cmdlet...?

Sample one:

$IsConnected=true

if($IsConnected -eq 'true') {
    echo IsConnected!
} else {
    echo IsNotConnected
}

Results, as expected, in: IsConnected

Sample two:

$IsConnected=False
if($IsConnected -eq 'true') {
    echo IsConnected!
} else {
    echo IsNotConnected
}

Results, as expected, in: IsNotConnected

So now my knowledge ends...:

Sample three:

PS ~> $IsConnected=get-iscsitarget | select -ExpandProperty IsConnected
PS ~> echo $IsConnected
True
PS ~> if($IsConnected -eq 'True') {Echo "IsConnected"}else{echo "IsNotConnected"}
IsConnected
PS ~> if($IsConnected -eq 'False') {Echo "IsConnected"}else{echo "IsNotConnected"}
IsConnected
PS ~> if($IsConnected -eq '17beerarenotenaugh') {Echo "IsConnected"}else{echo "IsNotConnected"}
IsConnected
2

There are 2 best solutions below

1
Mathias R. Jessen On BEST ANSWER

PowerShell's comparison operators are overloaded, meaning they might have different behaviors based on the type of operand you provide.

The behavior depends entirely on the type of the left-hand side (lhs) operand you provide, and PowerShell will try to convert the right-hand side (rhs) to the same.

In your example, the value of the $IsConnected variable is a [bool] - and PowerShell therefore attempts to convert the rhs operand to a [bool] to.

The conversion logic for [string] to [bool] is:

  • Empty strings = $false
  • Non-empty strings = $true

Since 'True', 'False' and '17beerarenotenaugh' are all non-empty, the if conditions are basically interpreted as:

if($IsConnected -eq $true) { ... }
if($IsConnected -eq $true) { ... }
if($IsConnected -eq $true) { ... }

Use the automatic variables $true and $false to avoid this:

PS ~> if($IsConnected -eq $false) {Echo "IsConnected"}else{echo "IsNotConnected"}
IsNotConnected

alternatively, use the -not operator:

PS ~> if(-not $IsConnected) {Echo "IsConnected"}else{echo "IsNotConnected"}
IsNotConnected
1
Heino Backhaus On

thanks for helping!. Our NAS disconnects sometimes or just don't connect after Reboot so maybe some others find this usefull...:

$IsConnected = Get-IscsiTarget | Select-Object -ExpandProperty IsConnected
If($IsConnected -eq $false)
{
    Get-IscsiTarget | Where-Object -Property NodeAddress -Like "iqn.2000-01.com.synology:nas01.Target-myiqnnumber" |
    Connect-IscsiTarget -AuthenticationType ONEWAYCHAP -ChapUsername mychapuser -ChapSecret mychapuserssecret
}
else
{
    echo "IsConnected=$Isconnected iSCSI-Drive:OK"
}