Docs / Módulo / Imágenes

Módulo de Imágenes

CDN y API para redimensionado, compresión y conversión (WebP / AVIF) con baja latencia en LatAm y caché integrada. Soporta tres modos de integración: URL directa, librería JavaScript con lazy loading, y API autenticada.

Introducción

Las imágenes representan más del 50 % del peso de una página web. El módulo de Imágenes de Webability las procesa, redimensiona y convierte a WebP o AVIF en tiempo real, con caché integrada. Solo necesitas tu clientid (10 letras minúsculas) disponible en la consola de administración.

Ideal para

  • • Web y móviles
  • • E-commerce y catálogos
  • • Mejora de Core Web Vitals

Formatos de salida

WebP y AVIF (o JPG como fallback automático). Entrada: JPG, PNG, GIF, WebP, AVIF.

Modos de integración

  • 1. URL directa en HTML
  • 2. Lazy Loading JS
  • 3. API autenticada

Quickstart

En menos de 2 minutos puedes servir tu primera imagen optimizada. Solo necesitas tu clientid, que se obtiene en la consola → Configuración.

  1. 1 Obtén tu clientid de 10 letras en la consola de administración.
  2. 2 Configura el dominio de tu CDN de origen (donde viven las imágenes originales).
  3. 3 Usa el endpoint directamente en tu código HTML:

URL directa — estructura

https://cdn.webability.info/[IDCliente]/ruta/en/tu/cdn/720x480/imagen.jpg.webp
clientid — tu identificador único (10 letras minúsculas) · ruta — directorio en tu CDN de origen · WxH — ancho × alto en píxeles · archivo — nombre del archivo original · formatowebp, avif o jpg
Nota importante — El identificador único (10 letras minúsculas) puede ser personalizado para las cuentas empresariales.

Ejemplo concreto — logo 50×50 en AVIF

<!-- imagen original: https://www.tusitio.com.mx/imagenes/logo.png -->
<img src="https://cdn.webability.info/abcdefghij/imagenes/50x50/logo.png.avif" alt="Logo">

💡 Recomendado para producción

Usa el modo Lazy Loading JS para mejor SEO y performance: la librería detecta el viewport, carga imágenes bajo demanda y elige automáticamente el mejor formato soportado por el navegador.

1

Llamada directa por URL

El método más simple: construye la URL de la imagen optimizada y úsala directamente en el atributo src de cualquier etiqueta <img>, en CSS, en etiquetas <picture> o como argumento de cualquier petición HTTP. No requiere JavaScript ni autenticación.

Estructura de la URL

https://cdn.webability.info/{clientid}/{ruta}/{WxH}/{archivo.ext}
Segmento Descripción
{clientid} Tu identificador de cliente (10 letras minúsculas). Disponible en la consola → Configuración.
{ruta} Directorio de la imagen en tu CDN de origen, sin el dominio. Puede contener subcarpetas.
{WxH} Dimensiones objetivo en píxeles. Formato: anchoXalto, p. ej. 800x600.
{archivo.ext} Nombre del archivo original incluyendo su extensión, seguido de .webp, .avif o .jpg para la salida deseada.

Ejemplos

Etiqueta <img> simple

<img
  src="https://cdn.webability.info/abcdefghij/productos/800x600/zapatilla.jpg.webp"
  alt="Zapatilla deportiva"
  width="800" height="600"
/>

Elemento <picture> con AVIF y WebP

<picture>
  <source
    type="image/avif"
    srcset="https://cdn.webability.info/abcdefghij/blog/1200x630/portada.jpg.avif"
  />
  <source
    type="image/webp"
    srcset="https://cdn.webability.info/abcdefghij/blog/1200x630/portada.jpg.webp"
  />
  <img
    src="https://cdn.webability.info/abcdefghij/blog/1200x630/portada.jpg.jpg"
    alt="Portada del artículo"
    width="1200" height="630"
  />
</picture>

srcset responsivo

<img
  srcset="
    https://cdn.webability.info/abcdefghij/hero/480x320/banner.jpg.webp  480w,
    https://cdn.webability.info/abcdefghij/hero/768x512/banner.jpg.webp  768w,
    https://cdn.webability.info/abcdefghij/hero/1200x800/banner.jpg.webp 1200w
  "
  sizes="(max-width: 600px) 480px, (max-width: 900px) 768px, 1200px"
  src="https://cdn.webability.info/abcdefghij/hero/1200x800/banner.jpg.webp"
  alt="Banner principal"
