Used Kai's irule as a basis for one we needed. The conditions were a bit different where our determination of if/what value to return was based on the presence and contents of a query string value. In short, the query string value for 'CID' identifies a client for which we needed to respond with different X-Frame-Options header values based on whether they were framing us.
Configure a custom response for the X-Frame-Options header based on the CID in the URI query string.
Custom cid-specific settings are pulled from the 'xfo_client_overrides' list where the client cid
is the 'string' and the desired X-Frame-Options value the 'value'. Example: 12345678 := DENY
when HTTP_REQUEST {
set uri [string tolower [HTTP::uri]]
set qcid [URI::query $uri cid]
set ccid ([HTTP::cookie value "xcid"])
if {[info exists qcid] and $qcid ne ""} {
set cid [string trim $qcid "()"]
set setcookie 1
} elseif {[info exists ccid] and $ccid ne ""} {
set cid [string trim $ccid ")("]
} else {
set cid 0
}
}
when HTTP_RESPONSE {
if { [ class search xfo_client_overrides equals $cid ] } {
HTTP::header replace "X-Frame-Options" [class lookup $cid xfo_client_overrides]
}
if { [info exist setcookie] } {
HTTP::cookie insert name "xcid" value $cid path "/" version 1
HTTP::cookie secure "xcid" enable
HTTP::cookie httponly "xcid" enable
}
}
The value that is returned in the header is looked up from a 'xfo_client_overrides' string-based Data Group List. So basically there's a lookup table that matches the CID value (or subsequent xcid cookie value) to the value returned in the X-Frame-Options header.
So for example:
999991 := DENY
999992 := SAMEORIGIN
999993 := ALLOW-FROM https://www.somedomain.com
Since in our situation the CID query value goes away after the initial request, I set that value into a 'xcid' cookie so the information persists for the duration of the session. Should a new CID query value come in on the URI, that value would be used and the xcid cookie value updated.
This script does not permit for a default response were the CID not listed in 'xfo_client_overrides' or if the CID were absent altogether. This could be added relatively easily with an
else
on the first
if
condition in HTTP_RESPONSE (either be hard-coding in the script or by doing a lookup for a default value configured in 'xfo_client_overrides' as '0' or 'default' as in
default := SAMEORIGIN
). Haven't thought through the logic on this entirely but the answer is close if not quite right. The advantage to the default value in 'xfo_client_overrides' solution should be that one could choose to have a default or not based on whether one exists in the lookup table (though this would necessitate an
elseif
rather than an
else
I suppose).