Forum Discussion

Jeff_Giroux's avatar
Sep 08, 2011

irule processing and performance of 2 irules both doing http_request

I have a VIP that receives a peak of 2,500 current client connections. It has a current irule that "when http_request" doing basic pool decisions. I need to apply another irule that does high speed logging. I have both irules working fine.

 

 

irule for high speed logging

 

1. performs a "when client_accept" and also "when http_request".

 

2. sets some variables like client IP, http query, http path, etc.

 

3. sends high speed log

 

 

current vip irule

 

1. performs a "when http_request" with "if" pool decision based on URI match.

 

 

Question:

 

1. How will the box behave once I apply the new irule to the top of the list? Both irules are doing the http_request and I want to avoid having the packets inspected twice in separate irules.

 

2. Will I benefit from extracting the parts in the high speed logging irule and pasted into the appropriate section of the current prod irule?

 

 

high speed logging - irule that needs to be added

 

high speed logging - will grab certain fields to be used for forensics data

 

 

when CLIENT_ACCEPTED {

 

set hsl [HSL::open -proto UDP -pool pool_syslog_514]

 

set clientip [IP::remote_addr]

 

}

 

 

when HTTP_REQUEST {

 

set method [HTTP::method]

 

set path [HTTP::path]

 

set host [HTTP::host]

 

set query [HTTP::query]

 

set uri [HTTP::uri]

 

}

 

 

when HTTP_RESPONSE {

 

set now [clock format [clock seconds] -format "%d/%b/%Y:%H:%M:%S %z"]

 

set contentlength [HTTP::header "Content-Length"]

 

log local0. "<;190> src_ip=$clientipdest_vip=$host http_method=$method http_path=$path $query http_version=HTTP/[HTTP::version] return_code=[HTTP::status]"

 

HSL::send $hsl "<;190> src_ip=$clientipdest_vip=$host http_method=$method http_path=$path $query http_version=HTTP/[HTTP::version] return_code=[HTTP::status]"

 

}

 

 

--currentirule already applied making pool decisions--

 

when HTTP_REQUEST {

 

if { [HTTP::path] starts_with "/123/help" } {

 

pool serverpool01_8080

 

persist none }

 

elseif { [HTTP::path] starts_with "/123/petsemail" } {

 

pool serverpool02_8080

 

persist none }

 

elseif { [HTTP::path] starts_with "/123/profileeditor" } {

 

pool serverpool03_8080

 

persist none }

 

elseif { [HTTP::path] starts_with "/123/activitystream" } {

 

pool serverpool04_8080

 

persist none }

 

elseif { [HTTP::path] starts_with "/123/core" } {

 

pool serverpool05_8080

 

persist none }

 

elseif { [HTTP::path] starts_with "/123/" } {

 

pool serverpool06_8080

 

persist none }

 

elseif { not ([HTTP::path] starts_with "/admin/") } {

 

pool serverpool07_8080 }

 

elseif { ([IP::client_addr] == "10.1.1.1" or [IP::client_addr] == "10.50.1.1" or [IP::client_addr] == "10.100.1.1" ) and [HTTP::path] starts_with "/admin/"} {

 

pool pool_qlaxorin_8080 }

 

else { HTTP::respond 404 content { 404 Not Found 404 Not Found }

 

}

 

}

 

 

  • There isn't much you could save by trying to combine the iRules or share variables across them. However, you can optimize both rules separately:

     logging iRule
    when CLIENT_ACCEPTED {
       set hsl [HSL::open -proto UDP -pool pool_syslog_514]
    }
    when HTTP_REQUEST {
        Save the request components we want to log in the response
       set log_string <190> src_ip=[IP::client_addr], dest_vip=[HTTP::host],http_method=[HTTP::method],\
          http_uri=[HTTP::uri], http_version=HTTP/[HTTP::version]"
    }
    when HTTP_RESPONSE {
       HSL::send $hsl "$log_string, return_code=[HTTP::status]"
    }

    Pool selection iRule

    when HTTP_REQUEST {   
       switch -glob [HTTP::path] {
          "/123/help*" {
             poolserverpool01_8080
             persist none
          }
          "/123/petsemail*" {
             poolserverpool02_8080
             persist none
          }
          "/123/profileeditor*" {
             poolserverpool03_8080
             persist none
          }
          "/123/activitystream*" {
             poolserverpool04_8080
             persist none
          }
          "/123/core*" {
             poolserverpool05_8080
             persist none
          }
          "/123/*" {
             poolserverpool06_8080
             persist none
          }
          "/admin*" {
             if { [IP::addr [IP::client_addr] equals 10.1.1.1] or \
                [IP::addr [IP::client_addr] equals 10.50.1.1 or \
                [IP::addr [IP::client_addr] equals 10.100.1.1 } {
                poolpool_qlaxorin_8080
             } else {
                HTTP::respond 404 content { 404 Not Found       }
             }
          }
          default {
             HTTP::respond 404 content { 404 Not Found       }
          }
       }
    }

    I haven't tested the iRules, but hopefully they give you an idea of how you can make these more efficient.

    Also, you could add the hosts/networks you want to allow access to the /admin URIs from to an address type datagroup and then use the class command to do the lookup.

    Aaron