/>

Imagen de fondo en CSS

.hero {
  background-image: url(
    "https://cdn.webability.info/abcdefghij/home/1920x1080/fondo.jpg.webp"
  );
  background-size: cover;
}

cURL — descarga directa

curl -L "https://cdn.webability.info/abcdefghij/productos/400x400/item.png.avif" -o item.avif

Imagen de demostración del sitio (1.6 MB original → ~32 KB en WebP 600×450)

<img src="https://cdn.webability.info/webability/static/600x450/images.png.webp" />

La primera solicitud genera y cachea la imagen. Las siguientes son servidas directamente desde caché con Cache-Control: public, max-age=31536000.

2

Lazy Loading con la librería JavaScript

Recomendado

Incluye en tu sitio la librería JavaScript personalizada. Detectará automáticamente todos los elementos marcados, construirá las URLs correctas y los cargará de forma diferida (lazy loading), mejorando los Core Web Vitals y el SEO. Si el navegador no soporta WebP o AVIF, servirá automáticamente la alternativa en JPG.

Paso 1 — Incluir la librería en el <head>

<head>
  ...
  <!-- Librería de imágenes Webability (reemplaza {clientid} con tu ID) -->
  <script src="https://cdn.webability.info/js/[IDCliente]" defer></script>
  ...
</head>

Paso 2 — Marcar las imágenes con atributos data-*

En lugar del atributo src, usa los atributos de datos siguientes:

Atributo Obligatorio Descripción
data-src Ruta completa de la imagen en tu CDN de origen (URL absoluta o ruta relativa al dominio configurado).
data-width Ancho deseado en píxeles (número entero).
data-height Alto deseado en píxeles (número entero).
data-format No Formato de salida: webp (defecto), avif, jpg u original (mantiene el formato fuente).

Ejemplos

Imagen básica en WebP (formato por defecto)

<img
  class="wa-lazy"
  data-src="/imagenes/logo.png"
  data-width="50"
  data-height="50"
  style="width:50px; height:50px;"
  alt="Logo"
/>

Imagen en AVIF con dimensiones explícitas

<img
  class="wa-lazy"
  data-src="/fotos/producto.jpg"
  data-width="400"
  data-height="300"
  data-format="avif"
  style="width:400px; height:300px;"
  alt="Producto"
/>

Hero banner en WebP

<img
  class="wa-lazy rounded-xl"
  data-src="/static/images.png"
  data-width="600"
  data-height="450"
  data-format="webp"
  style="width:600px;"
  alt="Hero"
/>

Formato original (sin conversión)

<img
  class="wa-lazy"
  data-src="/catalogos/ficha.gif"
  data-width="300"
  data-height="200"
  data-format="original"
  alt="Animación de ficha"
/>

Página completa — ejemplo de integración

<!DOCTYPE html>
<html lang="es">
<head>
  <meta charset="UTF-8">
  <title>Mi Sitio</title>
  <script src="https://cdn.webability.info/js/abcdefghij" defer></script>
</head>
<body>

  <!-- Logo en header -->
  <img class="wa-lazy" data-src="/static/logotr.png" data-width="50" data-height="50" style="width:50px;">

  <!-- Galería de productos -->
  <img class="wa-lazy" data-src="/productos/camisa-azul.jpg" data-width="400" data-height="400" data-format="webp">
  <img class="wa-lazy" data-src="/productos/pantalon.jpg"   data-width="400" data-height="400" data-format="avif">

  <!-- Indicador de carga (opcional) -->
  <div class="wa-loader"></div>

</body>
</html>

URL generada automáticamente por la librería (lo que termina en el src)

https://cdn.webability.info/abcdefghij/productos/400x400/camisa-azul.jpg.webp

La librería solo carga imágenes cuando entran al viewport del usuario (Intersection Observer API), reduciendo el ancho de banda inicial y mejorando el LCP.

3

API autenticada

La API autenticada permite operaciones avanzadas desde tu backend: obtener imágenes procesadas, subir originales directamente y gestionar la caché. Todos los endpoints requieren los tres headers de autenticación descritos en la sección Autenticación.

