Skip to main content
The run log shows you exactly what happened in every run of your tasks. It is comprised of logs, traces, and spans.

Logs

You can use console.log(), console.error(), and other console methods as normal — they will appear in your run log. Any logs emitted by packages your task calls are also captured.

Using the logger object

We recommend using the logger export from @trigger.dev/sdk. It creates structured logs that include key-value metadata, making it easy to search and filter runs.
/trigger/logging-example.ts
import { task, logger } from "@trigger.dev/sdk";

export const loggingExample = task({
  id: "logging-example",
  run: async (payload: { data: Record<string, string> }) => {
    // First argument: message. Second argument: key-value object (Record<string, unknown>)
    logger.debug("Debug message", payload.data);
    logger.log("Log message", payload.data);
    logger.info("Info message", payload.data);
    logger.warn("You've been warned", payload.data);
    logger.error("Error message", payload.data);
  },
});

Log levels

MethodLevelUse case
logger.debug()DEBUGVerbose diagnostic info, hidden by default
logger.log()LOGGeneral log messages
logger.info()INFOInformational messages about task progress
logger.warn()WARNNon-fatal issues that should be reviewed
logger.error()ERRORErrors that affect task execution

Tracing and spans

Trigger.dev uses OpenTelemetry tracing under the hood. Automatic tracing is provided for:
NameDescription
Task triggersWhen a task is triggered
Task attemptsEach attempt of a task run
HTTP requestsOutgoing HTTP requests made by your code

Adding instrumentations

You can add instrumentations in your trigger.config.ts. For example, the Prisma instrumentation automatically traces all Prisma queries.

Custom traces

Use logger.trace() to create a custom OpenTelemetry span around any block of code. You can set attributes on the span and return a value from the callback.
/trigger/custom-trace.ts
import { logger, task } from "@trigger.dev/sdk";

export const customTrace = task({
  id: "custom-trace",
  run: async (payload) => {
    const user = await logger.trace("fetch-user", async (span) => {
      span.setAttribute("user.id", "1");

      // ... fetch user from database ...

      return {
        id: "1",
        name: "John Doe",
        fetchedAt: new Date(),
      };
    });

    logger.info("Fetched user", { name: user.name });
  },
});

Metrics

Trigger.dev collects system and runtime metrics automatically for deployed tasks, and provides an API for recording custom metrics using OpenTelemetry. You can view metrics in query them with TRQL, and export them to external services via telemetry exporters.

Custom metrics API

Import otel from @trigger.dev/sdk and use the standard OpenTelemetry Metrics API. Create instruments at module level — outside the run function — so they are reused across runs.
/trigger/metrics.ts
import { task, logger, otel } from "@trigger.dev/sdk";

// Create a meter — instruments must be created once at module level
const meter = otel.metrics.getMeter("my-app");

const itemsProcessed = meter.createCounter("items.processed", {
  description: "Total number of items processed",
  unit: "items",
});

const itemDuration = meter.createHistogram("item.duration", {
  description: "Time spent processing each item",
  unit: "ms",
});

const queueDepth = meter.createUpDownCounter("queue.depth", {
  description: "Current queue depth",
  unit: "items",
});

export const processQueue = task({
  id: "process-queue",
  run: async (payload: { items: string[] }) => {
    queueDepth.add(payload.items.length);

    for (const item of payload.items) {
      const start = performance.now();

      // ... process item ...

      const elapsed = performance.now() - start;

      itemsProcessed.add(1, { "item.type": "order" });
      itemDuration.record(elapsed, { "item.type": "order" });
      queueDepth.add(-1);
    }

    logger.info("Queue processed", { count: payload.items.length });
  },
});

Available instrument types

InstrumentMethodUse case
Countermeter.createCounter()Monotonically increasing values (items processed, requests sent)
Histogrammeter.createHistogram()Distributions of values (durations, sizes)
UpDownCountermeter.createUpDownCounter()Values that go up and down (queue depth, active connections)
All instruments accept optional attributes when recording values. Attributes let you break down metrics by dimension (e.g., by item type, status, or region).

Automatic system and runtime metrics

Trigger.dev automatically collects the following metrics for deployed tasks. No configuration is needed. Requires SDK version 4.4.1 or later.
Metric nameTypeUnitDescription
process.cpu.utilizationgaugeratioProcess CPU usage (0–1)
process.cpu.timecountersecondsCPU time consumed
process.memory.usagegaugebytesProcess memory usage
nodejs.event_loop.utilizationgaugeratioEvent loop utilization (0–1)
nodejs.event_loop.delay.p95gaugesecondsEvent loop delay p95
nodejs.event_loop.delay.maxgaugesecondsEvent loop delay max
nodejs.heap.usedgaugebytesV8 heap used
nodejs.heap.totalgaugebytesV8 heap total
In dev mode (trigger dev), only process.* and custom metrics are available.

Context attributes

All metrics (both automatic and custom) are tagged with run context so you can filter and group them:
  • run_id — the run that produced the metric
  • task_identifier — the task slug
  • attempt_number — the attempt number
  • machine_name — the machine preset (e.g., small-1x)
  • worker_version — the deployed worker version
  • environment_typePRODUCTION, STAGING, DEVELOPMENT, or PREVIEW

Querying metrics

Use TRQL to query metrics data. For example, to see average CPU utilization over time:
SELECT
  timeBucket(),
  avg(value) AS avg_cpu
FROM metrics
WHERE metric_name = 'process.cpu.utilization'
GROUP BY timeBucket
ORDER BY timeBucket
LIMIT 1000
See the Query page for the full metrics table schema.

Exporting metrics

You can send metrics to external observability services (Axiom, Honeycomb, Datadog, etc.) by configuring telemetry exporters in your trigger.config.ts.

Build docs developers (and LLMs) love