Appendix A. HTTP Quick Reference

Everything Started with Hypertext

The term hypertext was first  defined in 1965 by Ted Nelson, as text containing links to other text. The World Wide Web Consortium defines hypertext as “text that is not constrained to be linear.”

Generally speaking, we can think of hypertext as text displayed on electronic devices that references or links to other text.

The term hypermedia is an extension of this term. Generally speaking, hypermedia means hypertext that includes images, videos, and sounds. Ted Nelson was again the first to use the term.

REST is an architectural style introduced by Roy Thomas Fielding in 2000, which has been at the core of web design and development ever since.

REST actually defines the architecture of the Web: the way clients and servers communicate on the Web nowadays is dictated by REST principles.

REST principles emphasize scalability, both of components and of interactions between them. REST advocates for generality of interfaces and protocols and independent deployment of components. Furthermore, REST architectures make use of intermediary blocks, to reduce latency, enforce security, or simply encapsulate legacy systems.

Ted Nelson’s idea of hypertext was a little bit different from what we know today. He envisioned the possibility not only of tracking links, but also of versioning of documents. His vision was translated into Xanadu, a software system that was meant to be a universal library (like Wikipedia), a worldwide hypertext publishing tool, and a means for resolving copyright issues, as well as a forum for discussion and debate.

Xanadu was meant to provide most of the services that we can find nowadays on the Web in a single application; its ultimate purpose was to eliminate ignorance and misunderstanding, and to fix politics and communications. Xanadu was supposed to change the world for the better. Instead, the project went many times to the brink of bankruptcy and became one of the biggest vaporware stories in the history of the Internet.

The project has been developed and redeveloped but never released, although a working prototype is available.

While Xanadu was being rewritten and redesigned, the Web developed into a distributed hypermedia system, thanks to the collective effort of numerous cooperative projects and technological companies.

The Web consumes and generates enormous quantities of data, as a consequence of the constant interchange of information between users, client software, and services. These streams of data have often been referred to as hyperdata, or in other words interconnected data snippets that could therefore be explored.

Hyperdata represents the evolution of the Web as we now know it. When Tim Berners-Lee envisioned the Semantic Web in 2001, the Web of Data was described as a framework where autonomous agents could access structured information and conduct automated reasoning. These agents can be imagined as interconnected services accessing resources through a set of protocols or interfaces.

APIs can provide such interfaces by specifying how software components can interact with one another through one or more protocols. When a request is sent to a certain service through an API, one or more data objects are streamed through the network as a reply. This reply is expressed in a format that can be parsed and interpreted.

A hypermedia API would additionally specify links between the data objects returned, and a hypermedia browser would be able to explore the resulting flow of information just as a web browser can navigate through the hyperlinks in a web page.

From this point of view the “Web of Data,” as the future evolution of the Web has already been defined, does not present too many innovative concepts. We have been surfing websites and using web apps for many years now, and the idea of what hypertext is and how hypertext documents can be explored through the links that interconnect them has almost become intuitive.

This appendix provides some basic information about the HTTP protocol—the protocol that makes the Web, hypertext, and hypermedia possible—that can serve as a quick reference when you’re using this book. While our aim in the opening chapters of the book was to get up and running with Rails quickly, the more theoretical information you’ll find here will give you a deeper understanding of how things work behind the scenes.

Creating an HTTP Server in Ruby, Quickly

Before diving into the HTTP protocol, let’s try to grasp the basics. When the browser sends an HTTP request, a TCP socket connection is opened to website.com on port 80. The server accepts the connection and opens a socket for bidirectional communication. When the connection is established, the HTTP client sends an HTTP request:

