Forum Discussion

JCMATTOS_41723's avatar
JCMATTOS_41723
Icon for Nimbostratus rankNimbostratus
Aug 08, 2013

Combining Swtich iRules for HTTP::uri and HTTP::cookie?

We have version 11.1 and trying to create a new application workflow process by combining the current switch irules into one. We currently have an HTTP::uri and HTTP::cookie irules working separately but have the need to combine them to create new order of operation workflow. When combining them the first switch entry works by parsing uri /application/ and sending it to (POOLA), BUT the second nested cookie irule does not work and sends it to the default pool and NOT the assigned (POOLB). It seems to stop after the first switch irule logic and skip the cookie process altogether. Any suggestions?

 

when HTTP_REQUEST {

 

switch -glob [string tolower [HTTP::uri]] {

 

"*/application/*" {

 

pool QA-POOLA-80 }

 

switch [ HTTP::cookie "UserInfo" ] {

 

}

 

"*COMPANYID=GC*" {

 

pool QA-POOLB-80 }

 

}

 

}

 

 

8 Replies

  • If I understand what you're doing, it looks like you're attempting to use a switch command as a condition to a higher switch command, which wouldn't work. You can nest switches if you put the internal conditionals INSIDE the action of a specific condition:

    Example:

    switch test1 {

    "test1_condition1" {

    switch test2 {

    test2_condition1 {...}

    }

    }

    }

    So if you're trying to say "if a URI equals something -OR- a cookie equals something, then I think you really need to first pick the most important one and refactor them:

    Example:

    
    when HTTP_REQUEST {
        switch - glob [string tolower [HTTP::uri]] {
           "*/application/*" {
                pool QA-POOLA-80
            }
            default {
                switch -glob [HTTP::cookie "UserInfo"] {
                    "*COMPANYID=GC*" {
                        pool QA-POOLB-80
                    }
                }
            }
        }
    }
    

  • Thx for the assistance Kevin! So in other words, my current irule is an "AND" switch process? What I really need is an "OR" switch process. Will the default switch logic not send unmatched traffic thru the main pool under the virtual server then? If so, I would still need the default catchall main pool to still work. Thx!
  • If you don't have a "default" condition in the switch, and nothing matches any condition, it would fall through. I was assuming you needed an OR based on your original iRule. Do you need an AND?
  • Essentially, we have 3 independent pools for each logic that are eligible depending on the match. The uri /application/ switch logic needs to supercede the other 2 logics. In other words, if no match is found to the /application/ uri then the cookie logic will takeover and if no match is found the default pool will catch all. If we can't get it to work in the switch logic fashion than I don't mind going to the "if and elseif" logic if that makes it easier. Originally, the problem we ran into running them independently was the cookie was taking precedence over the uri logic even when the order of the irules was placed in the correct sequence. Hope that makes a little more sense...Thx!
  • if no match is found to the /application/ uri then the cookie logic will takeover and if no match is found the default pool will catch all.doesn't irule Kevin suggested work? i am not sure but i think it matches what you described.
  • Well, you definitely want an OR structure, but honestly I think an if/elseif would be a better choice here. You only have 2 conditions and a switch context would require nesting another switch in the default condition of the parent switch, and then another switch nested in the default condition of that switch. Generally speaking, a switch is faster when you're comparing large sets of values, compared to an if/elseif, but with only 2 conditions I think you'd be hard pressed to see a difference in performance.

    
    if { [string tolower [HTTP::uri]] contains "/application/" } {
        pool this_pool
    } elseif { [HTTP::cookie exists foo-cookie] } {
        pool that_pool
    } else {
        pool default_pool
    }
    

  • I tried the if format and did want to eventually add more cookie parsers, if I use the datagroups would this work?

     

    when HTTP_REQUEST { if { [string tolower [HTTP::uri]] contains "/application/"} { pool QA-POOLA-80 } elseif { ([class match [HTTP::cookie "UserInfo"] contains company_ID])} { pool QA-POOLB-80 } }

     

  • I would use [HTTP::cookie value UserInfo], but otherwise yes that should all work.