RUNTIME ATLAS / DOCUMENTATION

Make a real request path
read like architecture.

Runtime Atlas combines TypeScript declarations with bounded runtime traces. It shows a source-backed topology immediately, then animates and replays the causal path of recent Node.js requests.

MITNode.js 24TypeScriptLocal-first
What it is — and is not

Runtime Atlas is a developer observability tool. It is not a durable tracing database, metrics/logs platform, cross-replica store, or public multi-tenant service.

01 / GET STARTED

Quick start

Install the runtime pinned in .nvmrc, install the locked dependency graph, and start the collector plus Vite UI together.

NODE.JS24.15.0pinned development runtime
PACKAGE MANAGERnpm 11lockfile-backed install
SUPPORTED DEV OSmacOS / LinuxUbuntu verified in CI
terminal
git clone https://github.com/OthmaneBlial/Runtime-Atlas.git
cd Runtime-Atlas
nvm install && nvm use
npm ci && npm run dev

Open the loopback URL printed by Vite — normally http://127.0.0.1:5173, or the next available port. The API and collector run at 127.0.0.1:4319.

02 / EXPLORE

Local demo

The demo topology appears before traffic arrives. Run one of three deterministic scenarios from the workspace, then select trace history, scrub replay, inspect a node, export, or clear the retained evidence.

POST/checkout

Successful order path across session, cart, pricing, dependencies, and fulfillment.

GET/search

Smaller read path through rate limiting, catalog data, and cache.

FAIL/payment

Deterministic payment dependency outage with an observable error path.

The downstream operations are simulated local delays; they do not call Stripe, PostgreSQL, Redis, Kafka, or TaxJar.
03 / CONNECT

Instrument with the Node.js SDK

The workspace package @runtime-atlas/sdk emits trace and span lifecycle events while keeping observed application requests independent from collector availability. It is currently a local workspace artifact, not a claimed public registry release.

Build and link the workspace package

terminal
npm run build:sdk

Wrap application work

instrumented-orders.ts
import { createAtlas } from "@runtime-atlas/sdk";

const atlas = createAtlas({
  serviceName: "orders-api",
  collectorUrl: "http://127.0.0.1:4319",
  maxQueueSize: 2_000,
  requestTimeoutMs: 3_000,
  onError: (error) =>
    applicationLogger.warn({ error }, "atlas collector unavailable"),
});

const ordersDb = atlas.database(
  { id: "db.orders", label: "Orders DB", meta: { engine: "PostgreSQL" } },
  async () => saveOrder(),
);

const createOrder = atlas.route(
  { id: "route.orders", label: "POST /orders" },
  async () => ordersDb(),
);

Use request middleware safely

Connect/Express applications can use atlas.httpMiddleware(). Normalize user-specific path segments before telemetry leaves the process; the SDK removes query strings and URL fragments but cannot know which remaining segments identify a user.

app.ts
app.use(
  atlas.httpMiddleware({
    path: (request) =>
      (request.originalUrl ?? request.url ?? "/").replace(
        /\/\d+(?=\/|$)/g,
        "/:id",
      ),
    ignore: (request) => request.url === "/health",
  }),
);

Download the complete TypeScript example Browse SDK source

04 / CONNECT

Connect OpenTelemetry

Configure an OTLP/HTTP exporter to send JSON to the exact traces endpoint. Uncompressed and gzip-compressed OTLP JSON are supported. Binary protobuf and gRPC are intentionally not accepted.

POSThttp://127.0.0.1:4319/v1/traces

Test the bundled payload

terminal
curl --request POST http://127.0.0.1:4319/v1/traces \
  --header 'content-type: application/json' \
  --data-binary @examples/otlp-trace.json

Span reconciliation order

  1. 01
    Explicit node IDruntime.atlas.node_id
  2. 02
    Code provenancecode.function.name · code.file.path · code.line.number
  3. 03
    HTTP evidencehttp.request.method · http.route
  4. 04
    Bounded inferencedatabase · messaging · service · code allowlist
Partial success is explicit

Malformed or incomplete individual spans are counted in OTLP partialSuccess. Malformed envelopes and capacity violations return protobuf-JSON google.rpc.Status errors.

Download the standards-shaped OTLP payload

05 / CONNECT

Point the analyzer at TypeScript

Configure one or more comma-separated source globs. The analyzer uses ts-morph without executing the target application.