GET /index.html HTTP/1.1 
User-Agent: MyBrowser/1.0 
Host: website.com 
Accept: */*

The server parses the request. The first line defines the HTTP method (GET, in this case), the Request-URI (/index.html), and the HTTP protocol version (1.1).

The following line defines the request headers, consisting of key/value pairs separated by a colon (:).

Using the same connection, the server answers the request with the content of the requested file:

HTTP/1.1 200 OK 
Content-Type: text/html
Content-Length: 145
Connection: close 
<!DOCTYPE html>
<html>
<head>
  <title>Hello HTTP</title>
</head>
<body>
  <h1>HELLO WORLD</h1>
  <p>My first HTTP request.</p>
</body>
</html>

You can quickly try this out with this one-liner Ruby script:

$ ruby -rwebrick -e'WEBrick::HTTPServer.new(:Port => 3000, 
  :DocumentRoot => Dir.pwd).start'

The web server will run on 127.0.0.1 on port 3000.

We can now create a simple HTML document so that we can request it from the server:

<!DOCTYPE html>
<html>
<head>
  <title>Hello HTTP</title>
</head>
<body>
  <h1>HELLO WORLD</h1>
  <p>My first HTTP request.</p>
</body>
</html>

To try this out, we can use telnet:

$ telnet 127.0.0.1 3000

We will get the command prompt:

Trying 127.0.0.1...
Connected to localhost.
Escape character is '^]'.

At which point we can request the index page:

GET /

We will then receive the HTML document in response, and the server will close the connection.

WEBrick

WEBrick is an HTTP server toolkit available in Ruby that can be configured as an HTTPS server, a proxy server, or a virtual-host server. It offers complete logging of server operations as well as HTTP access and supports basic and digest authentication.

The HTTP Protocol

HTTP is an application protocol designed with lightness, speed, and hypermedia in mind. Between 1991 and 1992 the Internet Engineering Task Force (IETF) introduced the first documented versions of HTTP (HTTP v0.9 and HTTPv1.0) as a “stateless object-oriented protocol,” with the capability to negotiate data representation, thereby allowing software systems to be built independently of the data format used for the actual communication.

The 1991 definition of the protocol implemented three actions:

  • Request
  • Response
  • Disconnection

The request action consisted of sending a document request. This request was formed with the word “GET,” a space, the document address (omitting the “http:”), the host name, and the port number.

The response consisted of the actual HTML document that had been requested, sent as a byte stream of ASCII characters.

When the whole document had finished transferring, the connection with the server was broken (the disconnection action).

HTTP has been extended and developed up to version 1.1 (RFC 7230), where it has been defined as a “generic interface protocol for information systems.” One interesting aspect of the protocol’s definition is that HTTP requests can be considered in isolation—i.e., the server can transparently ignore specific aspects of the client itself or a defined sequence of application steps. The protocol can hence be used in a wide range of contexts, where the actual implementations can evolve independently.

HTTP can also be implemented as an intermediate protocol used to translate communication messages between non-HTTP systems. In this particular implementation, HTTP proxies are responsible for translating their own sets of protocols into a hypertext format that can be interpreted and manipulated by HTTP clients and services.

The HTTP protocol’s flexibility resides in the idea that it only defines the syntax of the communication between the parties involved, the intent of the received communication, and the expected behavior of the recipients. What happens behind the interfaces of the communicating parties is out of the scope of the protocol definition.

To understand the basics of HTTP and be able to reason about the protocol, let’s start by getting some HTTP manually. We are going to “pretend” we are a web browser and request a resource through telnet.

From a terminal window, type:

$ telnet google.com 80

This will open a telnet request to google.com on port 80:

Trying 173.194.45.174...
Connected to google.com.
Escape character is '^]'.

Now let’s request the index page:

GET /

To which we will get the reply:

HTTP/1.1 302 Found
Cache-Control: private
Content-Type: text/html; charset=UTF-8
Location: http://www.google.es/?gfe_rd=cr&ei=6xwvVOTHIcnBUOrygsAD
Content-Length: 256
Date: Fri, 03 Oct 2014 22:02:19 GMT
Server: GFE/2.0
Alternate-Protocol: 80:quic,p=0.01
<HTML><HEAD><meta http-equiv="content-type" content="text/html;
charset=utf-8">
<TITLE>302 Moved</TITLE></HEAD><BODY>
<H1>302 Moved</H1>
The document has moved
<A HREF="http://www.google.es/?gfe_rd=cr&ei=6xwvVOTHIcnBUOrygsAD">
here</A>.
</BODY></HTML></p>

Google is telling us that it has moved the page.

Architecture

HTTP was created to support the World Wide Web, and its development over time has reflected the Web’s needs and its scalability challenges.

HTTP’s architecture is based on a client and server model. The definitions of client and server only define the particular roles that the programs or services fulfill for a particular connection, though. This means the same party can be a server in one connection and a client in others.

HTTP is stateless. This means that the communication protocol treats each request independently from previous ones and that the server does not retain session or status information regarding the parties involved in a certain communication.

The message exchange pattern used by HTTP is request/response. Messages are exchanged over a reliable transport or session layer connection.

The client in a HTTP communication is the party that establishes a connection to a server for sending one or more HTTP requests. Other terms that complete the HTTP protocol glossary are user agent, origin server, sender, and recipient.

A user agent is a software client originating an HTTP request. This can be a browser, a spider (robot program) crawling the Web, or any generic application. An origin server is a program that can originate authoritative responses for a certain resource. This is the server where the specified resource resides.

Sender and recipient are the terms used to indicate any party that sends and receives messages, respectively.

It is important to note that HTTP has been designed to be implemented in a wide range of situations. Not all user agents are general-purpose browsers accessing large public websites served by origin servers.

A user agent can be any sort of application, from mobile apps, to household appliances, to environmental sensors, to personal devices like fitness activity trackers.

The same applies when considering origin servers: these can be anything from city traffic cameras to networking components.

Most HTTP communication consists of a request for some resource indicated by a Uniform Resource Identifier (URI). The URI is a standard for identifying local and remote resources and describing the relationships between resources.

HTTP considers URIs as formatted strings identifying specific resources, composed from a limited set of characters and some graphic symbols and consisting of a hierarchical sequence of components: the scheme identifying the protocol, host name and port number, absolute path, query, and fragment. The format is (with optional components indicated by square brackets):

"http:""//"host[":"port][abs_path["?"query]["#"fragment]]

HTTP also allows the use of intermediaries between the client and server (as illustrated in Figure A-1), to handle requests through a chain of connections. Generally speaking, it is possible to identify three common HTTP intermediaries:

Proxy

A proxy’s function is to forward messages. The client selects the proxy via some local configuration rule to receive requests for all or some absolute URIs and redirects these requests through the HTTP interface toward some origin servers, in the attempt to satisfy them.

Gateway

A gateway, or reverse proxy, acts as an origin server translating received requests and forwarding these inbound to other servers. A gateway may communicate with inbound servers using different protocols, but if it wants to interoperate with third-party HTTP servers it will have to respect the user agent requirements for the inbound connections.

Tunnel

A tunnel is a relay between two connections that doesn’t change the messages exchanged in any way. Once it has been activated, a tunnel is not considered a party in the HTTP communication itself, and it is terminated when both ends of the connections are closed. An example of where tunnels are used is when Transport Layer Security (TLS) is used to establish a confidential communication.

This categorization is actually very versatile, as a single intermediary might act as an origin server, proxy, gateway, or tunnel in different communications, while at the same time handling many requests simultaneously.

HTTP moreover distinguishes between upstream and downstream communications, to describe directional requirements in relation to the message flow (messages always originate upstream and flow downstream). The terms inbound and outbound are instead used to describe directions regarding the request route, where inbound means toward the origin server and outbound means toward the user agent.

Figure A-1. A simple HTTP communication, initiated from a user client toward an origin server, can pass through a series of intermediaries

Parameters

Within HTTP request and response messages, colon-separated name/value pairs are transmitted in clear-text string format and terminated by a carriage return (CR) and line feed (LF) character sequence. These constitute the header fields of the HTTP message and define the operating parameters of an HTTP transaction. The end of the header fields is marked by two consecutive CRLF pairs.

If you were to visit http://www.oreilly.com, your browser would send a number of HTTP requests; if you captured one of these, the “headers” part of the request would look more or less like this:

GET / HTTP/1.1 Host: www.oreilly.com
Accept-Encoding: gzip,deflate,sdch
Accept-Language: en-US,en;q=0.8,es;q=0.6,it;q=0.4,en-GB;q=0.2,ca;
q=0.2
Cookie: <Some garbled cookie data>
User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10_9_2) 
AppleWebKit/537.36 (KHTML, like Gecko) Chrome/35.0.1916.153 
Safari/537.36
X-Client-Data: <Some garbled client data>
HTTP/1.1 200 OK Accept-Ranges: bytes
Cache-Control: max-age=14400
Connection: keep-alive
Content-Encoding: gzip
Content-Length: 16813
Content-Type: text/html; charset=utf-8
Date: Sat, 12 Jul 2014 16:59:01 GMT
Expires: Sat, 12 Jul 2014 20:59:01 GMT
Last-Modified: Sat, 12 Jul 2014 08:28:40 GMT
Server: Apache
Vary: Accept-Encoding

The Internet Engineering Task Force (IETF) has standardized a core set of field names that must be implemented by all HTTP-compliant protocol implementations. In addition to the core set, each application can also define their own field names and permissible values.

The Internet Assigned Numbers Authority (IANA) maintains the permanent registry of headers and a repository of provisional registrations. Up to June 2012, nonstandard header fields were conventionally marked by prefixing the field name with “X-”; however it was decided to deprecate this convention to avoid issues when nonstandard fields became part of the standard set.

Among the message headers, an HTTP-Version field is also specified to indicate the version of HTTP in use. This allows the sender to specify the format of a message and its capacity to understand further HTTP communications.

Note

Although a detailed analysis of HTTP parameters is outside of the scope of this book, a particularly interested reader might find the following RFC documents useful:

  • RFC 2616 (Hypertext Transfer Protocol—HTTP 1.1, Section 3, Protocol Parameters)
  • RFC 4229 (HTTP Header Field Registrations)
  • RFC 3986 (Uniform Resource Identifier (URI): Generic Syntax)

Messages

HTTP messages are either requests from client to server or responses from server to client.

Both requests and responses consist of a start line, zero or more header fields, an empty line (i.e., a line containing just a CRLF) that indicates the end of the header fields, and possibly a message body with the payload of the message. The format is therefore:

start-line 
*(message headers CRLF) 
CRLF 
[ message-body ]

The header fields include general headers, request headers, response headers, and entity header fields.

The message body of an HTTP message (if there is one) carries the entity body associated with the request or response. The entity body might be encoded as defined by the Transfer-Encoding field. In this case it will differ from the message body:

message-body = entity-body 
               | <entity-body as encoded per Transfer-Encoding>
Note

HTTP messages are described in greater detail in RFC 2616, Section 4.

Although request and response messages use a generic format for transferring the message payload, some syntax differences apply between the two.

Request messages

An HTTP request is always sent from the client to the server. The first line of the message includes the method of the request, the resource identifier (URI), and the protocol version.

HTTP defines a list of common methods; in addition, resources might specify allowed methods in an Allow header field. When a request message specifies a certain method, the return code of the response message notifies the client whether that method is allowed or implemented.

Whenever the method is implemented by the server but not allowed for the requested resource, the origin server should return the status code 405 (Method Not Allowed); it should return 501 (Not Implemented) if the method is not recognized or not implemented. We’ll look at status codes in more detail shortly.

The client can use the request headers to pass additional information to the origin server. The request header fields act as modifiers, following semantics equivalent to those of parameters in a programming language method invocation.

The complete list of core HTTP methods includes the following:

Method = "OPTIONS" ;
| "GET" ;
| "HEAD" ;
| "POST" ;
| "PUT" ;
| "DELETE" ;
| "TRACE" ;
| "CONNECT" ;
| extension-method
| extension-method = token
Note

For a detailed discussion of several of these methods and how they are mapped to controller actions in Rails, please see “HTTP Semantics” in Chapter 4. The HTTP methods are defined in RFC 2616, Section 9.

Response messages

Once the origin server receives and interprets a request message, it will respond with an HTTP response message.

The response message starts with a status line, comprised of the protocol version, a numeric status code, and its associated textual phrase:

Status-Line = HTTP-Version SP Status-Code SP Reason-Phrase CRLF

Status codes are three-digit identifiers that the server sends in its response after parsing and interpreting a request. They are intended to be used by the client software to understand the server’s reply. The reason phrase is just a human-readable explanation of the status code, which the client is not required to examine or display.

Following the status line, the response message contains the response headers. These allow the server to pass additional information about itself and the requested resource.

Entity

Both request and response messages may contain an entity consisting of entity headers and an entity body.

The headers define metainformation regarding the entity body or the requested resource. Some of this information is optional, and some might be required by the protocol specification.

An entity body can only be included in a message when a message body is present. When an entity body is included, the Content-Type and Content-Encoding fields determine the data type of the entity body.

The entity body follows a two-layer, ordered model:

entity-body := Content-Encoding( Content-Type( data ) )

The Content-Type field specifies the media type of the enclosed data, while the Content-Encoding field may indicate additional content codings applied to the data (e.g., for the purpose of data compression). No default encoding is specified in the protocol definition.

Connections

HTTP supports the possibility of using a single TCP connection to send and receive multiple HTTP request/response messages. This method is called persistent connection, keep-alive, or connection reuse. Under HTTPv1.0, if the client supports the Keep-Alive header field, it will add it to the request:

Connection: Keep-Alive

Then, when attempting to handle this request, the server will add the same header field to the response. For following messages, the connection is kept open. When the client sends another request it will therefore use the same TCP connection. The connection will be interrupted only when either the client or the server drops it, signaling that the communication is over.

In HTTPv1.1 all connections are considered persistent unless otherwise specified. A short connection timeout is also implemented to allow origin servers to deliver multiple components of a web page rapidly enough, while not consuming excessive resources.

Clients supporting persistent connections may also wish to “pipeline” their requests, i.e., sending multiple requests without waiting for each response. The origin server will serve the responses in the same order that the requests were received.

Status Code Definitions

Status codes are three-digit codes that define the response of the server to a certain request. The first digit corresponds to the class of response. HTTP defines five classes:

1xx: Informational - Request received, continuing process
2xx: Success - The action was successfully received, 
  understood, and accepted
3xx: Redirection - Further action must be taken in order to 
  complete the request
4xx: Client Error - The request contains bad syntax or cannot 
  be fulfilled
5xx: Server Error - The server failed to fulfill an apparently 
  valid request

HTTPv1.1 also defines individual values of the status codes, with corresponding reason phrases that are intended to be used as recommendations for individual implementations (these can be replaced without affecting the protocol). Codes that you will probably use most frequently are:

Status-Code = 100 : Continue
| 200: OK
| 201: Created
| 202: Accepted
| 204: No Content
| 301: Moved Permanently
| 302: Found
| 303: See Other
| 304: Not Modified
| 400: Bad Request
| 401: Unauthorized
| 403: Forbidden
| 404: Not Found
| 500: Internal Server Error
| 501: Not Implemented
| 502: Bad Gateway
| 503: Service Unavailable
Note

HTTP status codes are defined in RFC 2616, Section 10.

Access Authentication

HTTP provides different optional challenge-response authentication mechanisms, which can be used either by the server to challenge a client request, or by a client to provide authentication information.

These are defined separately from the protocol specification in RFC 2617. Note, however, that the authentication scheme provided by HTTP is not considered to be a secure method of user authentication unless used together with other external secure methods, such as SSL.

Content Negotiation

Content negotiation is the process of selecting a representation for a given response when multiple representations are available, in terms of type, language, encoding, and so on. HTTP defines two kinds of content negotiation: server-driven and agent-driven. The two methods are orthogonal and therefore can be used either independently or in combination. Transparent negotiation is one type of combination, where the negotiation work is taken over by the cache.

Note

For details on the supported forms of content negotiation, see RFC 2616, Section 12.

Caching

HTTP was designed for distributed information systems, where caching is known to improve performance. Therefore, the protocol definition includes a number of methods and elements to make the use of response caches as efficient as possible.

The ultimate goal of caching in HTTP is to reduce the need to send requests or response message in as many cases as possible, therefore limiting the number of network round-trips and network bandwidth required for a given communication.

Caching is an important aspect of HTTP and REST. Within RESTful architectures, the most efficient network request is one that doesn’t use the network, but efficiently relies on caching.

When defining its caching capabilities, HTTP introduces the concept of semantic transparency. It is said that a caching method is semantically transparent regarding a certain response when its use affects neither the client nor the origin server, except to improve performance. In other words, if the caching method is semantically transparent, the client receives the response from the cache exactly as it would have received it if the origin server had handled the request.

HTTPv1.1 allows clients, servers, and caching methods to explicitly reduce semantic transparency when necessary to improve performance.

HTTP also defines cache correctness as the idea that the cache, or caching method, responds to a certain request with the most up-to-date response possible that is appropriate to the request.

If the response returned by the cache is neither firsthand nor considered “fresh enough,” a Warning header is attached to the response so that the client can handle it properly.

Client and server caching and cache control mechanisms were discussed in detail in Chapter 12, where we saw how to best integrate external resources into our own application.

Security Considerations

HTTP clients and servers often exchange large amounts of user-generated data, and this should be handled carefully to prevent leakage to external sources through the HTTP protocol.

Chapter 16 discussed a number of security challenges that developers face, but it’s worth repeating a few key points.

Particularly, a server is in the position to log personal data contained in users’ requests that might reveal more than intended about them, and can be used by a potential attacker in a variety of ways. Users often reveal information regarding their thoughts, actions, tastes, and preferences by sharing them either indirectly, through their request messages, or directly, by voluntarily publishing this information online.

It is also important to note that as users’ online interactions become more complex and as shared documents are enriched with different media content, it is often difficult for the users to understand and ponder what kind of information is actually being shared with a single post, or what they might consider just innocuous activity.

It is therefore the responsibility of the application developer to implement methods and practices to safeguard privacy and protect user data from unintended leakages and unauthorized accesses. 

..................Content has been hidden....................

You can't read the all page of ebook, please click here login for view all page.
Reset
18.117.11.247