
Security News
Attackers Are Hunting High-Impact Node.js Maintainers in a Coordinated Social Engineering Campaign
Multiple high-impact npm maintainers confirm they have been targeted in the same social engineering campaign that compromised Axios.
@emeryld/obs-stack
Advanced tools
Docker Compose-based Grafana + Tempo + Loki + OpenTelemetry Collector stack
A Docker Compose bundle that wires Grafana, Tempo, Loki, and an OpenTelemetry Collector together with a lightweight Node CLI for managing the stack from anywhere in the workspace.
pnpm install
cp packages/obs-stack/.env.example packages/obs-stack/.env
packages/obs-stack/.env if you hit conflicts. The compose stack already declares persistent volumes (grafana-data, tempo-data, loki-data) so dashboards, traces, and logs survive restarts.pnpm --filter @emeryld/obs-stack obs-stack up
The CLI sets OBS_STACK_DIR to the packages/obs-stack directory so every docker compose run sees the Grafana provisioning and config files no matter where you invoke the command. If you manage the stack by calling docker compose directly, either run the command from packages/obs-stack or set OBS_STACK_DIR (for example OBS_STACK_DIR=packages/obs-stack docker compose up) so the bind mounts keep pointing at grafana/provisioning/dashboards/files.pnpm --filter @emeryld/obs-stack obs-stack urls
The CLI loads packages/obs-stack/.env and also merges in any .env file that lives beside the directory where you run the command, so you can keep machine-specific overrides outside of version control.
obs-stack up [...] – starts the stack (docker compose up -d plus any extra args you pass).obs-stack down [...] – stops the containers without deleting persistent volumes.obs-stack reset [...] – runs docker compose down -v so you can start from scratch.obs-stack status [...] – shows docker compose ps for the stack so you can see container health.obs-stack logs [...] – tails all services (docker compose logs --follow --tail 100 [...]). Pass service names or additional flags to limit the stream.obs-stack urls – prints the Grafana, Tempo, Loki, and OTLP host endpoints using your current .env overrides.Each command ensures both docker and docker compose are available before delegating to Compose. Run the CLI from the workspace root via pnpm --filter @emeryld/obs-stack obs-stack <command> so it can find the Compose file and configs, or cd packages/obs-stack and run the same command if you prefer.
Run the CLI with no arguments to launch the helper menu from a terminal:
pnpm --filter @emeryld/obs-stack obs-stack
You can also pass menu, --menu, --interactive, or -m to open it explicitly. The menu lets you pick bring-up, stop, reset, status, logs, or URLs by pressing the numbered keys.
The legacy obs-stack-menu binary is still published (and available via pnpm --filter @emeryld/obs-stack obs-stack-menu) for backwards compatibility.
| Name | Description | Default |
|---|---|---|
GRAFANA_PORT | Host port forwarded to Grafana | 3000 |
GRAFANA_USER | Grafana admin user (provisioned) | admin |
GRAFANA_PASS | Grafana admin password (provisioned) | admin |
OTEL_OTLP_HTTP_PORT | Host port forwarded to OTLP HTTP (4318 inside the collector) | 4318 |
OTEL_OTLP_GRPC_PORT | Host port forwarded to OTLP gRPC (4317 inside the collector) | 4317 |
LOKI_PORT | Host port forwarded to Loki query API (3100) | 3100 |
TEMPO_HTTP_PORT | Host port forwarded to Tempo query API (3200) | 3200 |
Override any of these by editing packages/obs-stack/.env, creating another .env alongside your working directory, or exporting the variables before running the CLI.
cp packages/obs-stack/.env.example packages/obs-stack/.env
pnpm obs-stack up
pnpm obs-stack status
pnpm obs-stack urls
pnpm obs-stack logs # add service names or flags if you need to scope the output
obs-stack urls prints the host ports for Grafana, Tempo, Loki, and both OTLP endpoints so you can plug them into clients or instrumentation.
@emeryld/otel-bootstrap into your backend workspace:
pnpm add @emeryld/otel-bootstrap
Then either import "@emeryld/otel-bootstrap"; as early as possible in your entry point or preload it via NODE_OPTIONS="--require ./node_modules/@emeryld/otel-bootstrap/dist/otel.cjs" when running node so traces + logs are configured automatically.OTEL_EXPORTER_OTLP_ENDPOINT=http://otel-collector:4318
OTEL_EXPORTER_OTLP_PROTOCOL=http/protobuf
OTEL_EXPORTER_OTLP_ENDPOINT=http://localhost:${OTEL_OTLP_HTTP_PORT}
OTEL_EXPORTER_OTLP_PROTOCOL=http/protobuf
OTEL_SERVICE_NAME and OTEL_RESOURCE_ATTRIBUTES defined so traces/logs carry meaningful service metadata.Once telemetry is flowing, Grafana Explore (Tempo + Loki) will start showing traces and logs with matching trace_id values.
If you want your backend inside the same Docker network as the observability stack (so it can target otel-collector by name and share volumes), use the override example:
cd packages/obs-stack
docker compose -f docker-compose.yml -f examples/docker-compose.override.yml up -d
Adjust the backend service inside examples/docker-compose.override.yml to match your build image, ports, and runtime command. The override already makes the service depend on otel-collector and sets its OTLP exports to http://otel-collector:4318.
Grafana relies on the datasources defined in grafana/provisioning/datasources/datasources.yaml to wire up Loki and Tempo automatically. You never need to configure the data sources manually—just open Grafana at the URL reported by obs-stack urls.
Each datasource now exposes a stable uid (loki and tempo) so the shipping dashboards can reference them reliably.
We also preload three starter dashboards via grafana/provisioning/dashboards/. Each JSON file targets the Loki datasource (uid loki) so they work out of the box:
Edit the JSON in grafana/provisioning/dashboards/files/ (or export updates from Grafana) and restart the stack or reload dashboards to see your changes automatically.
packages/obs-stack/.env (or your local override), then run pnpm --filter @emeryld/obs-stack obs-stack reset to recreate the stack with the new settings.OBS_STACK_DIR environment variable points at packages/obs-stack (the CLI sets it automatically) so Grafana sees grafana/provisioning/dashboards/files. Running docker compose without OBS_STACK_DIR from another directory binds an empty host path and Grafana keeps logging stat /etc/grafana/provisioning/dashboards/files: no such file or directory; once the variable points at the stack, restart with obs-stack reset.tempo and loki. The CLI always runs Compose inside the package directory so no host networking is required.docker compose not on PATH: install Docker Desktop (Mac/Windows) or Docker Engine with the Compose plugin (Linux) so both docker and docker compose can run.The package ships with a lightweight Node test suite that enforces that the Compose stack is wired up the way the README describes. Run it with:
pnpm --filter @emeryld/obs-stack test
The tests check that the services/all volumes exist, host networking is avoided, Grafana data sources point at the local Loki/Tempo, the collector exports to both Loki and Tempo, configs keep 24h retention, and the env example still documents the exposed ports.
FAQs
Docker Compose-based Grafana + Tempo + Loki + OpenTelemetry Collector stack
We found that @emeryld/obs-stack demonstrated a healthy version release cadence and project activity because the last version was released less than a year ago. It has 1 open source maintainer collaborating on the project.
Did you know?

Socket for GitHub automatically highlights issues in each pull request and monitors the health of all your open source dependencies. Discover the contents of your packages and block harmful activity before you install or update your dependencies.

Security News
Multiple high-impact npm maintainers confirm they have been targeted in the same social engineering campaign that compromised Axios.

Security News
Axios compromise traced to social engineering, showing how attacks on maintainers can bypass controls and expose the broader software supply chain.

Security News
Node.js has paused its bug bounty program after funding ended, removing payouts for vulnerability reports but keeping its security process unchanged.