terminal
ATLAS_SOURCE_GLOB='../orders-api/src/**/*.ts' \
ATLAS_PROJECT_NAME='orders-api' \
ATLAS_ENVIRONMENT='development' \
npm start
atlas.routeatlas.middlewareatlas.service atlas.databaseatlas.cacheatlas.externalatlas.queue

Calls may live inside application factories. IDs, labels, metadata, and source locations must remain literal enough to prove. Dynamic descriptors or wrappers that hide these call shapes may appear only as visibly runtime-only nodes.

06 / OPERATE

Architecture

The Express application owns analysis, validation, ingestion, retained trace state, SSE, and the production UI. The process boundary owns configuration, structured logs, sockets, and graceful shutdown.

Ordered runtime model

trace:startspan:startspan:finish / errortrace:finish

Each event receives an increasing collector sequence. The UI uses that sequence rather than service clocks to follow the newest evidence and compute replay state.

Read the source architecture note

07 / OPERATE

HTTP surface

Every response receives a request ID and restrictive browser security headers.

Method Endpoint Purpose
GET /health Lightweight process liveness
GET /ready Topology, production UI, and runtime readiness
GET /api/topology AST-derived topology and enabled capabilities
GET /api/source Analyzer-approved source context window
GET /api/traces Recent bounded in-memory history
GET /api/traces/export Download retained traces as JSON
DELETE /api/traces Clear history when enabled
GET /api/stream SSE runtime events and heartbeats
POST /api/ingest First-party SDK batches
POST /v1/traces OTLP/HTTP JSON traces
POST /api/demo/checkout Deterministic success trace
GET /api/demo/search Shared-infrastructure trace
POST /api/demo/failure Deterministic dependency failure
08 / OPERATE

Configuration

The server reads environment variables directly and does not auto-load .env files. Invalid configuration fails before the listener starts.

Variable Default Purpose
HOST 127.0.0.1 Listener; use non-loopback only in a controlled network
PORT 4319 API, collector, SSE, and production UI
ATLAS_SOURCE_GLOB demo source Comma-separated TypeScript source globs
ATLAS_PROJECT_NAME demo / project Displayed project name
ATLAS_ENVIRONMENT local Displayed environment label
ATLAS_INGEST_TOKEN unset Optional bearer token, minimum 16 characters
ATLAS_EXPOSE_SOURCE loopback only Enable analyzer-approved source context
ATLAS_ALLOW_CLEAR local demo only Enable trace deletion API and control
ATLAS_TRUST_PROXY false Trust one reverse-proxy hop
ATLAS_LOG_LEVEL info debug, info, warn, error, or silent
ATLAS_OTLP_BODY_LIMIT 8mb Decompressed OTLP JSON limit
ATLAS_OTLP_MAX_SPANS 1000 Maximum span groups per OTLP request
ATLAS_OTLP_MAX_CONCURRENT_REQUESTS 16 OTLP conversion concurrency
ATLAS_INGEST_RATE_LIMIT 600 Ingest requests per client per minute
ATLAS_MAX_TRACES 60 In-memory trace retention
ATLAS_MAX_BUFFERED_EVENTS 800 SSE replay buffer
ATLAS_MAX_EVENTS_PER_TRACE 5000 Per-trace event retention
ATLAS_MAX_RETAINED_EVENTS 50000 Aggregate retained events
ATLAS_MAX_STREAM_CLIENTS 100 Concurrent SSE clients per process
ATLAS_SHUTDOWN_TIMEOUT_MS 10000 Graceful shutdown deadline
09 / OPERATE

Privacy and security boundaries

Trace evidence stays in process memory. Restarting the server clears it; authorized users may also clear it through the UI when that capability is enabled.

RETAINED, WITH BOUNDS
  • Trace and span IDs, parents, timestamps, durations, status
  • Bounded method and normalized path
  • Configured node IDs and service names
  • Allowlisted operation, code, route, database, and messaging evidence
  • Bounded error messages
NOT RETAINED
  • url.full, query strings, or URL fragments
  • Database statements
  • Request or response bodies
  • Credentials
  • Arbitrary OpenTelemetry attributes

Source inspection

/api/source returns a small context window only when the exact file and line belong to an analyzed node. It defaults on for loopback and off for non-loopback bindings.

Shared network rule

Do not expose Runtime Atlas directly to the public internet.

