working with -ge and -le

This topic contains 10 replies, has 3 voices, and was last updated by  Richard Siddaway 1 month, 1 week ago.

  • Author
    Posts
  • #89122

    Zach
    Participant

    hey guys, struggling to understand why this is happening.

    I've written a script to go out to our Azure ServiceBus, check the message count in the message queues, then call up a function to scale the instances if that count is greater or less than specified thresholds. However, I've noticed that the first set of If/Elseif/Else works fine, however, the second set does not and it appears to be due to the comparison statements. Here's more script:

    $clientTriggerOut = "50"
    $clientTriggerIn = "25"
    $ServerTriggerOut = "2000"
    $ServerTriggerIn = "1000"
    
    $queueAR = "Client", "Server"
    
    foreach ($i in $queueAR){
    $queue = $i
    Get-AzureRmServiceBusqueue -ResourceGroupName servicebus -NamespaceName  -Name $Queue 
    Get-AzureRmServiceBusqueue -ResourceGroupName servicebus -NamespaceName  -Name $Queue | Select MessageCount | Export-csv -Path "\\Server\c$\Temp\Azure Scripts\ServiceBus\$queue.txt" -NoTypeInformation
    $MessageCount = (Get-Content "\\Server\c$\Temp\Azure Scripts\ServiceBus\$queue.txt" | Select-Object -Skip 1 | Out-String) -replace '"'
    
    if ($queue -match "Client"){
         If ($MessageCount -le $clientTriggerIn){
           write-host "in"    #Clientin
               }
        elseif ($MessageCount -ge $Clienttriggerout) {
           write-host "out"     #Clientout
    
               }
        else {Write-Host "Uhhhhh.... Something went wrong"}
    }
    
    elseif ($queue -match "Server"){
    
         If ($MessageCount -le $ServerTriggerIn){
         write-host "in"      #Serverin
               }
        elseif ($MessageCount -ge $Servertriggerout) {
            write-host "out"   #Serverout
               }
        else {Write-Host "Uhhhhh.... Something went wrong"}
     }
    else {Write-Host "Didn't work Bob!"}
    
    }
    
    

    When I run this right now, Client comes back with 0 messages and write-host tells me "in". That's good since the IN trigger is 25.

    However, when it gets to server, the count is currently 541 which is less than or equal to the IN trigger, however, that comparison comes back false, moves on to the out trigger and comes back true, thus write-host returns "out".

    My understanding is that $messagecount -ge $servertriggerout should return a boolean value of $true if $messagecount (541) is greater than or equal to $servertriggerout (2000) and $false if not.

    So what am I missing here?

    Also, if you know of a better way to format the message count value so that its just the numerical value without any headers or spaces please let me know.

  • #89128

    Don Jones
    Keymaster

    I'm curious as to why you've defined those initial values as strings rather than as integers?

    • #89129

      Zach
      Participant

      Cause I don't know any better obviously ;-).
      I've only been in powershell for about a year so by all means if you see something not quite right let me know.

  • #89131

    Don Jones
    Keymaster

    Yeah, I'd drop the quotes. When you ask PowerShell to compare strings, in terms of less or greater, it thinks about them in terms of their lengths. It isn't going to implicitly make those into numeric values. But if you define them as numbers you should get the results you're expecting.

    For example, try:

    "55" -gt "00001"

    versus

    55 -gt 00001

  • #89134

    Don Jones
    Keymaster

    And, BTW, it takes the first operand as its cue for the data type if it's going to do coercion.

    "5" + 5

    versus

    5 + "5"

    As another example you can try to see how the behavior changes.

    • #89138

      Zach
      Participant

      That makes more sense. So I've removed the double quotes from the trigger variables and added [int] before $messagecount so I wouldn't have to rearrange things and their now returning the expected results.

      So it now looks like this

      
      
      $clientTriggerOut = 50
      $clientTriggerIn = 25
      $ServerTriggerOut = 2000
      $ServerTriggerIn = 1000
      
      $queueAR = "client", "server"
      
      foreach ($i in $queueAR){
      $queue = $i
      Get-AzureRmServiceBusqueue -ResourceGroupName servicebus -NamespaceName  -Name $Queue 
      Get-AzureRmServiceBusqueue -ResourceGroupName servicebus -NamespaceName  -Name $Queue | Select MessageCount | Export-csv -Path "\\server\c$\Temp\Azure Scripts\ServiceBus\$queue.txt" -NoTypeInformation
      $MessageCount = (Get-Content "\\server\c$\Temp\Azure Scripts\ServiceBus\$queue.txt" | Select-Object -Skip 1) -replace '"'
      
      if ($queue -match "client"){
           If ([int]$MessageCount -le $clientTriggerIn){
             write-host "in"    #Clientin
                 }
          elseif ([int]$MessageCount -ge $Clienttriggerout) {
             write-host "out"     #Clientout
      
                 }
          else {Write-Host "Uhhhhh.... Something went wrong"}
      }
      
      elseif ($queue -match "server"){
      
           If ([int]$MessageCount -le $ServerTriggerIn){
           write-host "in"      #Serverin
                 }
          elseif ([int]$MessageCount -ge $Servertriggerout) {
              write-host "out"   #Serverout
                 }
          else {Write-Host "Uhhhhh.... Something went wrong"}
       }
      else {Write-Host "Didn't work Bob!"}
      
      }
      
      

      Would you mind expounding on your formatting recommendation though? I'm not sure i understand what this is doing or where it should go.

      $props = @{'ClientName'=$clientName
      'MessageCount'=$messageCount} New-Object -Type PSObject -Prop $props

  • #89137

    Don Jones
    Keymaster

    Oh, you also asked:

    Also, if you know of a better way to format the message count value so that its just the numerical value without any headers or spaces please let me know.

    Write-Host isn't how you want to create output in PowerShell. It kills puppies. You probably want to construct an object and output that to the pipeline. For example:

    $props = @{'ClientName'=$clientName
               'MessageCount'=$messageCount}
    New-Object -Type PSObject -Prop $props
    

    That will let PowerShell engage its formatting system to display the output on-screen. I've a lovely couple of books about all this if you're interested ;).

    • #89141

      Zach
      Participant

      oh also, the script won't actually use write-host, i'm just using it to verify that the if/else statements are working properly. I've commented out the function calls so that they won't trigger while i'm testing. a $true will call a function to either spin up a new instance or remove one using a function that i did not include here.

      Also book recommendations are great!

  • #89143

    Don Jones
    Keymaster

    Write-Verbose would be a suitable replacement for the way you're using Write-Host.

    Output from a PowerShell script/function/whatever should be objects. Objects are basically a data structure, where you create properties to contain bits of information. PowerShell's formatting commands – like Format-Table, ConvertTo-HTML, etc – all understand objects. So if you get your output into that kind of data structure, it becomes a lot easier to consume that output in various ways, format it in various ways, etc. As opposed to just dumping out numbers or strings. This is, in fact, the entire reason PowerShell exists (object-based output) and is what MS has patents on. It's what makes PowerShell not Bash.

    • #89144

      Zach
      Participant

      Ok,

      I think I understand what you're saying. Based on that, this would be the better way to do it.

      Get-AzureRmServiceBusQueue -ResourceGroupName servicebus -NamespaceName -Name $Queue  < ---will be removed in final $messages = Get-AzureRmServiceBusQueue -ResourceGroupName servicebus -NamespaceName  -Name $Queue | Select MessageCount
      $MessageCount = $messages.MessageCount
      if ($queue -match "client"){
           If ($MessageCount -le $clientTriggerIn){
             Clientin
                 }
          elseif ($MessageCount -ge $Clienttriggerout) {
             Clientout
      
                 }
          else {Write-Host "Uhhhhh.... Something went wrong"}
      }
      
      elseif ($queue -match "server"){
      
           If ($MessageCount -le $ServerTriggerIn){
           Serverin
                 }
          elseif ($MessageCount -ge $Servertriggerout) {
           Serverout
                 }
          else {Write-Host "Uhhhhh.... Something went wrong"}
       }
      else {Write-Host "Didn't work Bob!"}
      
      }
      
  • #89234

    Richard Siddaway
    Moderator

    I'd use Write-Warning instead of Write-Host when something goes wrong if you want the processing to continue. if you want it to stop use throw

You must be logged in to reply to this topic.