¿Qué es una Solicitud HTTP?
Creo que primero habría que definir que es HTTP (Hipertext Transfer Protocol). El protocolo HTTP no le debe ser muy indiferente. Si leíste sobre el Modelo OSI, recordarás que este protocolo de comunicación pertenece al nivel de aplicación, que a su vez, esta por encima de otro famoso protocolo, el protocolo TCP (Transmission Control Protocol) que se sitúa en la capa transporte de este modelo. Como todo protocolo de comunicación, el protocolo HTTP define unas normas que debe seguir el emisor que desea transmitir información a un receptor. HTTP utiliza el patrón de request / response (petición / respuesta), lo cual quiere decir, que un emisor (sistema X) realiza una solicitud (request) y un servidor (Sistema Y) responde (response) a dicha solicitud.
En la siguiente imagen se puede apreciar como un computador (emisor) realiza una solicitud HTTP (HTTP Request) a un servidor (receptor) y este último le responde (HTTP Response) el pedido.
A continuación un ejemplo de las reglas que debe seguir el cliente para que el servidor comprenda su petición HTTP.
La primera línea se llama Línea de Solicitud y contiene tres elementos;
1. El método HTTP (para este ejemplo es POST).
2. Una ruta de acceso (también denominada como endpoint en una API).
3. La versión HTTP (para este ejemplo es HTTP/1.1)
Existen otros métodos HTTP, más adelante se mencionarán.
El contenido que le sigue a la “Línea de Solicitud” se denomina Headers (en español encabezados). Los headers son pares de key – value (clave – valor), donde la clave es la primera palabra, seguido de dos puntos y un espacio y, a continuación, el valor. Los headers están separados por saltos de línea. Es recomendable que las claves de los headers inicien con su primera letra en mayúscula. Los headers pueden repetirse en situaciones en las que es necesario enviar valores duplicados.
Una solicitud HTTP (HTTP Request) solo necesita tener una Línea de Solicitud y algunos headers para ser válido. Esto se aplica principalmente a las solicitudes que utilizan los métodos HTTP GET, DELETE, HEAD y OPTIONS. Sin embargo, también podemos proporcionar un cuerpo de solicitud (request body), que requiere dos líneas nuevas después del último header antes del contenido del cuerpo. Los cuerpos se utilizan principalmente con los métodos HTTP POST, PUT y PATCH.
Endpoints
Al diseñar una API HTTP RESTful, es importante poder abstraer la funcionalidad de su servicio de tal manera que todas las operaciones puedan representarse realizando operaciones CRUD(Create, Read, Update, Delete) para los diferentes recursos (entidades). Las acciones (verbos HTTP ó métodos HTTP) que se realizan nunca deben ser parte del endpoint.
El enfoque más utilizado es exponer diferentes colecciones de recursos relacionados. Por ejemplo, si su servicio contiene información sobre diferentes empresas y empleados, podría tener una colección llamada empresas y otra colección llamada empleados. Podemos obtener información más específica y hacer referencia a una empresa individual o a sus empleados dentro de cada una de estas colecciones. Como por ejemplo, un empleado puede ser empleado en una empresa. Lo siguiente es cómo podemos representar estos datos y sus relaciones:
Por lo tanto, podemos decir que si queremos obtener la lista de empresas debemos solicitar el endpoint /companies o si queremos obtener información de solo una empresa debemos solicitar el endpoint /companies/{company_id}
Headers HTTP
Habíamos dicho que los headers son un conjunto de pares de clave-valor. Hay muchos headers diferentes que podemos utilizar. Los navegadores web, por lo general, envían varios headers en sus solicitudes HTTP (requests) y los nuevos navegadores están siendo estandarizados todo el tiempo. A continuación una lista de los headers más comunes y su significado, que además debe tener en cuenta para que sean compatibles con el API HTTP que construyas.
Accept: Puede contener una lista de “Tipos de Contenido” (Content-Types) que son aceptados por el cliente (navegador web por ejemplo). Un tipo de contenido muy usado en las APIs HTTP es application/json. Es decir, el cliente acepta recibir información del servidor en formato JSON.
Accept-Language: Puede contener una lista de idiomas que son aceptados por el cliente. Por ejemplo podemos indicar que el cliente acepta recibir información del servidor en idioma ingles en-US, o en español es-pe.
Content-Length: Es la longitud en bytes del cuerpo de la solicitud. Si se conoce el tamaño del cuerpo de la solicitud, se debe enviar este valor.
Content-Type: Representa al tipo de contenido proporcionado en el cuerpo de la solicitud. Sólo enviar si la solicitud contiene un cuerpo. Por ejemplo podemos indicar en nuestra solicitud HTTP que la información que vamos a enviar al servidor estará en formato JSON.
Host: Este header siempre se debe enviar en las solicitudes HTTP. Representa al Host HTTP del servidor. Las aplicaciones probablemente ignorarán esto, sin embargo, es sobre todo útil para los hosts virtuales y el enrutamiento de solicitudes.
User-Agent: Este header incluye información de identificación del cliente, como por ejemplo el nombre del navegador web de donde se envía la solicitud HTTP.
Estos son solo algunos de los headers estandarizados que existen, pero también hay un montón de headers que puedes agregar de manera ad-hoc. Como regla general, al inventar sus propios headers, el patrón común es prefijarlo con una X por adelante, como por ejemplo X-API-Version para representar la versión del API.
Método GET
El método GET hace referencia a la acción de Leer (Read) del CRUD. Las solicitudes GET (GET requests) se consideran seguras, lo que significa que no deben alterar el estado del servidor. Las solicitudes GET se consideran idempotentes, lo que significa que deben ser repetibles sin causar efectos secundarios. Las solicitudes GET no deben tener un cuerpo (body request).
Cuando se usa el método GET contra una colección (por ejemplo /empresas) significa que deseas recuperar una lista de recursos dentro de esa colección (es decir una lista de empresas). Podemos recuperar todos los recursos o filtrar recursos específicos según los criterios definidos. El siguiente ejemplo es para obtener obtener una lista de empleados:
La solicitud anterior podría traducirse en “Obtener una lista de 10 empleados que trabajan en Twitter que estén en el rango salarial entre 3000 y 8000 (dólares por ejemplo), omitiendo los primeros 20“. El endpoint contiene parámetros de consulta (filtros) que inician luego del símbolo ? (? Key1 = Value1 & Key2 = Value2). Si no se especifican las propiedades de filtrado (parámetros de consulta), el servidor debe responder con todos los recursos coincidentes. Es común que los servidores tengan límites por defecto en los datos devueltos, de lo contrario sería muy abrumador devolver todos los datos de una colección, imagina que hubiesen millones de registros :0.
Te esperamos en los próximos artículos en donde hablaremos mas acerca de estos temas que hoy en día son de importancia e interés en el mundo de la tecnología.