Forum Discussion

4 Replies

  • Hi Sekharchandra,

     

    the following iRule is hopefully doing what you try to accomplish. Please replace the relevant values for hostnames to redirect to and the ratio values.

     

    Turn off logging, if it works as expected. Please keep in mind, that there is no default pools needs to be associated with this iRule and there is no healthchecking considered.

     

    No need to modify anything in the context of HTTP_REQUEST.

     

    when RULE_INIT {
         set servername to use for responses (default will be "BIGip"), turned off with "noserver" switch in HTTP::respond
        set static::srvname "ServerLB"
         set redirect code (301=moved permanently, 302=moved temporarily)
        set static::statcode 301
         set server ratio values
        set static::ratioA 1
        set static::ratioB 9
         set server hostnames
        set static::hostA "www.serverA.bit"
        set static::hostB "www.serverB.bit"
         activate logging (0=disabled, 1=enabled)
        set static::debugRatioLb 1
    }
    
    when HTTP_REQUEST {
        if { [expr {[table incr req_counter]%[expr {$static::ratioA+$static::ratioB}]}] < $static::ratioA } {
             values from 0 to less than ratioA will be directed to serverA
            if { $static::debugRatioLb > 0 } {
                log local0. "total counter: <[table lookup req_counter]>; modulo <[expr {[table lookup req_counter]%[expr {$static::ratioA+$static::ratioB}]}]> match ratio <$static::ratioA>"
            }
            HTTP::respond $static::statcode noserver server $static::srvname Location http://$static::hostA[HTTP::uri]
            return
        } else {
             values greater than ratioA will be directed to serverB
            if { $static::debugRatioLb > 0 } {
                log local0. "total counter: <[table lookup req_counter]>; modulo <[expr {[table lookup req_counter]%[expr {$static::ratioA+$static::ratioB}]}]> match ratio <$static::ratioB>"
            }
            HTTP::respond $static::statcode noserver server $static::srvname Location http://$static::hostB[HTTP::uri]
            return
        }
    }
    

    The iRule is designed for two target servers only but can be easily enhanced.

     

    Thanks, Stephan

     

  • You could also do something like create your pool with a ratio of 18:1:1 for your

    ::
    . Make your dummy members with the names www.abc.com and www.xyz.com with ips like 1.1.1.1 and 1.1.1.2 and not assign a monitor to them. Then use an iRule like this. Obviously you'll have to tweak the pool ratios if you have more than one real member. Persistence could work with this and you could monitor pool member status, other than the dummies.

    when HTTP_REQUEST {
        set myLocation [HTTP::uri]
    }
    
    when LB_SELECTED {
        if { [LB::server name] starts_with "www." } {
            set myHost [string map {"//" ""} [LB::server]]
            set redirect 1
            persist none
        }
        else {
            set redirect 0
        }
    }
    
    when HTTP_RESPONSE {
        if {$redirect} {
            HTTP::respond 302 noserver Location "http://$myHost$myLocation"
        }
    }
    

    With this you would need to put the partition name where the pool member lives, could be Common.

  • Hi Sekharchandra,

     

    I guess you will run into all kind of persistence problems trying to let 90% traffic get through to the primary site and pick 10% to be distributed via redirect.

     

    The virtual server needs a criteria to differentiate between clients with a local connection an new requests. This could be a cookie to be evaluated with the initial client request.

     

    To simplify things I just enhanced my proposed solution by a third direction. So the distribution schema follows Brads approach of 18:1:1.

     

    when RULE_INIT {
         set servername to use for responses (default will be "BIGip"), turned off with "noserver" switch in HTTP::respond
        set static::srvname "ServerLB"
         set redirect code (301=moved permanently, 302=moved temporarily)
        set static::statcode 301
         set server ratio values
        set static::ratioA 18
        set static::ratioB 1
        set static::ratioC 1
         set server hostnames
        set static::hostA "www.serverA.bit"
        set static::hostB "www.serverB.bit"
        set static::hostC "www.serverC.bit"
         activate logging (0=disabled, 1=enabled)
        set static::debugRatioLb 1
    }
    
    when HTTP_REQUEST {
        if { [expr {[table incr req_counter]%[expr {$static::ratioA+$static::ratioB$static::ratioC}]}] < $static::ratioA } {
             values from 0 to less than ratioA will be directed to serverA
            if { $static::debugRatioLb > 0 } {
                log local0. "total counter: <[table lookup req_counter]>; modulo <[expr {[table lookup req_counter]%[expr {$static::ratioA+$static::ratioB+$static::ratioC}]}]> match ratio <$static::ratioA>"
            }
            HTTP::respond $static::statcode noserver server $static::srvname Location http://$static::hostA[HTTP::uri]
            return
        } elseif { [expr {[table incr req_counter]%[expr {$static::ratioA+$static::ratioB$static::ratioC}]}] < [expr {$static::ratioA+$static::ratioB}]} {
             values greater than ratioA and less than ratioA + ratioB will be directed to serverB
            if { $static::debugRatioLb > 0 } {
                log local0. "total counter: <[table lookup req_counter]>; modulo <[expr {[table lookup req_counter]%[expr {$static::ratioA+$static::ratioB+$static::ratioC}]}]> match ratio <$static::ratioB>"
            }
            HTTP::respond $static::statcode noserver server $static::srvname Location http://$static::hostB[HTTP::uri]
            return
        } else {
             values greater than ratioA  + ratioB will be directed to serverC
            if { $static::debugRatioLb > 0 } {
                log local0. "total counter: <[table lookup req_counter]>; modulo <[expr {[table lookup req_counter]%[expr {$static::ratioA+$static::ratioB+$static::ratioC}]}]> match ratio <$static::ratioC>"
            }
            HTTP::respond $static::statcode noserver server $static::srvname Location http://$static::hostC[HTTP::uri]
            return
        }
    }
    

    Thanks, Stephan

     

    PS: Reposted due to broken formatting