¿Qué es una API REST?

Una API (Interfaz de Programación de Aplicaciones) REST (Representational State Transfer) es un conjunto de reglas que permiten a los sistemas comunicarse entre sí a través de la web. REST utiliza los métodos HTTP para interactuar con los recursos representados en la web.

Estructura de una Petición HTTP

Antes de profundizar en los métodos HTTP, es importante entender cómo está estructurada una petición HTTP. Cada petición consta de varios componentes:

Línea de Petición

Contiene el método HTTP, la ruta del recurso y la versión del protocolo:

GET /api/usuarios/123?incluir=perfil HTTP/1.1

Headers (Cabeceras)

Proporcionan información adicional sobre la petición:

Content-Type: application/json           # Formato de datos enviados
Authorization: Bearer eyJhbGci...        # Credenciales de autenticación
Accept: application/json                 # Formato esperado de respuesta
User-Agent: MiApp/1.0                    # Información del cliente
Host: api.ejemplo.com                    # Servidor de destino

Query Parameters

Se incluyen en la URL después del símbolo ? para filtrar, ordenar o configurar la respuesta:

GET /api/usuarios?page=2&limit=20&sort=nombre&activo=true

Casos de uso comunes:

  • Filtrado: ?categoria=electronica&precio_min=100
  • Paginación: ?page=2&limit=20
  • Ordenamiento: ?sort=nombre&order=asc
  • Búsqueda: ?search=ana&campo=nombre

Request Body

Contiene los datos enviados al servidor (principalmente POST, PUT, PATCH):

JSON (más común):

POST /api/usuarios
Content-Type: application/json
 
{
  "nombre": "Ana García",
  "email": "ana@ejemplo.com",
  "edad": 28
}

Form Data:

POST /api/login
Content-Type: application/x-www-form-urlencoded
 
email=usuario%40ejemplo.com&password=mi_password

Headers importantes

  • Content-Type: Especifica el formato de los datos
  • Authorization: Contiene credenciales de autenticación
  • Accept: Indica qué formatos puede procesar el cliente

Métodos HTTP

Las APIs REST utilizan los siguientes métodos HTTP para operaciones CRUD:

GET - Recuperar información

Propósito: Obtiene información sin modificar el estado del servidor. Características: Idempotente, sin efectos secundarios.

GET /api/usuarios                  # Lista todos los usuarios
GET /api/usuarios/123              # Obtiene usuario específico
GET /api/usuarios?page=2&limit=10  # Con paginación
GET /api/usuarios?activo=true      # Con filtros

POST - Crear recursos

Propósito: Crea nuevos recursos. Características: No idempotente, datos en request body.

POST /api/usuarios
Content-Type: application/json
 
{
  "nombre": "Ana García",
  "email": "ana@ejemplo.com",
  "edad": 28
}

PUT - Actualizar completamente

Propósito: Reemplaza completamente un recurso. Características: Idempotente, requiere todos los campos.

PUT /api/usuarios/123
Content-Type: application/json
 
{
  "nombre": "Ana García López",
  "email": "ana.garcia@ejemplo.com",
  "edad": 29,
  "telefono": "+56912345678"
}

PATCH - Actualizar parcialmente

Propósito: Modifica parcialmente un recurso. Características: Idempotente, solo campos a modificar.

PATCH /api/usuarios/123
Content-Type: application/json
 
{
  "email": "nuevo.email@ejemplo.com"
}

DELETE - Eliminar recursos

Propósito: Elimina un recurso del servidor. Características: Idempotente, generalmente sin request body.

DELETE /api/usuarios/123       # Elimina usuario específico

Estructura de una Respuesta HTTP

Así como las peticiones HTTP tienen una estructura definida, las respuestas también siguen un formato específico que incluye varios componentes:

Línea de Estado

La primera línea contiene la versión HTTP, el código de estado y una descripción:

HTTP/1.1 200 OK
  • Versión HTTP: HTTP/1.1
  • Código de estado: 200
  • Descripción: OK

Headers de Respuesta

Proporcionan información adicional sobre la respuesta:

