Note that there is an ultra-modern protocol called HTTP / 2 – this protocol is significantly different from the classic HTTP (versions 1.0 and 1.1 or simply HTTP / 1). In the following, we only discuss classic HTTP,
In HTTP, client requests contain method identifiers that indicate how they are processed on the server side. So, a request with the GET method – corresponds to extracting the full document located at the specified address on the server. GET is commonly used to retrieve code from web pages.
The POST method, on the other hand, allows the client to upload some block of data to the server in a protocol-defined format. A typical way to use POST is to send web form data (for example, a questionnaire filled out on a website) to the server. Methods are denoted by plain text strings.
HTTP in Web Practice
Since the scenarios for using the HTTP protocol in the modern web are quite complex, HTTP requests and responses contain, in addition to method identifiers and document addresses, a lot of additional service information. The most famous example here is the User-Agent field, in which the client specifies its type, name, version. In particular, the User-Agent field allows the web server to determine the type of browser that sent the request. User-Agent in classic HTTP is a text string consisting of an identifier (actually, “User-Agent”) and a value, separated by a “:” character. Other HTTP headers are written in the same way.
Additional fields are transmitted by both the client and the server. All these fields are a combination of a text field name and a text value. It is these additional fields in the HTTP response of the server that are commonly called HTTP headers, and identifiers are used as names by which a particular header is referred to. For example, the browser type field is referred to as the “User-Agent HTTP header”.
As mentioned above, the HTTP protocol is a client-server protocol: the client sends requests, and the server fulfills them (if possible) and sends responses. The client, in a typical situation, is a browser, and the server is a web server. A modern website session includes many HTTP requests and HTTP responses, which can be sent either sequentially or in parallel.
The web server uses HTTP headers to convey to the client extended information about the server settings in the HTTP context, about the rules for processing HTTP connections accepted on the server side. Headers also allow you to send recommendations for further interaction with the server. The headers also contain other technical information about the connection, such as cookies used for authorization.
In other words, the set of HTTP headers of the server is a small text directory, with the help of which the client, in automatic mode, determines the scenario for further work with this web server.
Until the moment of the first connection with the server, the client, in general, cannot find out what additional parameters will be passed by the server in the headers, therefore, it is guided by the default settings; however, after the server’s response to the first request, the client has the opportunity to adjust subsequent requests in accordance with the server’s recommendations, as well as change the way the data just received from the server is interpreted. The latter aspect, in particular, allows you to block large classes of attacks directed at user browser sessions, because the browser can transform and filter the data before it renders the page or its element to the user.
The secure version of HTTP – HTTPS – uses TLS (Transport Layer Security protocol) to secure information. HTTPS, from the point of view of the HTTP part, works completely similar to the open version, however, since the channel is protected by cryptographic methods, the client and server receive authentication mechanisms and the integrity of the transmitted data. This validation takes place outside of HTTP. HTTPS greatly enhances the meaning of HTTP headers, and many of these headers are only relevant in the case of HTTPS.
So, HTTP headers are information presented in text format about various parameters of an HTTP session. Headers allow the web server to inform the browser about the settings that should be applied for a given address and a given site. These settings can apply to both the current session and subsequent ones. Consider an elementary example of an HTTP request and response (with headers):
Request (this is a GET request, it is sent by the client to the server address, in this case it means retrieving the index document from the root directory on the server, “HTTP/1.1” indicates the version used by the client):
GET / HTTP/1.1
(Here Host: is the _request_ HTTP service header indicating the name of the server the client is accessing: www.google.com in this case.)
Response (HTTP response with status code 200 indicating success – the status code is on the first line):
HTTP/1.1 200 OK
Date: Mon, 22 Jul 2022 18:33:48 GMT
Here you need to pay attention to the two bottom lines, which begin with the designations X-XSS-Protection and X-Frame-Options. These are examples of _server_ HTTP security headers.
Some of the HTTP server headers are designed to improve session security when the browser is working with websites. These headers are called “security headers”. Historically, they have been introduced gradually as a response to emerging new attack vectors. Security headers allow the administrator of a web resource to pass to the browser information that describes the rules and policies recommended by the administrator for the client (browser) to work with the website.
Header support and interpretation varies in detail from browser to browser (and across browser versions of the same line), but the basic principles are the same across all modern browsers.
Let’s go back to the two headings from the example above.
This header defines how the browser should display the corresponding page in the context of an embedded display. For example, in HTML there is the concept of a “frame” (the <frame> and <iframe> tags). “Frame” allows you to transparently embed a web page corresponding to one server into some scope within a page related to another server. This is how ads are displayed on websites: a visual block is allocated on the main page – usually a fixed size – and inside this block the browser shows content received from a completely different site (and server).
However, using the same “frames” construction, the content of one website can be embedded in the page of another, against the wishes of the owner of the first site. This not only allows attackers to pass off someone else’s content as their own by transparently replacing the visible page address, but also mislead the user as to which site actually performs certain actions – for example, the user clicks on some image. The X-Frame-Options header, if supported by the browser, counteracts all of these annoyances.
For X-Frame-Options, in the modern version, two values are allowed – DENY and SAMEORIGIN. The title is read by the browser and if DENY is specified as the value, then the browser will not show this page inside the “frame”. SAMEORIGIN – a softer version of the rule that allows pages to be shown in “frames” if the “enclosing” page belongs to the same source (however, the details of how it is determined that the source of two pages is common are rather vague, but to understand the principle, we can assume that this is determined by the matching domain name).
Let’s consider the mechanism of applying headers in detail, using the X-Frame-Options processing by the browser as an example. Suppose the browser loads a page with the address http://test.com/page/. The HTML code for this page contains an <iframe> construct that creates a “frame”. The scheme implies specifying the address of a web resource, the page of which is displayed inside the “frame”. Let this address be http://example.com/form/. Having loaded a page from the test.com site and found a link to http://example.com/form/ in its HTML code, the browser will execute the corresponding GET request to the server under the example.com domain and receive HTTP headers as part of the response.
If among these headers (generated by the example.com server) the string “X-Frame-Options: DENY” is found, the browser will ignore the <iframe> options and not display the http://example page.com/form/ inside “frame”. The SAMEORIGIN value is used if the “frames” mechanism is used by the developer directly within a specific web resource, but it is required that the ability to use “frames” does not extend beyond this resource. X-Frame-Options governs not only <iframe> and <frame> constructs, but also <embed> and <object> – the same principles apply.
This header controls the inclusion of the “cross-site scripting” filter on the browser side (the header is considered obsolete, but is still recommended for use, as it allows you to protect legacy browsers). “Cross-site scripting” (Cross-site scripting – XSS) is a common tool for building attacks that are based on the introduction of additional code and the imposition of specially generated HTTP requests in browser sessions related to other websites, and not to the site source.
The basic logic of XSS attacks is that the imposed script or request is executed in the context of another session. So, the user opens in the browser a web page of some site P, which contains a specially prepared script that forces the browser to perform, in the context of a saved session, request to site Q; since the saved session may contain active authorization for site Q, the request will be executed with the appropriate rights on site Q, as if the user himself opened this site in a browser and, for example, sent some message.
The X-XSS-Protection header is not supported by all modern browsers, it is being replaced by another header that allows you to solve the same tasks, but not only them. This is Content-Security-Policy.
Content-Security-Policy (CSP) is the most directive and option-rich security header. It allows the server administrator to set policies that determine how the browser loads various resources and objects related to a given address (or page). For example, the policies set by Content-Security-Policy determine how and from which servers the browser can download scripts, image files, additional fonts, plugins, and other page elements. But CSP is not limited to this – there are a lot of options and directives. They are divided into five sets: boot directives, document directives, navigation directives, informing directives, and other directives. Any detailed consideration of the components of all these sets will require a separate article, so we will only briefly describe the sets of directives.
CSP document directives govern the context in which the entire web page is interpreted. For example, the plugin-types directive limits the set of plugin types allowed for a given document context, in particular, using this directive, you can allow the loading and execution of Flash objects.
With the help of CSP navigation directives, restrictions are set on the addresses of other documents and servers that a user can access in one way or another in a given page context. A request means, for example, sending a web form – that is, the corresponding form-action directive limits the list of addresses to which the browser will send the data of the web form fields.
CSP alert directives allow you to specify a special address (URL) to which the browser will send a typical report about violations of the policies defined in the CSP. This address is needed so that the server administrator can know that some violation or failure has occurred on the client side – as this may be a sign of an attack.
The set of other directives includes several that are not included in other sets – for example, the upgrade-insecure-requests directive, which instructs the browser to automatically replace “insecure” requests (that is, those for which the HTTP protocol is specified) that occur in the context of the document with secure (HTTPS ).
Content-Security-Policy headers are a well-developed tool for controlling the attack surface on large and complex web projects that also use user-uploaded content. For example, using CSP tools, you can disable the execution of external scripts for all sources except verified ones, while verified ones remain external: they may include contextual advertising providers or web analytics systems.
Referrer-Policy- refers to a different type of security headers: this header defines what data the browser can send in the HTTP Referer header, which is used, for example, when the browser handles “following a link”. So, Referer can contain the address of the previous resource from which the user moved to this one. That is, the server serving the target resource sees where the user came from. To reduce information leaks through this header, the list of data that can be transferred in it is regulated by the Referrer-Policy security header. For example, “Referrer-Policy: origin” – determines that in the Referer field the browser sends only a part of the full address (URL) that determines the protocol and server name: when going from the page https://test.com/from.html to the Referer browser will write only https://test.com/. (Browsers have other mechanisms to restrict Referer.)
The X-Content-Type-Options header instructs the browser to strictly follow the list of content type identifiers specified in the Content-Type header field. It is assumed that the type of data (or content) transmitted by the server in the HTTP response is correctly indicated in the HTTP header.
However, in controversial cases, browsers can use their own flexible algorithms for determining the type of content based on the data itself. This helps, for example, to correctly process image files that are erroneously transferred with the wrong type. The X-Content-Type-Options header allows you to explicitly prevent the browser from using these algorithms. The header can block data spoofing attacks, in which the browser executes malicious code due to a type misinterpretation.
The Strict-Transport-Security header is especially important. It tells the browser to use only secure HTTPS when connecting to this web resource. This header counteracts attacks that use a decrease in the level of protection, namely, the replacement of the protocol specified in the resource address from https:// to http://. Such a replacement can be done in various ways, including by directly interfering with insecure HTTP traffic. At the same time, the user may not notice the difference in the type of connection, and the absence of TLS allows the address to be spoofed, keeping the familiar domain name in the browser’s address bar.
The Public-Key-Pins header is a mechanism to pass to the client the server’s TLS cryptographic key fingerprints that are valid for the server. This is known from other secure protocols (eg SSH) for remembering keys “at first meeting”. The method makes it possible to detect substitution in the future, even if such substitution is carried out with the participation of a trusted certification authority. This header was previously fully supported by common browsers, in particular, Mozilla Firefox, but, unfortunately, it is now practically withdrawn from support (in current versions of Firefox, you need to enable support manually, and correct operation is not guaranteed).
The last two headers mentioned are particularly sensitive to the protocol being used – HTTP or HTTPS. The fact is that in the case of an “insecure” version of HTTP, an active attacker can remove or replace any headers, respectively, it makes no sense to send headers that control the use of TLS: they simply may not reach the client, and the user will not notice anything.
At the same time, a single transmission of the header over a trusted channel, via HTTPS, allows the browser to remember the settings – since in this case the source server is authenticated, and the content of the headers is also trusted. The same observation applies to other headers: if the attack model involves the active substitution of any traffic, then none of the headers can be taken into account when transmitted over HTTP.
Nonetheless, more often, a weaker model is used, in which an attacker can only replace some fragments on web pages (usually on a server) and transmit arbitrary information from a controlled server in response to browser requests. In this model, a number of HTTP security headers also make sense for the open version (HTTP), such as Content-Security-Policy and X-Frame-Options.
We’ve covered the most important and common HTTP security headers. These headers provide flexible tools that can significantly increase the security of the use of web resources by users. Note that adding headers to the web server configuration in most cases is an elementary operation, which even a novice system administrator can perform.