Forum Discussion
squeezebox_2829
Nimbostratus
Aug 05, 2016HTTP::retry doesn't work on BIGIP LTM 10.2.4
I am attempting to reference an external service which performs a lookup based on the request's ip address and returns a response either allowing or disallowing the traffic. I am using the solution p...
Kai_Wilke
MVP
Aug 06, 2016Hi Squeezebox,
take a look to the iRule below. Its a polished version of your iRule with an added
[TABLE] functionality to cache previous verification results and an additional filter to HTTP::retry only request using a GET method (the verification of other methods would have lots of implications).
when RULE_INIT {
set string to match for valid connection
set static::valid_string "Sure"
set static::table_cache_duration "10" ; seconds
}
when CLIENT_ACCEPTED {
set flag to control logical flow. 1 means lookup is pending.
set lookup 1
}
when HTTP_REQUEST {
If each request on the same connection must force a lookup,
re-initialize the value of the flag here
In this case, lookup result based on client IP is good for
the life of the connection, so we'll leave the flag alone here.
if { $lookup } then {
verify only GET request.
if { [HTTP::method] eq "GET" } then {
try to offload the verification of the current request with data of previous lookup results
if { [table lookup -notouch "is_allowed_[IP::client_addr]"] eq "" } then {
No previous request data is cached. Performing an online verification...
save the request so we can replay it to the LB server later;
set orig_request [HTTP::request]
inject lookup URI in place of original request;
HTTP::uri "/getAllowed?ip=[IP::client_addr]"
remove any cookie information for security purposes
HTTP::header remove "Cookie"
and send the out-of-band validation query to the DB_pool.
pool geo_pool
} else {
The client is verified using cached results.
set lookup 0
}
} else {
Current request is not a GET request. Do not verify the request to reduce complexity of collection and replay of HTTP::payload data.
set lookup 0
}
}
}
when HTTP_RESPONSE {
If lookup flag is still on in response event, this is the response
to the lookup, so we collect entire payload (up to 1MB limit)
both to evaluate the DB server response and to prevent this response
from being returned to the client.
Already-validated connections will bypass the rest of the rule.
if { $lookup } then {
if { ( [HTTP::header value "Content-Length"] ne "" ) and
( [HTTP::header value "Content-Length"] < 1048576) } then {
HTTP::collect [HTTP::header "Content-Length"]
} else {
HTTP::collect 1048576
}
}
}
when HTTP_RESPONSE_DATA {
HTTP_RESPONSE_DATA will only be triggered for a DB lookup.
(All other requests have already been forwarded to the LB pool.)
If response from DB indicates connection is valid, reset the
lookup flag & replay the request to the LB server.
Otherwise, reject the connection
if { [HTTP::payload] contains $static::valid_string} then {
Cache the OK response to offload subsequent requests
table set "is_allowed_[IP::client_addr]" "1" indefinite $static::table_cache_duration
Replay the origianl request
set lookup 0
pool reg_pool
HTTP::retry $orig_request
} else {
log "rejected"
reject
}
}
Note: If written the iRule out of my mind. If the syntax isn't working correctly, then post back the error logs to see whats going wrong...
Cheers, Kai
Help guide the future of your DevCentral Community!
What tools do you use to collaborate? (1min - anonymous)Recent Discussions
Related Content
DevCentral Quicklinks
* Getting Started on DevCentral
* Community Guidelines
* Community Terms of Use / EULA
* Community Ranking Explained
* Community Resources
* Contact the DevCentral Team
* Update MFA on account.f5.com
Discover DevCentral Connects