Skip to content

Manual instrumentation

Use track() when you are not using HTTP middleware — background jobs, queue workers, scripts, or custom outbound HTTP clients.

Node.js

typescript
import { AmlexiaClient } from '@amlexiahq/node';

const client = new AmlexiaClient({
  sdkKey: process.env.AMLEXIA_SDK_KEY!,
});

const start = Date.now();
try {
  await callStripe();
  await client.track({
    endpoint: 'POST stripe/charges',
    method: 'POST',
    statusCode: 200,
    latencyMs: Date.now() - start,
    provider: 'stripe',
  });
} catch (err) {
  await client.track({
    endpoint: 'POST stripe/charges',
    method: 'POST',
    statusCode: 500,
    latencyMs: Date.now() - start,
    provider: 'stripe',
    errorMessage: err instanceof Error ? err.message : 'unknown',
  });
  throw err;
}

Python

python
import time
from amlexia import AmlexiaClient

client = AmlexiaClient.from_env()
start = time.perf_counter()
try:
    call_openai()
    client.track(
        "POST openai/chat",
        "POST",
        200,
        int((time.perf_counter() - start) * 1000),
        provider="openai",
        model_name="gpt-4o",
    )
finally:
    client.shutdown()

Webhooks (inbound)

Mark inbound webhook handlers so they appear distinctly:

typescript
await client.track({
  endpoint: 'POST /webhooks/stripe',
  method: 'POST',
  statusCode: 200,
  latencyMs: 45,
  provider: 'stripe',
  isWebhook: true,
});

Tracing context

Attach trace ids for correlation with other events in the same request:

typescript
import { createTraceContext } from '@amlexiahq/node/tracing';

const ctx = createTraceContext({ serviceName: 'worker' });
await client.track({
  endpoint: 'job/send-digest',
  method: 'POST',
  statusCode: 200,
  latencyMs: 1200,
  traceId: ctx.traceId,
  spanId: ctx.spanId,
  serviceName: ctx.serviceName,
});

When to prefer middleware

Use middlewareUse manual track()
Express, FastAPI, Next routesCron, BullMQ, Celery
Standard request/responseCustom gRPC (label yourself)
Automatic path normalizationOne-off scripts