With a destination configured, Elide records these without code changes:
| Area | Spans | Metrics | Setting |
|---|---|---|---|
| Served HTTP requests | SERVER span per request | http., http., elide. | runtime.traces, runtime.metrics |
fetch | CLIENT span per request | http. | runtime.traces, runtime.metrics |
| Process | — | CPU time, memory, threads, file descriptors, uptime | runtime.metrics |
| Errors | exception events | elide.errors | follows logs, traces, metrics |
elide build, elide test, elide install | Command, task, and test spans | — | runtime.traces |
| Elide’s own logs | — | — | runtime.logs |
Names, units, and attributes are listed in Emitted telemetry.
Serving
Every request served by elide serve, an exported fetch handler, or a node:http server gets a server span and
the HTTP server metrics. The handler runs inside the span, so spans your code starts there are its children:
// server.ts
import { trace } from "@opentelemetry/api";
const tracer = trace.getTracer("orders");
export default {
async fetch(request: Request): Promise<Response> {
return tracer.startActiveSpan("load order", async (span) => {
span.setAttribute("order.id", new URL(request.url).searchParams.get("id") ?? "");
span.end();
return new Response("ok\n");
});
},
};OTEL_EXPORTER_OTLP_ENDPOINT=http://localhost:4318 elide serve server.tsA request carrying a valid traceparent continues the caller’s trace. A 5xx response, a handler that throws, an
abandoned response, or a reset connection marks the server span ERROR.
Routes
Server spans are named after the method: GET. A node:http server can name the matched route, which sets
http.route and renames the span GET /items/:id:
// routes.ts
import http from "node:http";
import { trace } from "@opentelemetry/api";
http
.createServer((req, res) => {
trace.getActiveSpan()?.setAttribute("http.route", "/items/:id");
res.end("ok\n");
})
.listen(8091);A router that sets req.route (Express and compatible routers) supplies the route without that line; req.baseUrl
is prefixed. Inside a node:http handler or an exported fetch handler the active span stands for the server
span, and only http.route set on it reaches the exported span.
fetch
Each fetch gets a client span, parented to the span active where fetch was called, and sends traceparent and
tracestate so the next service continues the trace. A traceparent header you set yourself is kept.
import { trace } from "@opentelemetry/api";
await trace.getTracer("sync").startActiveSpan("sync inventory", async (span) => {
await fetch("https://inventory.example.com/items"); // child CLIENT span
span.end();
});Process metrics
process.cpu.time, process.memory.usage, process.thread.count, process.unix.file_descriptor.count, and
process.uptime, collected at each metric export on Linux and macOS.
Builds and tests in CI
elide build, elide test, and elide install record a root span for the command (elide.build, elide.test,
elide.install). Build stages and tasks become child spans with outcome and cache-hit attributes, and each test case
becomes a child of elide.test. The root span continues a W3C TRACEPARENT from the environment, so a CI job’s own
trace can include the build:
TRACEPARENT=00-4bf92f3577b34da6a3ce929d0e0e4736-00f067aa0ba902b7-01 \
OTEL_EXPORTER_OTLP_ENDPOINT=https://otel.example.com \
elide testThe command span carries elide.ci.* attributes from GitHub Actions, GitLab CI, Buildkite, and CircleCI variables
(see Emitted telemetry) and process.exit.code. Elide waits up to 5 seconds
for the export before the command returns.
In GitHub Actions:
- name: Test
run: elide test
env:
OTEL_EXPORTER_OTLP_ENDPOINT: ${{ vars.OTEL_ENDPOINT }}
OTEL_EXPORTER_OTLP_HEADERS: ${{ secrets.OTEL_HEADERS }}
OTEL_SERVICE_NAME: my-service-ciElide’s own logs
Elide’s warnings and errors are exported as log records in the dev.elide.runtime scope, at or above runtime.logs
(warn by default), with the active span’s ids. Set runtime { logs = "off" } to stop them.
Not instrumented yet
| Area | Workaround |
|---|---|
node:http and node:https client requests: no client span, no traceparent | Inject headers with propagation.inject; see Trace context |
Python HTTP clients (urllib, requests) | Inject headers with opentelemetry. |
| Serving from Python | Serve from JavaScript or TypeScript |
| Garbage collection and event-loop delay metrics | — |
| Database, file system, and child process spans | Create spans in your code |
| Java and Kotlin programs | Not supported; see Languages |