Content-Type: application/json           # Tipo de contenido devuelto
Content-Length: 156                      # Tamaño del cuerpo en bytes
Server: nginx/1.18.0                     # Información del servidor
Date: Wed, 21 Oct 2024 07:28:00 GMT      # Fecha de la respuesta
Cache-Control: no-cache                  # Políticas de caché
Location: /api/usuarios/124              # URL del recurso creado (201)

Response Body

Contiene los datos devueltos por el servidor.

Respuesta exitosa con datos:

HTTP/1.1 200 OK
Content-Type: application/json
Content-Length: 87
 
{
  "id": 123,
  "nombre": "Ana García",
  "email": "ana@ejemplo.com",
  "creado_en": "2024-01-15T10:30:00Z"
}

Respuesta de error:

HTTP/1.1 400 Bad Request
Content-Type: application/json
 
{
  "error": "Datos inválidos",
  "mensaje": "El campo email es requerido",
  "detalles": {
    "email": "Este campo no puede estar vacío"
  }
}

Respuesta sin contenido:

HTTP/1.1 204 No Content
Server: nginx/1.18.0
Date: Wed, 21 Oct 2024 07:28:00 GMT

Headers importantes en respuestas

  • Content-Type: Especifica el formato de los datos devueltos
  • Location: URL del recurso recién creado (usado con 201)
  • Cache-Control: Controla el comportamiento del caché
  • Date: Timestamp de cuándo se generó la respuesta

Códigos de Estado HTTP

Los códigos de estado indican si una petición se completó exitosamente:

Códigos Más Comunes

Éxito (2xx):

  • 200 OK: Petición exitosa (GET, PUT, PATCH)
  • 201 Created: Recurso creado (POST)
  • 204 No Content: Operación exitosa sin respuesta (DELETE)

Errores del cliente (4xx):

  • 400 Bad Request: Datos inválidos
  • 401 Unauthorized: Falta autenticación
  • 403 Forbidden: Sin permisos
  • 404 Not Found: Recurso no encontrado
  • 409 Conflict: Conflicto (ej: email duplicado)

Errores del servidor (5xx):

  • 500 Internal Server Error: Error interno
  • 503 Service Unavailable: Servicio no disponible

Guía de Uso por Operación

OperaciónÉxitoError ClienteError Servidor
GET200404, 400500
POST201400, 409500
PUT200400, 404500
PATCH200400, 404500
DELETE204404500

Principios de Diseño REST

Buen Diseño vs Mal Diseño

✅ Buen diseño:

GET /api/usuarios                  # Sustantivos en plural
GET /api/usuarios/123/pedidos      # Estructura jerárquica
POST /api/usuarios                 # Método correcto para crear

❌ Mal diseño:

GET /api/obtenerUsuarios           # Verbos en URL
GET /api/usuarios/crear            # GET para crear
GET /api/usuario                   # Inconsistencia singular/plural

Mejores prácticas:

  1. Sustantivos en plural: /api/usuarios
  2. Estructura jerárquica: /api/usuarios/123/pedidos
  3. Query parameters para filtros: ?categoria=tech&precio_max=1000
  4. Versionado: /api/v1/usuarios

Interacción con una API REST

Actualmente es común el esquema backend-frontend en el desarrollo de aplicaciones web:

  • Backend: Maneja la lógica de negocio, acceso a base de datos y comunicación con servicios externos
  • Frontend: Interfaz de usuario (HTML, CSS, JavaScript) que consume la API REST

El flujo de interacción sigue estos pasos:

  1. Cliente envía petición → Frontend hace solicitud HTTP al backend
  2. Backend procesa → Ejecuta lógica y consulta base de datos
  3. Servidor responde → Envía respuesta HTTP con datos JSON
  4. Cliente renderiza → Frontend muestra datos en la interfaz
sequenceDiagram
    participant F as Frontend
    participant B as Backend
    participant DB as Base de Datos

    F->>B: GET /api/usuarios
    B->>DB: Consultar lista de usuarios
    DB-->>B: Lista de usuarios
    B-->>F: Respuesta JSON con lista de usuarios
    F->>F: Renderizar lista de usuarios en la UI