--- title: "Recolectar y transformar logs con Vector en Ubuntu 24.04" description: "Instala Vector en Ubuntu 24.04, lee los logs de acceso de Nginx, conviértelos en campos estructurados con VRL, filtra el ruido y envíalos a Grafana Loki." category: "Ingeniería de Datos" language: es source: https://cubepath.com/es/docs/ingeniería-de-datos/vector-recoleccion-y-transformacion-de-logs updated: 2026-09-25 --- # Recolectar y transformar logs con Vector en Ubuntu 24.04 Vector es un agente de observabilidad escrito en Rust que recoge logs y métricas, los transforma y los envía a uno o varios destinos con un consumo de recursos muy bajo. Su configuración se organiza en fuentes (sources), transformaciones (transforms) y destinos (sinks), y las transformaciones se escriben en VRL (Vector Remap Language). En este tutorial instalarás Vector en Ubuntu 24.04, leerás los logs de acceso de Nginx, los convertirás en eventos estructurados, descartarás el ruido y los enviarás a Grafana Loki. ## Requisitos previos Para seguir esta guía necesitas: - Un servidor con Ubuntu 24.04 LTS, por ejemplo un VPS de CubePath. Vector funciona con 512 MB de RAM libres para cargas moderadas. - Un usuario no root con privilegios `sudo`. - Nginx instalado y sirviendo tráfico, que será la fuente de logs del ejemplo. Si no lo tienes, instálalo con `sudo apt install nginx`. - Opcional para el paso 6: un servidor Grafana Loki accesible desde este servidor. Si todavía no tienes uno, puedes completar los pasos 1 a 5 enviando los eventos a la consola. ## Paso 1: Instalar Vector desde su repositorio oficial Vector publica paquetes `.deb` en un repositorio APT mantenido por Datadog. La forma soportada de configurarlo es un script que añade las claves GPG y el archivo de origen de APT. Descárgalo y revísalo antes de ejecutarlo: ```bash curl -fsSL -o setup-vector.sh https://setup.vector.dev less setup-vector.sh ``` El script crea `/etc/apt/sources.list.d/vector.list` apuntando a `https://apt.vector.dev/` y guarda las claves en `/usr/share/keyrings/datadog-archive-keyring.gpg`. Ejecútalo (pedirá `sudo` cuando lo necesite) e instala el paquete: ```bash bash setup-vector.sh sudo apt install -y vector ``` Comprueba la versión instalada: ```bash vector --version ``` ```output vector 0.50.0 (x86_64-unknown-linux-gnu) ``` El número de versión será el más reciente disponible cuando hagas la instalación. El paquete crea el usuario de sistema `vector`, lo añade a los grupos `adm` y `systemd-journal` para que pueda leer `/var/log` y el journal, e instala la unidad `vector.service`, que lee la configuración de `/etc/vector/vector.yaml`. ## Paso 2: Entender la configuración de ejemplo El paquete incluye un `vector.yaml` de demostración que genera logs de prueba en formato syslog, los analiza y los imprime. Guárdalo como referencia antes de sustituirlo: ```bash sudo mv /etc/vector/vector.yaml /etc/vector/vector.yaml.example ``` Toda configuración de Vector tiene la misma forma: - `sources`: de dónde vienen los eventos (archivos, journald, syslog, Docker, Kafka, HTTP). - `transforms`: qué se hace con ellos (analizar, filtrar, enriquecer, muestrear). Cada transformación declara en `inputs` de qué componentes recibe eventos. - `sinks`: a dónde se envían (Loki, Elasticsearch, S3, la consola). También declaran sus `inputs`. Cada componente tiene un identificador que eliges tú, y los `inputs` enlazan unos con otros para formar la topología. ## Paso 3: Leer y analizar los logs de Nginx Crea la nueva configuración con una fuente que lee el log de acceso de Nginx, una transformación que lo analiza y un destino de consola para comprobar el resultado: ```bash sudo nano /etc/vector/vector.yaml ``` ```yaml api: enabled: true address: "127.0.0.1:8686" sources: nginx_access: type: file include: - /var/log/nginx/access.log read_from: end transforms: parse_nginx: type: remap inputs: - nginx_access source: | parsed, err = parse_nginx_log(.message, "combined") if err != null { abort } . = merge(., parsed) del(.message) sinks: console: type: console inputs: - parse_nginx encoding: codec: json ``` Qué hace cada bloque: - `api` activa la API local de Vector en `127.0.0.1:8686`, que usan las herramientas `vector top` y `vector tap`. Solo escucha en localhost. - La fuente `file` sigue `access.log` y guarda su posición en `/var/lib/vector`, así que tras un reinicio continúa donde se quedó. Con `read_from: end` ignora las líneas anteriores al primer arranque. - La transformación `remap` ejecuta VRL. `parse_nginx_log` con el formato `combined` (el predeterminado de Nginx) devuelve campos como `client`, `method`, `path`, `status`, `size`, `referer` y `agent`. Si una línea no encaja, el evento se descarta con `abort`. VRL obliga a tratar ese posible error: por eso la función se llama con la forma `parsed, err = ...` en lugar de ignorarlo. Valida la configuración antes de aplicarla. `vector validate` comprueba la sintaxis, los tipos de VRL y que los componentes estén bien enlazados: ```bash sudo -u vector vector validate /etc/vector/vector.yaml ``` ```output √ Loaded ["/etc/vector/vector.yaml"] √ Component configuration √ Health check "console" ------------------------------------ Validated ``` Ejecutarlo como el usuario `vector` confirma además que ese usuario puede leer los archivos. Reinicia el servicio: ```bash sudo systemctl restart vector sudo systemctl status vector --no-pager ``` ```output ● vector.service - Vector Loaded: loaded (/usr/lib/systemd/system/vector.service; enabled; preset: enabled) Active: active (running) since ... ``` ## Paso 4: Comprobar los eventos procesados Genera algo de tráfico contra Nginx: ```bash curl -s -o /dev/null http://localhost/ curl -s -o /dev/null http://localhost/no-existe ``` El destino `console` escribe en la salida estándar, que systemd guarda en el journal. Mira los últimos eventos: ```bash sudo journalctl -u vector -n 2 --no-pager -o cat ``` ```output {"agent":"curl/8.5.0","client":"127.0.0.1","file":"/var/log/nginx/access.log","host":"your_hostname","method":"GET","path":"/","protocol":"HTTP/1.1","size":615,"source_type":"file","status":200,"timestamp":"2026-09-25T10:12:03Z"} {"agent":"curl/8.5.0","client":"127.0.0.1","file":"/var/log/nginx/access.log","host":"your_hostname","method":"GET","path":"/no-existe","protocol":"HTTP/1.1","size":162,"source_type":"file","status":404,"timestamp":"2026-09-25T10:12:04Z"} ``` La línea de texto de Nginx se ha convertido en un objeto con tipos: `status` y `size` son números, y `timestamp` es la hora de la petición, no la de lectura. Para inspeccionar el flujo en directo sin tocar la configuración, usa `vector tap`, que se conecta a la API y muestra los eventos que salen de un componente: ```bash vector tap parse_nginx ``` Y para ver el rendimiento de cada componente (eventos por segundo, errores), `vector top`. Sal de ambos con `Ctrl+C` o `q`. ## Paso 5: Filtrar el ruido y añadir campos Los health checks y las peticiones de monitorización suelen ser la mayoría de las líneas y no aportan nada. Añade una transformación `filter` que los descarte y otra `remap` que clasifique cada petición por su código de estado. Edita el archivo: ```bash sudo nano /etc/vector/vector.yaml ``` Sustituye la sección `transforms` y cambia el `inputs` del destino `console` para que reciba eventos de la última transformación: ```yaml transforms: parse_nginx: type: remap inputs: - nginx_access source: | parsed, err = parse_nginx_log(.message, "combined") if err != null { abort } . = merge(., parsed) del(.message) drop_healthchecks: type: filter inputs: - parse_nginx condition: '!includes(["/health", "/healthz", "/favicon.ico"], .path)' classify: type: remap inputs: - drop_healthchecks source: | status = to_int(.status) ?? 0 .level = if status >= 500 { "error" } else if status >= 400 { "warning" } else { "info" } sinks: console: type: console inputs: - classify encoding: codec: json ``` `filter` deja pasar solo los eventos cuya condición VRL es verdadera. En `classify`, el operador `??` da un valor por defecto si la conversión falla, algo que VRL exige para compilar: no permite ignorar errores posibles. Valida y recarga. La unidad de systemd ejecuta `vector validate` y envía `SIGHUP`, por lo que la configuración se aplica sin perder eventos: ```bash sudo -u vector vector validate /etc/vector/vector.yaml sudo systemctl reload vector ``` Repite las peticiones del paso 4 y añade una a `/health`. En el journal verás los dos primeros eventos con el campo `level` (`info` y `warning`) y ninguno para `/health`. ## Paso 6: Enviar los logs a Grafana Loki Cuando el pipeline produce los eventos que quieres, añade un destino real. Sustituye `your_loki_host` por la dirección de tu servidor Loki y añade este bloque dentro de `sinks`: ```yaml loki: type: loki inputs: - classify endpoint: http://your_loki_host:3100 encoding: codec: json labels: job: nginx host: "{{ host }}" level: "{{ level }}" ``` Usa como etiquetas de Loki solo campos con pocos valores distintos (`job`, `host`, `level`). Campos como `path` o `client` tienen miles de valores y degradan Loki; déjalos dentro de la línea JSON, donde puedes filtrarlos con LogQL. Antes de recargar, comprueba que Loki responde desde este servidor: ```bash curl http://your_loki_host:3100/ready ``` ```output ready ``` Valida y recarga Vector: ```bash sudo -u vector vector validate /etc/vector/vector.yaml sudo systemctl reload vector ``` `vector validate` ejecuta también el health check del destino de Loki, así que un error de conexión aparecerá aquí. Cuando todo funcione, puedes quitar el destino `console` para no llenar el journal. En Grafana, una consulta como `{job="nginx", level="error"}` mostrará las respuestas 5xx. > Consejo: si Loki está en otra red, envía los logs por la red privada o pon Loki tras un proxy con TLS y autenticación. El destino `loki` admite `auth` con `strategy: basic` para ese caso. ## Solución de problemas **`Permission denied` al leer `/var/log/nginx/access.log`.** El usuario `vector` debe pertenecer al grupo `adm`. Compruébalo con `id vector`; si falta, ejecuta `sudo usermod -aG adm vector` y reinicia el servicio (una recarga no aplica cambios de grupo). **El servicio no arranca tras un cambio.** La unidad ejecuta `vector validate` antes de iniciar, y si falla no arranca. Lee el motivo con `sudo journalctl -u vector -n 50 --no-pager`; los errores de VRL señalan la línea exacta del programa y el motivo. **No llega nada al destino.** Usa `vector tap parse_nginx` y luego `vector tap classify` para ver en qué componente desaparecen los eventos. Si `vector tap` no conecta, revisa que la sección `api` esté activada. **Eventos perdidos cuando Loki no está disponible.** Por defecto, cada destino usa un búfer en memoria de 500 eventos. Para cortes largos, configura en el destino un búfer en disco con `buffer.type: disk` y `buffer.max_size` en bytes. ## Conclusión Tienes Vector en Ubuntu 24.04 leyendo los logs de acceso de Nginx, convirtiéndolos en eventos estructurados con VRL, descartando el ruido y enviándolos a Grafana Loki, con validación antes de cada recarga. Como siguientes pasos puedes añadir una fuente `journald` para los logs de systemd, generar métricas a partir de los logs con la transformación `log_to_metric` o archivar una copia comprimida en un bucket S3 compatible con el destino `aws_s3`.