This article has two sections;
1. Introduction to HTTP Security response headers
2. Testing for the proper implementation of HTTP security response headers
Sec.1: Intro to HTTP Security response headers:
Whenever our browser requests data from a web site or web application, the application responds with the requested content along with HTTP response headers. These headers contain some information regarding the content, application server, also some directives to the browser regarding the handling of received content.
Security response headers were introduced a while back; These security directives can be included in the response headers, so that the browsers will treat the delivered content in a secure manner; thus making the web application more secure!
Implementation of HTTP security headers are relatively very easy. It does not need any code changes, just need some slight changes in configuration files such as .htaccess or web.config
In practice most of the developers just don’t care about these security headers. Simple tweaks to the response header values can gain more security rating in the real world scenarios. Most of the internet based vulnerability scanning tools and services rates and ranks web sites and applications, also based on security header implementation.
Some of the essential HTTP security headers are explained below with their recommended directives and values; along with various testing methods and services.
Use the recommended header values in mind while testing for security header implementation and mis-configuration.
X-XSS-Protection header sets the configuration for the default cross-site scripting filter in browsers. It will help to filter and block malicious script queries.
Recommended setting would be; X-XSS-Protection: 1; mode=block
This security header stops a browser from trying to MIME-sniff the content type and forces it to stick with the declared content-type.
Recommended value would be; X-Content-Type-Options: nosniff
This header value defines conditions for storing data in the browser and intermediate devices cache.
Recommended value would be; Cache-Control: no-cache
HTTP Strict-Transport-Security header is an excellent feature to support and strengthen the TLS implementation by getting the user agent to enforce the use of HTTPS. HSTS allows for a more effective implementation of TLS by ensuring all communication takes place over a secure transport layer on the client side.
Recommended value would be; Strict-Transport-Security: max-age=”max age value”; includeSubDomains; preload
https://hstspreload.org/ this URL will help to find out whether the target domain is listed in HSTS preload database of the browsers. If you are a developer, the same can be used to add your domain name.
I’ve written a blog post related to HSTS protected traffic interception using Firefox and Burp suite – https://abhijith.live/intercepting-hsts-protected-traffic-using-burp-suite-and-firefox/
As a security measurement, always white list approves sources using CSP
For example: Content-security-policy: default-src ‘self’
Supported directives of CSP is given below; Copied from OWASP
default-src : Define loading policy for all resources type in case of a resource type dedicated directive is not defined (fallback),
script-src : Define which scripts the protected resource can execute,
object-src : Define from where the protected resource can load plugins,
style-src : Define which styles (CSS) the user applies to the protected resource,
img-src : Define from where the protected resource can load images,
media-src : Define from where the protected resource can load video and audio,
frame-src : Define from where the protected resource can embed frames,
font-src : Define from where the protected resource can load fonts,
connect-src : Define which URIs the protected resource can load using script interfaces,
form-action : Define which URIs can be used as the action of HTML form elements,
sandbox : Specifies an HTML sandbox policy that the user agent applies to the protected resource,
script-nonce : Define script execution by requiring the presence of the specified nonce on script elements,
plugin-types : Define the set of plugins that can be invoked by the protected resource by limiting the types of resources that can be embedded,
reflected-xss : Instructs a user agent to activate or deactivate any heuristics used to filter or block reflected cross-site scripting attacks, equivalent to the effects of the non-standard X-XSS-Protection header,
report-uri : Specifies a URI to which the user agent sends reports about policy violation
Content-security-policy is very hard to test or analyze. Its damn complex and messy! The web service report-uri (https://report-uri.io/home/analyse) would be very helpful to evaluate CSP implemented on our target web application.
Refer the below screenshot:
This security header tells the browser whether you want to allow your site to be displayed in an iframe or not. Click-jacking attacks can be prevented by implementing proper X-Frame-Options headers.
There are three configuration strings for X-Frame-Options:
DENY : Deny option will protect a web page from loading using an iframe
SAMEORIGIN : This will let the page to load iframe from the same source as the parent web page.
ALLOW-FROM uri : This will allow the page to load iframes from a selected origin
Recommended value would be, X-Frame-Options: SAMEORIGIN
Referrer-Policy header controls what kind of information is being sent to other web sites, navigating from our web page. Internal information/URLs can be revealed because of this. Also this is how web sites identify, from where exactly their traffic is originating.
Refer the below screenshot: Someone tried to access my blog post from a link posted in Facebook, using a mobile phone.
The Referrer-Policy header has the following options/values:
empty value : does not set referrer policy
no-referrer : It will not send a referrer header to the target
no-referrer-when-downgrade : Will not send referrer header to target from HTTPS to HTTP connections
origin : The header value will be set as the origin URL
origin-when-cross-origin : It will send the complete URL to the same origin target and sends only the origin URL to other targets
same-origin : Shares the header only with same origin target URLs
strict-origin : This is same as orgin; But enforces HTTPS URLs
strict-origin-when-cross-origin : This is like origin-when-cross-origin; But will not send any referrer values to cross origin (HTTPS to HTTP)
unsafe-url : Browser will send the full URL to targets all the time
HTTP Public Key Pinning (HPKP):
Public-key-Pins or HPKP is another security response header, which provides certain information to the browsers, to make sure which SSL certificates it should accept from the web server. HPKP generates unique pins/fingerprints for certificates using cryptographic algorithms.
An example header will look as per the below screenshot:
To achieve an A+ score from securityheaders.io without HPKP implementation, please do visit test.securityheaders.io
The below URL can be used to analyze public-key-pins for a web application, just using their web address. https://report-uri.io/home/pkp_analyse
Anyway, its better to implement Public-Key-Pinning for highly secure/confidential web applications only. The very first thing is, Implementing HPKP can cause a lot of issues. For example, just imagine your SSL certificates are expired and you have installed a new SSL certificate for your application. The new pins will be different for the new SSL certificate but the browsers are taught to accept the old certificates only. It happens mostly because of “max-age” parameter.
Refer the below blog posts before implementing Public-Key-Pins for your web application. Or these links can also help you if you are facing some issues regarding HPKP configuration.
Is Public-Key-Pinning dead? – https://blog.qualys.com/ssllabs/2016/09/06/is-http-public-key-pinning-dead
Be Afraid Of HTTP Public Key Pinning (HPKP) – https://www.smashingmagazine.com/be-afraid-of-public-key-pinning/
Giving up on HPKP – https://scotthelme.co.uk/im-giving-up-on-hpkp/
This header includes the cookie creation and session management.
A cookie must contain, HTTPOnly and Secure flags
Sec.2: Testing for the proper implementation of HTTP security response headers:
We had a look at the basic and essential security headers for a web application. I’ve summarized some of the quick and effective testing methods for HTTP headers below. Keep in mind that, we need to understand about the recommended/secure implementation of headers before analyzing them.
1. Testing HTTP response headers using CURL:
This is the easiest way to test security headers. Just open up a console and fire Curl;
Curl will grab the headers for you within seconds. We need to use Curl with parameters I and L. I switch will tell curl to grab the head and L parameter will help to follow the redirects, if our target has any.
curl -I -L --url <target domain or IP>
2. Testing HTTP security headers with nmap script:
Nmap can be used to test and validate security headers very easily. We can leverage an nmap script named “http-security-headers”. Download it from this link: https://svn.nmap.org/nmap/scripts/http-security-headers.nse
nmap -p 443,80 --script http-security-headers <target IP or Domain>
3. Testing for HTTP security headers using securityheaders.io
Securityheaders.io is a web service created by Scott Helme , which can be used to test and rate the security headers of our web application.
Navigate to Securityheaders.io and enter the web site URL. That’s all we have to do for analyzing the HTTP headers. This web service displays detailed information regarding Security header implementation, and suggests which header should be added. Also dont forget to select “Follow redirects” checkbox before scanning. So that it will get the correct results from the redirected URL.
Refer the screenshot for a web site with F rating:
Securityheaders.io also displays the missing headers and how to fix them. Which makes them the perfect place for testing HTTP security headers.
Below screenshot is the header scanning result/rating for my blog, abhijith.live
4. Scanning for headers using Mozilla Observatory
Mozilla Observatory is a public project maintained by Mozilla. Observatory uses their own algorithms and scoring mechanisms to analyze security headers and implementation of web applications.
Observatory also uses various third party scanning tools and services to make the results more accurate. It offers various TLS and SSH scanning features as well.
Observatory also suggests what are the recommended to achieve a better score; thus better security! Refer the below screenshot
URL for Mozilla Observatory is, https://observatory.mozilla.org/ and the scoring methodology can be found in here – https://github.com/mozilla/http-observatory/blob/master/httpobs/docs/scoring.md
5. Testing headers using Burp suite OR any other proxy tool
This is relatively simple. It can be performed along with web application security testing without any effort. Just intercept the traffic and have a look at it yourself. And its better to have a good understanding about security headers and their recommended config values.
6. Testing header implementation using Headers Analyzer (Burp suite Plugin)
The plugin Headers Analyzer can be downloaded from BApp store. Jython is required for this burp plugin. Jython can be downloaded from here and more information regarding this plugin can be found here.
Personally I may not recommend this plugin, since burp suite itself is enough for analyzing the response header values. Anyway, this plugin makes it a little bit easier.
Headers analyzer can be configured as per the below screenshot:
This is quite simple burp plugin, which analyzes the headers passively, then displays the output as shown below.
I’ll keep updating this post with new headers, testing methods or any other new information:
Last updated : 02/Oct/2017