What are HTTP headers?
HTTP headers are a list of key-value pairs which are sent along with HTTP requests and responses.
Let us take an example with below request(left) and response(right):
In the above snapshot, we can see that we have an HTTP request being sent to Host.
Along with that request/response, we see Key:Value pairs, these are HTTP Headers.
These look similar to YAML format.
HTTP headers let the client and the server pass additional information with an HTTP request or response. 1
Security Headers
Security Headers are HTTP headers that can be used to enhance the security of an application.
Having these can stop common attacks such as code injection, cross-site scripting attacks, and clickjacking.
Below is a list of commonly used HTTP Security Headers:
X-Frame-OptionsAccess-Control-Allow-OriginStrict-Transport-SecurityContent-Type and X-Content-Type-OptionsReferer and Referrer-PolicySet-CookieCache-ControlContent-Security-Policy
X-Frame-Options
X-Frame-Optionsis a response header.- It instructs the browser whether the page being fetched can be displayed inside an
<iframe>,<embed>,<frame>&<object>. - This improves protection against clickjacking. 2
- A new implementation
CSP frame-ancestorsis used more recently.
IfCSP frame-ancestorsis presentX-Frame-Optionswill be ignored.
Example:
| Attribute | Usage |
|---|---|
DENY | Page should not be displayed in a frame. |
SAMEORIGIN | Page can be displayed only if the origin is the same as the page itself. For example, siteA.com can have siteA.com’s frames embedded but siteB.com cannot display a frame of siteA.com within itself. |
ALLOW-FROM _uri_ |
Access-Control-Allow-Origin
Access-Control-Allow-Originis a response header- It instructs the browser whether the response can be accessed(shared to Origin by the browser) by the Origin which has requested the resource.
- When
siteX.comtries to fetch content fromsiteY.com, the browser sends anOriginheader which contains the site which is requesting the resource, in this case,siteX.com. This is a normal Cross-Origin request. - By default
siteX.comcannot accesssiteY.com’s resources unlesssiteY.comopens it by using theAccess-Control-Allow-Originheader. - Thus, for each page/resource that
siteY.compermitssiteX.comto access it should include a reponse header:which will letAccess-Control-Allow-Origin: https://siteX.comsiteX.comaccess resources fromsiteY.com
| Value | Usage | Example |
|---|---|---|
* | Allows accessing the resouce from any origin | Access-Control-Allow-Origin: * |
<origin> | Allows accessing the resouce from specified origin. | Access-Control-Allow-Origin: https://adityatelange.in |
null | Allows accessing the resources from any origin | Access-Control-Allow-Origin: null |
Note: When specifying an origin, only one origin can be set in the value. For example:
Access-Control-Allow-Origin: https://adityatelange.in https://www.adityatelange.in Access-Control-Allow-Origin: *.adityatelange.inare invalid values!
- To counter the above issue, the
Access-Control-Allow-Originhas to be set to*for requests not containing anyOriginheader. - For requests containing an
originheader, theoriginheader should be checked against an allow-list of origins stored which can access the resource and then added back to the response as a value toAccess-Control-Allow-Origin. Along with this, aVaryresponse header has to be sent with a value asOriginAccess-Control-Allow-Origin: https://adityatelange.in Vary: Origin
Strict-Transport-Security
- Strict-Transport-Security is a response header.
- Popularly known as
HSTS: HTTP Strict Transport Security. - It instructs that the website should be accessed only using HTTPS.
- Browsers automatically convert any further attempts to connect to the site from HTTP to HTTPS.
- This helps prevent Man-In-The-Middle(MITM) attack.
- Google maintains an HSTS preload service which recommends setting value as per the below example. 3
Usually
max-ageis set to63072000or 2 years.
Strict-Transport-Security: max-age=<expire-time-in-seconds>; includeSubDomains, preload
Content-Type and X-Content-Type-Options
X-Content-Type-Optionsis a response header.- It instructs the browser that the MIME type value set in the
Content-Typeheader should only be used and not changed by using MIME type sniffing 4 (guessing MIME type by parsing the bytes of the resource, sometimes called magic-bytes) - Using strict type checking will ensure that the browser does not render/process unidentified content as valid content by guessing the file type.
- For example, if the app has an upload functionality that lets users upload images only of type PNG, the
Content-Typeheader will have the value set asimage/png, thus even after uploading a non-PNG file (suppose PHP) will only be processed asimage/pngby the browser.
X-Content-Type-Options: nosniff
Referer and Referrer-Policy
Refereris a request header.Referrer-Policyis a response header.Refererheader indicates the origin/URL from which the request was made.Referrer-Policyindicates what part or URL should be made available in theRefererheader.- So, if we set
Referrer-Policytosame-origin, it means that theRefererfield will only be included in requests made to the same origin as the current page. Referrer-Policywill be set by the web-app developer while theRefererheader will be set by the browser following the policy stated inReferrer-Policy.
Basic Syntax:
Referrer-Policy: {policy-directive};
Policy Directives for Referrer-Policy:
| Attribute | Value | Description |
|---|---|---|
no-referrer | - | This instructs the browser to not set Referer header on any request. |
no-referrer-when-downgrade | - | This instructs the browser to set the Referer header on all requests unless the request is made from a secure HTTPS page to an insecure HTTP page. |
same-origin | - | This instructs the browser to set the Referer header on requests made to the same origin as the current page. |
origin | - | This instructs the browser to replace the Referer header with the origin of the current page, and should only be included in requests made to the same origin as the current page. |
strict-origin | - | This instructs the browser to replace the Referer header with the origin of the current page, and should only be included in requests made to the same origin as the current page unless the request is made from a secure HTTPS page to an insecure HTTP page. |
Referer vs Origin:
Refereris similar to theOriginheader we saw in earlier parts of this blog, but it also includes a path along with the origin.Refereris typically used to identify the webpage that is linked to the resource being requested whileOriginis used to identify the source of the request itself.- That means
Referertells you which page the user was on before they made the request, while theOrigintells you which website or application made the request.
Set-Cookie
Set-Cookieis a response header.- It is used to send a cookie(s) from the server to the browser.
- A cookie is a small string that is used to identify a user/device.
- A client will then store this data and send it in subsequent requests through the
Cookieheader.
Basic Syntax:
Set-Cookie: {cookie-name}={cookie-value}
Attributes:
Of these Secure, SameSite, Domain, Path, and HttpOnly are considered important when it comes to securing an application.
Set-Cookie: {cookie-name}={cookie-value}; Domain={domain-value}; Path={path-value}; Secure; HttpOnly; SameSite={samesite-value}
Note: Remember setting multiple cookies separately (not comma
,separated) for example:Set-Cookie: c_one=val_one; Domain=abc.xyz; Secure; HttpOnly; SameSite=Strict Set-Cookie: c_two=val_two; Domain=abc.xyz; Secure; HttpOnly; SameSite=Lax
Let’s look into what each of the attributes does.
| Attribute | Value | Description |
|---|---|---|
Secure | - | This instructs the browser to send the cookie over a secure channel only, that is over an HTTPS connection. |
SameSite | Strict | When operating in Strict mode the browser will not send the cookie on any cross-origin request & will only be sent in a first-party context. |
| 〃 | Lax | When operating in Lax mode the browser will not send the cookie on normal cross-site subrequests but will send the cookie when a user is navigating to the origin site (when the reader follows the link) |
| 〃 | None | When operating in None mode the browser will send the cookie in all contexts, in responses to both first-party and cross-origin requests |
HttpOnly | - | This instructs the browser not to share the cookie with JavaScript. This will ensure cookies are sent only with HTTP requests. |
Domain | (Domain value ex. siteA.com) | This instructs the browser, for which all hosts the cookie should be sent. |
Path | (Path Value ex. /admin) | This instructs the browser to send the cookie only if the mentioned URL path exists in the requested URL. |
Cache-Control
Cache-Controlis both request and response header.- It holds instructions about caching content.
- It is important to prevent certain information from getting cached, which can leave behind sensitive information for other users to find and exploit, such as passwords or credit card numbers. 5
- A web app should use an appropriate caching policy that specifies the extent to which each web page and associated form fields should be cached.
- There are mainly 2 types of caches:
- Private Cache
- Public Cache/Shared Cache
Basic Syntax:
Cache-Control: {attribute}={value}; {attribute}={value}
Policy Directives:
| Attribute | Value | Description |
|---|---|---|
max-age | (N, in seconds ex. 604800) | This instructs the browser that it can reuse the response for N seconds. Ex. Cache-Control: max-age=604800 |
no-cache | - | This instructs the browser that it can store responses in caches, but the response must be validated with the origin server before each reuse. Ex. Cache-Control: no-cache |
no-store | - | This instructs the browser that any cache (private or shared) should not be stored. Ex. Cache-Control: no-store |
public | - | This instructs the browser that cached response can be stored in the public cache. Ex. Cache-Control: public. As a result, responses containing authorization and authentication tokens should not use this attribute. |
private | - | This instructs the browser that cached response can be stored in the private cache that is the browser cache. Ex. Cache-Control: private. |
Content-Security-Policy
Content-Security-PolicyorCSPis a response header.- It is used to specify a whitelist of allowed sources of content for a web page.
- By far it can be said that CSP is the most powerful security header out of all the headers discussed above.
- If the CSP policy is set properly, many attacks can be mitigated on the browser/client side.
- CSP header is made up of one or more directives which are separated by a semicolon
;. - It is important to carefully consider the allowed sources of content for a page and test the CSP configuration to ensure that it does not break the functionality of the page.
- Tool to generate CSP: Report URI: Generate your Content Security Policy
Basic Syntax:
Content-Security-Policy: {policy-directive}; {policy-directive}
Policy Directives: 6
| Attribute | Value | Description |
|---|---|---|
default-src | (N, in seconds ex. 604800) | - This defines the default policy for fetching any resource. - This is often a fallback for other directives. - That means if we specify default-src but do not specify other directives the values set for default-src will be used as a fallback.- Few directives that do not fall back to default-src are base-uri, frame-ancestors, form-action, block-all-mixed-content, upgrade-insecure-requests. |
script-src | script-src {source}script-src 'unsafe-inline'script-src 'unsafe-eval' | It is used to specify the allowed sources of JavaScript for a page. |
style-src | style-src {source}style-src 'unsafe-inline' | It is used to specify the allowed sources of CSS for a page. |
img-src | img-src {source} {source} | It is used to specify the allowed sources of images for a page. |
font-src | font-src {source} {source} | It is used to specify the allowed sources of fonts for a page. |
connect-src | connect-src {source} {source} | It is used to specify the allowed sources for network connections, such as WebSockets and XMLHttpRequests. |
media-src | media-src {source} {source} | It is used to specify the allowed sources of audio and video for a page. |
object-src | object-src {source} {source} | It is used to specify the allowed sources of plugins, such as Flash and Java. |
Note:
{source}can hold values:
-'self': Used as it is, denotes the origin from which the document is being served.
-scheme-type: Includes schemes such ashttp:,https:,data:,blob:.
-host: Includes hostnames or IP addresses with ports, like*.adityatelange.in,http://*.adityatelange.in:8080.
How do we define a good starter CSP Policy?
- A good starting point for CSP policy is to define the scope of the policy.
- Listing out the domains and subdomains which are necessary to make the application function is necessary.
- The types of content which should be allowed to be loaded should be noted.
- It is a good idea to include a
default-srcdirective. - The security implications should be thought about such as
unsafe-inlineandunsafe-evalwhich are underscript-src. - It’s also important to regularly review and update the CSP to ensure that it does not break the site’s functionality as well as continues to provide adequate protection against security threats.