Enrichers

Enrichers Overview

Enrich your wide events with derived context like user agent, geo data, request size, and trace context. Built-in enrichers and custom enricher support.

Enrichers add derived context to your wide events after they are emitted, before they reach your drain adapters. Use them to automatically extract useful information from request headers without cluttering your application code.

How Enrichers Work

Enrichers hook into the evlog:enrich event, which fires after a wide event is emitted and before the evlog:drain hook. The enricher receives the event and request metadata, and can mutate the event to add derived fields.

Request → emit() → evlog:enrich → evlog:drain
                    ↑ enrichers      ↑ adapters
                    add context      send to services
server/plugins/evlog-enrich.ts
import { createUserAgentEnricher, createGeoEnricher } from 'evlog/enrichers'

export default defineNitroPlugin((nitroApp) => {
  const enrichers = [
    createUserAgentEnricher(),
    createGeoEnricher(),
  ]

  nitroApp.hooks.hook('evlog:enrich', (ctx) => {
    for (const enricher of enrichers) enricher(ctx)
  })
})

Enrich Context

Every enricher receives an EnrichContext with:

FieldTypeDescription
eventWideEventThe emitted wide event (mutable)
requestobjectRequest metadata (method, path, requestId)
headersobjectSafe HTTP request headers (sensitive headers are filtered)
responseobjectResponse metadata (status, headers)
Security: Sensitive headers (authorization, cookie, x-api-key, etc.) are automatically filtered and never passed to enrichers.

Available Enrichers

User Agent

Parse browser, OS, and device type from the User-Agent header.

Geo

Extract country, region, city, and coordinates from platform headers.

Request Size

Capture request and response payload sizes from Content-Length headers.

Trace Context

Extract W3C trace context (traceId, spanId) from the traceparent header.

Custom

Write your own enricher for any derived context.

Overwrite Behavior

By default, enrichers preserve existing fields. If your application code already sets event.userAgent, the enricher won't overwrite it. Pass { overwrite: true } to change this:

createUserAgentEnricher({ overwrite: true })

Next Steps

Copyright © 2026