Base URL: https://api.webability.info

Endpoint /v1/image

Gestión completa de imágenes: obtener, subir y purgar caché.

GET /v1/image/{ruta}/{WxH}/{archivo.ext}

Recupera una imagen procesada y redimensionada. Si no existe en caché, la descarga desde tu CDN de origen, la convierte y la almacena. La respuesta es el binario de la imagen con el Content-Type correspondiente.

Segmentos de la URL

Segmento Descripción
{ruta} Directorio de la imagen en el repositorio del cliente.
{WxH} Dimensiones en píxeles. Formato: anchoXalto, p. ej. 800x600.
{archivo.ext} Nombre del archivo original con su extensión fuente, más la extensión de salida: imagen.jpg.webp. Salida soportada: webp, avif, jpg.

Ejemplos de request

cURL — obtener imagen

curl -X GET \
  -H "X-WA-Token: {token}" \
  -H "X-WA-Timestamp: {unix}" \
  -H "X-WA-Digest: {hmac}" \
  "https://api.webability.info/v1/image/productos/800x600/zapatilla.jpg.webp" \
  -o zapatilla.webp

Go — HTTP client

req, _ := http.NewRequest("GET",
  "https://api.webability.info/v1/image/productos/800x600/zapatilla.jpg.webp", nil)
req.Header.Set("X-WA-Token", token)
req.Header.Set("X-WA-Timestamp", ts)
req.Header.Set("X-WA-Digest", digest)
resp, _ := http.DefaultClient.Do(req)
// resp.Body contiene la imagen binaria

Respuesta

HTTP/1.1 200 OK
Content-Type: image/webp
Cache-Control: public, max-age=31536000

[binary image data]
POST /v1/image/{ruta/archivo.ext}

Sube una imagen original al repositorio del cliente. Acepta los formatos jpg, jpeg, png, gif, webp y avif. Tamaño máximo: 50 MB. Al subir un archivo, purga automáticamente todas las versiones cacheadas del mismo.

Nota:

El tamaño máximo se puede cambiar en las cuentas empresariales.

Body

Content-Type: multipart/form-data con el campo file conteniendo el binario de la imagen.

cURL — subir imagen

curl -X POST \
  -H "X-WA-Token: {token}" \
  -H "X-WA-Timestamp: {unix}" \
  -H "X-WA-Digest: {hmac}" \
  -F "file=@/local/zapatilla.jpg" \
  "https://api.webability.info/v1/image/productos/zapatilla.jpg"

Respuesta JSON

{
  "status": "ok",
  "path": "productos/zapatilla.jpg",
  "filename": "zapatilla.jpg",
  "size": 284560,
  "cache_purged": 12
}
DELETE /v1/image · /v1/image/{ruta/imagen.ext} · /v1/image/{carpeta/}

Permite tres modos de eliminación:

URL Efecto
/v1/image Purga toda la caché de versiones procesadas (secondcache). Los originales se conservan.
/v1/image/prod/img.jpg Elimina el original y todas sus versiones cacheadas.
/v1/image/carpeta/ Elimina la carpeta completa de ambas cachés (originales y versiones procesadas).

cURL — purgar imagen específica

curl -X DELETE \
  -H "X-WA-Token: {token}" \
  -H "X-WA-Timestamp: {unix}" \
  -H "X-WA-Digest: {hmac}" \
  "https://api.webability.info/v1/image/productos/zapatilla.jpg"

Respuesta JSON

{
  "status": "ok",
  "deleted_firstcache": 1,
  "deleted_secondcache": 8,
  "total": 9
}

Endpoint /v1/stat

Estadísticas de uso del repositorio y la caché del cliente. Solo soporta GET.

GET /v1/stat — estadísticas globales

Devuelve el total de archivos y tamaño por caché y por formato.

Request

curl -X GET \
  -H "X-WA-Token: {token}" \
  -H "X-WA-Timestamp: {unix}" \
  -H "X-WA-Digest: {hmac}" \
  "https://api.webability.info/v1/stat"

Respuesta JSON

