Hello Arnaud,
Thanks for your time to look on this.
We created the below iRule to achieve this. But it is not working as expected.
Do you see any mistake on our irule?
!!!!!!!
when RULE_INIT {
log local0. "Running RULE_INIT"
All of these parameters SHOULD be set from a class... So you can vary them and only require ONE iRule for all...
Max session count
set static::max_active_clients 10
Prefix for session cookie (VS name will be appended)
set static::sessionCookiePrefix "session"
Session (Idle) timeout in seconds
set static::sessionTimeout 600
HTML content for limit notification page
set static::html_content "over limit"
base64 enconded sorry page
set ::sorrypage {
We're Sorry. Our servers are currently over capacity and certain areas of our site may be temporarily unavailable. We're working to resolve the issue as quickly as possible.
}
log local0. "rule session_limit initialized: max: $static::max_active_clients cookieprefix: $static::sessionCookiePrefix timeout: $static::sessionTimeout"
}
when HTTP_REQUEST {
set subtableName "sessionLimit-[virtual name]"
set sessionCookieName "$static::sessionCookiePrefix-[virtual name]"
set need_cookie 0
set URI [string tolower [HTTP::uri]]
; test cookie presence
if {[HTTP::cookie exists $sessionCookieName]} {
set client_id [HTTP::cookie $sessionCookieName]
Check the session still exists
set sessiondata [table lookup -subtable $subtableName $client_id]
if { $sessiondata != "" } {
We have a valid session... The lookup has reset the timer on it so just finish processing
Optional processing in here to check or validate the client session via IP etc if required...
log local0. "Valid session $client_id - continuing"
return
}
}
No valid session... So do we have a free 'slot'?
log local0. "No session. Checking for free slot (Max $static::max_active_clients)"
set sessionCount [table keys -subtable $subtableName -count]
log local0. "No session. Checking for free slot (Current $sessionCount)"
if {($sessionCount < $static::max_active_clients) or ($URI contains "ops")} {
Yes we have a free slot... Allocate it and note that we need to set the cookie on the client
set need_cookie 1
set client_id [format "%08d" [expr { int(100000000 * rand()) }]]
set sessionValue [IP::client_addr]
avoid /ops/ to be added on count table
if { !($URI contains "ops") } {
table add -subtable $subtableName $client_id $sessionValue $static::sessionTimeout
}
log local0. "New Session ($client_id) added value $sessionValue Timeout $static::sessionTimeout"
} else {
Send a response
HTTP::respond 200 content $static::html_content
HTTP::respond 200 content [b64decode $::sorrypage]
Close the connection
TCP::close
Log a message to /var/log/ltm if debug is enabled
if {$::debug}{log local0. "Over limit showing limiter page"}
}
}
when HTTP_RESPONSE {
; insert cookie if needed
if {$need_cookie == 1} {
HTTP::cookie insert name $sessionCookieName value $client_id path "/"
}
}
!!!!!