Terminate TLS and require user authentication at a trusted reverse proxy. Configure a long ingest token and keep source inspection and trace clearing disabled unless every viewer is authorized.

Privacy model Security policy

10 / OPERATE

Production and container deployment

Compiled Node.js process

terminal
nvm use
npm ci
npm run build
NODE_ENV=production npm start

Open http://127.0.0.1:4319. GET /health proves liveness; GET /ready also analyzes the configured source and verifies the built UI.

Hardened local container

terminal
docker compose up --build

The image runs as the unprivileged node user. Compose binds the exposed port to loopback, uses a read-only filesystem, and enables demo-only source and clear controls.

Shared network checklist

  • Terminate TLS and require user authentication at a reverse proxy.
  • Generate an ATLAS_INGEST_TOKEN of at least 16 characters.
  • Keep source inspection and trace clearing disabled unless explicitly needed.
  • Trust a proxy hop only when the deployment actually uses that trusted topology.
  • Tune body, span, concurrency, rate, event, trace, and SSE limits for available memory.
  • Use one process per instance; in-memory trace state is not coordinated across replicas.

On SIGINT or SIGTERM, the server closes SSE clients, stops accepting new connections, waits for active sockets, then enforces the configured shutdown deadline. Rollback requires no persistent schema migration.

11 / OPERATE

Validation

The repository exposes one complete local gate:

terminal
npm run check
STATICPrettier · oxlint · TypeScript
BEHAVIORUnit · component · integration
BROWSERChrome desktop · Pixel 7 · axe
BUILDSDK · server · React UI
POLICYRepository files · credential signatures · docs links
RUNTIMECompiled startup · success + failure smoke · asset budgets

Browser tests fail on unexpected console errors, page exceptions, failed requests, HTTP errors, accessibility violations, or mobile horizontal overflow. The production smoke enforces 100 KiB JavaScript and 20 KiB CSS gzip entry-asset budgets.

focused commands
npm test
npm run test:e2e
npm run typecheck
npm run lint
npm run build
npm run smoke
npm audit --omit=dev --audit-level=high
docker build --tag runtime-atlas:local .
12 / SUPPORT

Troubleshooting

The UI shows a connection error

In development, Vite and the API must both run. Start them with npm run dev, check http://127.0.0.1:4319/health, then use Retry connection.

Readiness returns 503

Check the structured readiness.failed log. Common causes are an empty or excessive source glob, duplicate node IDs, or a missing dist/index.html. Run npm run build before npm start.

Static nodes are missing

Keep the declaration shape literal: atlas.service({ id: "…", label: "…" }, handler). Dynamic descriptors and calls hidden behind wrappers cannot be proven statically.

The collector returns 401

The server has ATLAS_INGEST_TOKEN configured. Send the exact value as Authorization: Bearer …. Never put it in source, URLs, or logs.

The OTLP collector returns 415

Use OTLP/HTTP JSON at /v1/traces with Content-Type: application/json. Binary protobuf and gRPC are not supported; gzip content encoding is.

The OTLP response reports partialSuccess

The envelope was valid, but one or more resource/span groups were malformed, incomplete, or over a configured bound. Use the rejected count to inspect exporter configuration without logging sensitive payloads.

A trace does not appear

Confirm first-party ingest returned 202 or OTLP returned 200. Check retention limits and service clocks. If the browser disconnected, reconnect so the bounded server event buffer can replay.

Port 4319 is already in use

Use another server port such as PORT=4320 npm run dev:server, then update the Vite proxy target, or stop the conflicting process.

Playwright cannot launch Chrome

Install or update Google Chrome, confirm it launches, and rerun npm run test:e2e. The tests use the installed Chrome channel rather than a downloaded browser binary.

13 / BOUNDARIES

Compatibility, limits, and support

RUNTIME

Node.js ^22.22.2, ^24.15.0, or ≥26. Node 24.15.0 is pinned for development and CI.

BROWSER

Evergreen browsers with ES modules, SVG foreignObject, SSE, and color-mix(). Chrome is automated; Firefox and Safari remain release checks.

STATE

Telemetry is in memory, per process, and deliberately not durable or replicated.

STATIC PROOF

The analyzer favors provable TypeScript call shapes over speculative inference.

Use GitHub Issues for reproducible bugs and focused feature requests. Security reports belong in the repository’s private vulnerability process, not a public issue.