Forum Discussion
Applying lowercase iRule to HTTPS virtual server?
Hi,
For SEO reasons, I need to apply force all HTTP requests to my site to be lowercase.
The Big-IP configuration for the site is a HTTP virtual server and a HTTPS virtual server (with a client SSL profile).
I currently have this iRule below on the HTTP virtual server and this works perfectly.
when HTTP_REQUEST {
if { [string tolower [HTTP::host]] eq "mysitename.com" } then {
HTTP::respond 301 noserver Location "https://www.mysitename.com[string tolower [HTTP::uri]]"
} else {
HTTP::respond 301 noserver Location "https://[getfield [HTTP::host] ":" 1][string tolower [HTTP::uri]]"
}
}
This iRule correctly forces HTTP traffic to HTTPS with a 301 response code and forces the URI's to lowercase.
E.g. http://www.sitename.com/WHATEVER gets converted to https://www.sitename.com/whatever
So this is all good.
However my problem is that I can't work out how to do the same lowercase rule for the HTTPS virtual server connections.
I currently have this iRule below applied to the HTTPS virtual server and nothing is being converted to lowercase.
when HTTP_REQUEST {
if { [string tolower [HTTP::host]] starts_with "mysitename.com" } {
HTTP::respond 301 noserver Location "https://www.mysitename.com[string tolower [HTTP::uri]]"
}
}
E.g. https://www.sitename.com/WHATEVER remains as https://www.sitename.com/WHATEVER
Is there a way to force lowercase to the HTTPS virtual server as well?
Any advice would be appreciated.
Thanks in advance!
6 Replies
Do you have a clientside SSL profile enabled?
If the F5 isn't doing SSL offload or SSL bridging you won't be able to run any HTTP irules to manipulate the data. You will need a HTTP profile as well, but you probably won't be able to attach the iRule without that.
- Stanislas_Piro2
Cumulonimbus
Hi,
To redirect only when string is not lower case, you can use the condition
if {[ set uri [string tolower [HTTP::uri]]] ne [HTTP::uri]} { HTTP::respond 301 noserver Location $uri } - Hectorm
Nimbostratus
here is another Irule to do this
when HTTP_REQUEST { # pool_group1 is the pool name for this virtual server set Vuri [ string tolower [HTTP::uri]] set Vheader [string tolower [HTTP::host]] set Poolmember1 [active_members pool_group1] set Default_site www.mysitename.com switch $Vheader { www.mysitename.com { if { [HTTP::uri] ne $Vuri } { [HTTP::uri] $Vuri } else { pool pool_group1 } } default { HTTP::redirect "https://$Default_site$Vuri"} } } - 1000blocks
Nimbostratus
Ok, looks like I have a working solution now.
Thanks Stanislas - it's basically your rule blended into with my existing redirection rule.
So the lowercasing happens as planned, but also every HTTP/HTTPS/WWW/non-WWW combination still gets detected and 301 redirected too.
Just tested all 10 possible combinations for a page and all good so far.
- mysitename.com/page (without HTTP/HTTPS/WWW) --> 301 redirect --> https://www.mysitename.com/page
- mysitename.com/PAGE (without HTTP/HTTPS/WWW) --> 301 redirect --> https://www.mysitename.com/page
- http://mysitename.com/page --> 301 redirect --> https://www.mysitename.com/page
- http://mysitename.com/PAGE --> 301 redirect --> https://www.mysitename.com/page
- http://www.mysitename.com/page --> 301 redirect --> https://www.mysitename.com/page
- http://www.mysitename.com/PAGE --> 301 redirect --> https://www.mysitename.com/page
- https://mysitename.com/page --> 301 redirect --> https://www.mysitename.com/page
- https://mysitename.com/PAGE --> 301 redirect --> https://www.mysitename.com/page
- https://www.mysitename.com/page --> HTTP/200 --> https://www.mysitename.com/page
- https://www.mysitename.com/PAGE --> 301 redirect --> https://www.mysitename.com/page
Working iRule 1
when HTTP_REQUEST { if {[string tolower [HTTP::host]] starts_with "www.mysitename.com" && [string match {*[A-Z]*} [HTTP::uri]]}{ HTTP::respond 301 noserver Location "https://www.mysitename.com[string tolower [HTTP::uri]]" } elseif {[string tolower [HTTP::host]] starts_with "mysitename.com" && [string match {*[A-Z]*} [HTTP::uri]]}{ HTTP::respond 301 noserver Location "https://www.mysitename.com[string tolower [HTTP::uri]]" } elseif {[string tolower [HTTP::host]] starts_with "mysitename.com" } { HTTP::respond 301 noserver Location "https://www.mysitename.com[string tolower [HTTP::uri]]" } }I'm going to continue to test, but looks good so far.
If anyone can see any ways that I can optimize this rule and trim some fat off it, please let me know.
Thanks for everyone's input on this post... much appreciated.
Hi 1000blocks,
you may take a look to the two iRules below. Both iRules are using a very fast code path to identify the "good" requests (should be >90% of the total request).
In addition both iRules are not [string tolower] the entire [HTTP::uri] string, since this approach may break certain applications. Both iRules will therefor [string tolower] only the [HTTP::host] and/or [HTTP::path] information, while keeping possible [HTTP::query] information in the original case.
iRule1: If is the only sitename served by the virtual server.
when HTTP_REQUEST { if { [string tolower "[HTTP::host][HTTP::path]"] equals "www.mysitename.com[HTTP::path]" } then { Allow the request to pass. Should be >90% of the requests. return } Wrong host or mixed case URL requested. if { [HTTP::query] ne "" } then { HTTP::respond 301 noserver Location "https://www.mysitename.com[string tolower [HTTP::path]]?[HTTP::query]" } else { HTTP::respond 301 noserver Location "https://www.mysitename.com[string tolower [HTTP::path]]" } }iRule2: If multiple sitenames are served by the virtual server.
when HTTP_REQUEST { switch -glob -- [string tolower [HTTP::host]] { "www.mysitename.com" { if { [string tolower [HTTP::path]] equals [HTTP::path] } then { Allow the request to pass... } else { if { [HTTP::query] ne "" } then { HTTP::respond 301 noserver Location "https://www.mysitename.com[string tolower [HTTP::path]]?[HTTP::query]" } else { HTTP::respond 301 noserver Location "https://www.mysitename.com[string tolower [HTTP::path]]" } } } "*mysitename.com*" { if { [HTTP::query] ne "" } then { HTTP::respond 301 noserver Location "https://www.mysitename.com[string tolower [HTTP::path]]?[HTTP::query]" } else { HTTP::respond 301 noserver Location "https://www.mysitename.com[string tolower [HTTP::path]]" } } "www.mysitename2.com" { if { [string tolower [HTTP::path]] equals [HTTP::path] } then { Allow the request to pass... } else { if { [HTTP::query] ne "" } then { HTTP::respond 301 noserver Location "https://www.mysitename2.com[string tolower [HTTP::path]]?[HTTP::query]" } else { HTTP::respond 301 noserver Location "https://www.mysitename2.com[string tolower [HTTP::path]]" } } } "*mysitename2.com*" { if { [HTTP::query] ne "" } then { HTTP::respond 301 noserver Location "https://www.mysitename2.com[string tolower [HTTP::path]]?[HTTP::query]" } else { HTTP::respond 301 noserver Location "https://www.mysitename2.com[string tolower [HTTP::path]]" } } default { Further/Unknown HOST-names... } } }Cheers, Kai
- Stanislas_Piro2
Cumulonimbus
Hi,
can you try this irule:
when HTTP_REQUEST { Manage HTTP / HTTPS and host values switch -glob -- [string tolower [HTTP::host]] { "mysitename.com" - "mysitename2.com" { set RedirLocation "https://www.[string tolower [HTTP::host]]" } "www.mysitename.com" - "www.mysitename2.com" { if {[TCP::local_port] equals 80} { set RedirLocation "https://[string tolower [HTTP::host]]" } else { set RedirLocation "" } } default { set RedirLocation "" } } Manage Path values if {[ set path [string tolower [HTTP::path]]] ne [HTTP::path]} { Convert path to lowercase to be used in redirect HTTP::path $path append RedirLocation [HTTP::uri] } else { append RedirLocation [HTTP::uri] } redirect if Host, protocol or path require redirect if {$RedirLocation ne [HTTP::uri]} { HTTP::respond 301 noserver Location $RedirLocation } }this irule check port, hostname and path values to create a variable RedirLocation with redirect URL (relative if host and scheme are unchanged, absolute else)
Help guide the future of your DevCentral Community!
What tools do you use to collaborate? (1min - anonymous)Recent Discussions
Related Content
* 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