{
  "status": "ok",
  "client": "abcdefghij",
  "firstcache": {
    "files": 120,
    "size_bytes": 48234560,
    "size_mb": 46.01,
    "by_format": { "jpg": 80, "png": 30, "gif": 10 }
  },
  "secondcache": {
    "files": 850,
    "size_bytes": 210345678,
    "size_mb": 200.61,
    "by_format": { "webp": 600, "avif": 150, "jpg": 100 }
  },
  "total": {
    "files": 970,
    "size_bytes": 258580238,
    "size_mb": 246.62
  }
}
GET /v1/stat/{ruta/imagen.ext} — estadísticas por imagen

Lista todas las versiones cacheadas de una imagen específica con sus dimensiones, formato y tamaño.

Request

curl -X GET \
  -H "X-WA-Token: {token}" \
  -H "X-WA-Timestamp: {unix}" \
  -H "X-WA-Digest: {hmac}" \
  "https://api.webability.info/v1/stat/banners/logo.jpg"

Respuesta JSON

{
  "status": "ok",
  "image": "banners/logo.jpg",
  "original": {
    "exists": true,
    "size_bytes": 142560
  },
  "versions": [
    {
      "filename": "800x600-logo.webp",
      "size": 18432,
      "width": 800,
      "height": 600,
      "format": "webp"
    },
    {
      "filename": "400x300-logo.webp",
      "size": 9216,
      "width": 400,
      "height": 300,
      "format": "webp"
    }
  ],
  "version_count": 2
}

Autenticación

Todos los endpoints de la API autenticada requieren tres headers en cada request. El digest es un HMAC-SHA256 calculado con tu token como clave secreta.

Header Valor
X-WA-Token Tu token de cuenta, disponible en la consola de administración.
X-WA-Timestamp Unix timestamp actual en segundos. Debe estar dentro de ±5 minutos del reloj del servidor.
X-WA-Digest HMAC-SHA256 en hexadecimal. Mensaje canónico: {METHOD}|{PATH}|{TIMESTAMP}|{TOKEN}. Clave: tu token.

Ejemplo de cálculo del digest

Go

import (
  "crypto/hmac"
  "crypto/sha256"
  "fmt"
  "time"
)

token  := "mi_token_secreto"
method := "GET"
path   := "/v1/image/productos/800x600/item.jpg.webp"
ts     := fmt.Sprintf("%d", time.Now().Unix())
msg    := method + "|" + path + "|" + ts + "|" + token

mac := hmac.New(sha256.New, []byte(token))
mac.Write([]byte(msg))
digest := fmt.Sprintf("%x", mac.Sum(nil))

JavaScript (Node.js)

const crypto = require('crypto');

const token  = 'mi_token_secreto';
const method = 'GET';
const path   = '/v1/image/productos/800x600/item.jpg.webp';
const ts     = Math.floor(Date.now() / 1000).toString();
const msg    = `${method}|${path}|${ts}|${token}`;

const digest = crypto
  .createHmac('sha256', token)
  .update(msg)
  .digest('hex');

PHP

$token  = 'mi_token_secreto';
$method = 'GET';
$path   = '/v1/image/productos/800x600/item.jpg.webp';
$ts     = (string) time();
$msg    = "$method|$path|$ts|$token";
$digest = hash_hmac('sha256', $msg, $token);

Códigos de error

Los errores de la API devuelven un JSON con status, code y message.

Formato de error

{ "status": "error", "code": 2010, "message": "Imagen original no encontrada" }
HTTP Código Descripción
4012001Headers de autenticación faltantes o inválidos.
4012002Firma HMAC inválida o timestamp fuera de rango (±5 min).
4012003Token no encontrado.
4002004El cliente no tiene configuración CDN activa.
4002010URL inválida (segmentos insuficientes) o imagen original no encontrada en el CDN de origen.
4002011Falta la extensión del archivo de salida.
4002012Formato de dimensiones inválido. Se espera WxH, p. ej. 800x600.
4002013Formato de salida no soportado. Usa webp, avif o jpg.
4002020Subida: falta el campo file en el formulario multipart.
4002021Subida: formato de archivo no permitido.
4032022Subida: path traversal detectado.
4002023Subida: error al guardar el archivo en el servidor.
4032030Eliminación: path traversal detectado.
4002031Eliminación: error durante la operación de borrado.