Forum Discussion
Restrict Access via HTTP referer
I'm attempting to restrict access to an application via HTTP REFERER. Using the example given by the dev team, I'm using something that looks like this:
when HTTP_REQUEST {
switch -glob [HTTP::header "Referer"] {
"https://SUB.DOMAIN.COM/*" {
Allow Request to go through...
}
"" {
HTTP::respond 200 content ""
}
default {
HTTP::redirect [HTTP::header "Referer"]
}
}
}
Unfortunately this isn't behaving as it should, and I'm not getting anything too helpful from the logs. Can you see anything glaringly wrong with this?
13 Replies
- Kevin_Stewart
Employee
Okay, so on initial request (open a new browser) and access the site, there would be no Referer header, so do you want it to show an empty page? Are you only expecting users to access this site linked from another site?
- insomniak_11745
Nimbostratus
Thanks for your reply Kevin!
Essentially I only want the VIP to be accessible from a particular subdomain. The client in question has an application that resides on its own subdomain, such as:
app1.DOMAIN.com app2.DOMAIN.com etc.
So, I want the Virtual Server in question to be accessible when a link is clicked on *.DOMAIN.COM, and inaccessible when referenced directly (by IP address). Also, an empty header being passed should be denied as well.
Does this make sense?
- Kevin_Stewart
Employee
Give this a shot:
when RULE_INIT { user-defined: enable/disable debug (1/0) set static::ref_debug 1 } when HTTP_REQUEST { if { not ( [HTTP::uri] equals "/favicon.ico" ) } { if { $static::ref_debug } { log local0. "Incoming referer: [HTTP::header Referer]" } switch -glob [string tolower [HTTP::header Referer]] { "http://*.mydomain.com*" { if { $static::ref_debug } { log local0. "From allowed referrer - allow" } return } "http://*.example.com*" { if { $static::ref_debug } { log local0. "local domain - allow" } return } default { if { $static::ref_debug } { log local0. "from disallowed referer - redirect" } HTTP::redirect [HTTP::header Referer] } } } }
I threw the favicon.ico check in there as it never seemed to carry a Referer header and was getting redirected unnecessarily. The trick here is that you have to catch and accept the Referer headers from both the remote site and the local site.
- hoolio
Cirrostratus
Also note that if a browser goes from https:// to http:// it will not send a Referrer header. So your blacklisted site could easily get around the iRule logic if they use https:// on their site.
http://tools.ietf.org/html/rfc2616section-15.1.3
Clients SHOULD NOT include a Referer header field in a (non-secure) HTTP request if the referring page was transferred with a secure protocol.
Aaron
- Kevin_Stewart
Employee
I would just add to Aaron's addition that, generally speaking, blocking access based on a Referer header is trivially surmountable. Aside from browsers not passing the Referer header going from HTTPS to HTTP, it's VERY easy to spoof the header.
- insomniak_11745
Nimbostratus
@hoolio - Yes, thank you for pointing this out. This is actually an issue with this particular implementation as we are going from https --> http. I'm looking into configuring the application (Etherpad) to use https instead of http.
@Kevin - I understand the concern with spoofing HTTP headers, however this particular implementation is not to address any security concerns. Rather, it's more of a forceful "training" of the end users to use the URL included in the application rather than accessing it directly.
Thank you everyone for your quick help!
- Sadorect_151355
Nimbostratus
This is exactly what I am trying to achieve with my application too. According to the config below:
when HTTP_REQUEST { switch -glob [HTTP::header "Referer"] { "http://click.bank.com/dashboard.php" { Allow Request to go through... if { [string tolower [HTTP::uri]] ends_with "/eod" } { pool BankAppPool member 10.10.1.51 8888 log local0. "Requested path - admin sent to App1" log local0. "clientIP:[IP::client_addr] accessed [HTTP::host][HTTP::uri]" HTTP::redirect "/forms/frmservlet?config=ref&serveruserparams=NLS_LANG=AMERICAN_AMERICA.AR8MSWIN1256&otherparams=P_WST_LAN_IND=1+P_BANKS_APP_URL=http://10.10.1.51:9001/banks" HTTP::redirect "http://10.10.1.51:9001/forms/frmservlet?config=ref&serveruserparams=NLS_LANG=AMERICAN_AMERICA.AR8MSWIN1256&otherparams=P_WST_LAN_IND=1+P_BANKS_APP_URL=http://10.10.1.51:9001/banks" } elseif { [string tolower [HTTP::uri]] ends_with "/" }{ log local0. "Requested path - distribute Round robin" HTTP::redirect "http://pam.bank.com:9001/forms/frmservlet?config=ref&serveruserparams=NLS_LANG=AMERICAN_AMERICA.AR8MSWIN1256&otherparams=P_WST_LAN_IND=1+P_BANKS_APP_URL=http://10.10.1.57:9001/banks" log local0. &8220;Requested path - banks" } } "" { HTTP::redirect "http://click.bank.com/index.php?resp_id=MLG" } default { HTTP::redirect "http://click.bank.com/index.php?resp_id=MLG" [HTTP::header "Referer"] } } }
The redirect is working very fine as defined but the application accepting the request for valid navigation fails to load. It just hangs indefinitely. It works fine without the referrer-based redirect but, once the referrer check is introduced, it doesn't load. Is there something I'm missing in the iRule definition?
- insomniak_11745
Nimbostratus
As a general question if anyone feels like chiming in, would there be a way to restrict access via iRule using something included in the URL itself? Something like:
index.php?http-referrer=VALUE
Or using some sort of authorized token, or the md5 hash of the originating site's URL?
- Arie
Altostratus
Have you considered using cookies? Either the app or the LTM can set/read them and they can cross from HTTP to HTTPS.
- insomniak_11745
Nimbostratus
Well, the main issue here is that I would like minimal to zero modifications needed to the application. Ideally, all of the restriction would be done on the F5. Is this possible to dictate in the LTM or would the application need to be modified to interpret data set by the LTM?
- Kevin_Stewart
Employee
It really depends on your overall requirement. Making sure that a user who accesses your site is coming from another site can be easy and insecure (Referer header), or very complex (auth tokens, auth protocols, etc.) and generally requires some coordination between the sites. Putting the Referer in the URI would make it easier to spoof, and adding an md5 hash doesn't really provide any security.
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