madapes

@aurora/runtime-observability (0.3.3)

Published 2025-12-27 10:44:39 +00:00 by vlad

Installation

@aurora:registry=
npm install @aurora/runtime-observability@0.3.3
"@aurora/runtime-observability": "0.3.3"

About this package

@aurora/runtime-observability

Observability primitives for Aurora applications - logging and metrics.

Overview

Aurora's observability package provides:

  • Structured logging
  • Prometheus-compatible metrics
  • Correlation IDs for request tracing

Installation

bun add @aurora/runtime-observability

Logging

Logger

import { Logger } from "@aurora/runtime-observability";

const logger = new Logger({
  level: "info",  // debug, info, warn, error
  format: "json", // json or text
});

// Log levels
logger.debug("Detailed debug info", { orderId: "123" });
logger.info("Order created", { orderId: "123", userId: "456" });
logger.warn("Order processing slow", { orderId: "123", duration: 5000 });
logger.error("Order creation failed", { orderId: "123", error: err.message });

Structured Logs

// JSON format
{
  "level": "info",
  "timestamp": "2024-12-26T10:30:00Z",
  "message": "Order created",
  "context": {
    "orderId": "123",
    "userId": "456",
    "tenantId": "tenant-1"
  }
}

Correlation IDs

import { createCorrelationId } from "@aurora/runtime-observability";

const correlationId = createCorrelationId();

logger.info("Processing request", {
  correlationId,
  path: "/api/v1/orders",
});

// All logs in this request use the same correlationId

Child Loggers

const orderLogger = logger.child({ module: "orders" });
const paymentLogger = logger.child({ module: "payments" });

orderLogger.info("Order created", { orderId: "123" });
paymentLogger.info("Payment processed", { paymentId: "456" });

Metrics

Metrics Registry

import { Metrics } from "@aurora/runtime-observability";

const metrics = new Metrics({
  prefix: "aurora",
  labels: {
    node_id: process.env.NODE_ID,
    environment: process.env.NODE_ENV,
  },
});

Counter

const ordersCreated = metrics.counter("orders_created", "Number of orders created");

// Increment
ordersCreated.inc();

// Increment with labels
ordersCreated.inc({ tenant_id: "tenant-1" });
ordersCreated.inc({ tenant_id: "tenant-2" });

// Increment by value
ordersCreated.inc({ tenant_id: "tenant-1" }, 5);

Gauge

const activeConnections = metrics.gauge("active_connections", "Number of active connections");

// Set value
activeConnections.set(10);

// Set with labels
activeConnections.set({ shard_id: "shard-1" }, 5);

// Increment/decrement
activeConnections.inc();
activeConnections.dec();

Histogram

const requestDuration = metrics.histogram(
  "http_request_duration_seconds",
  "HTTP request duration in seconds",
  [0.001, 0.005, 0.01, 0.05, 0.1, 0.5, 1, 5]  // Buckets
);

// Observe duration
const start = Date.now();
await processRequest();
requestDuration.observe((Date.now() - start) / 1000);

Summary

const requestSize = metrics.summary("http_request_size_bytes", "HTTP request size in bytes");

// Observe value
requestSize.observe(1024);
requestSize.observe(2048);

Prometheus Endpoint

import { Server } from "@aurora/runtime-http";
import { Metrics } from "@aurora/runtime-observability";

const metrics = new Metrics({ prefix: "aurora" });

const server = new Server({ port: 3000 });

// Expose /metrics endpoint
server.get("/metrics", () => {
  const metricsOutput = metrics.collect();
  return new Response(metricsOutput, {
    headers: { "Content-Type": "text/plain" },
  });
});

await server.start();

Example Output

# HELP aurora_orders_created_total Number of orders created
# TYPE aurora_orders_created_total counter
aurora_orders_created_total{tenant_id="tenant-1"} 42
aurora_orders_created_total{tenant_id="tenant-2"} 17

# HELP aurora_http_request_duration_seconds HTTP request duration in seconds
# TYPE aurora_http_request_duration_seconds histogram
aurora_http_request_duration_seconds_bucket{le="0.001"} 5
aurora_http_request_duration_seconds_bucket{le="0.005"} 23
aurora_http_request_duration_seconds_bucket{le="+Inf"} 100
aurora_http_request_duration_seconds_sum 2.345
aurora_http_request_duration_seconds_count 100

Integration

With HTTP Server

import { Server, Middleware } from "@aurora/runtime-http";
import { Logger, Metrics } from "@aurora/runtime-observability";

const logger = new Logger({ level: "info" });
const metrics = new Metrics({ prefix: "aurora" });

const requestDuration = metrics.histogram("http_request_duration_seconds", "Request duration");

const loggingMiddleware: Middleware = async (req, next) => {
  const correlationId = req.headers.get("X-Correlation-ID") || createCorrelationId();
  
  (req as any).correlationId = correlationId;
  
  const start = Date.now();
  const response = await next(req);
  const duration = (Date.now() - start) / 1000;
  
  logger.info("HTTP request", {
    correlationId,
    method: req.method,
    path: req.url,
    status: response.status,
    duration,
  });
  
  requestDuration.observe(duration, {
    method: req.method,
    path: req.url,
    status: response.status.toString(),
  });
  
  response.headers.set("X-Correlation-ID", correlationId);
  return response;
};

const server = new Server({ port: 3000 });
server.use(loggingMiddleware);

With EventLog

import { EventLog } from "@aurora/runtime-eventlog";
import { Logger, Metrics } from "@aurora/runtime-observability";

const logger = new Logger({ level: "info" });
const metrics = new Metrics({ prefix: "aurora" });

const eventsAppended = metrics.counter("events_appended_total", "Events appended to JetStream");
const eventErrors = metrics.counter("event_errors_total", "Event processing errors");

class InstrumentedEventLog implements EventLog {
  async append(event: Event) {
    try {
      await this.nats.publish(event);
      eventsAppended.inc({ event_type: event.type });
      logger.info("Event appended", { eventId: event.id, type: event.type });
    } catch (error) {
      eventErrors.inc({ event_type: event.type });
      logger.error("Event append failed", { error: error.message });
      throw error;
    }
  }
}

Labels

Labels provide dimensions to metrics:

const ordersCreated = metrics.counter("orders_created_total", "Orders created", {
  tenant_id: "default",
  environment: "production",
});

// Override labels
ordersCreated.inc({ tenant_id: "tenant-1", environment: "production" });
ordersCreated.inc({ tenant_id: "tenant-2", environment: "production" });

License

MIT

Dependencies

Dependencies

ID Version
prom-client ^15.1.0
Details
npm
2025-12-27 10:44:39 +00:00
3
latest
5.2 KiB
Assets (1)
Versions (3) View all
0.3.3 2025-12-27
0.3.2 2025-12-27
0.3.1 2025-12-27