Move docs/ package mirror into document-navigator plugin
Relocate the ~6k-file docs tree from the repo root into plugins/document-navigator/docs/ so the plugin is self-contained and portable. docs/superpowers/ (specs and plans) stays at the repo root. Moved via cp+rm rather than git mv because directory rename() fails with EPERM on this WSL /mnt DrvFs mount; git rename-detection pairs the identical-content files at commit time. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
This commit is contained in:
@@ -0,0 +1,96 @@
|
||||
# OTel instruments
|
||||
|
||||
<!-- begin:auto-docs -->
|
||||
_(no submodules)_
|
||||
<!-- end:auto-docs -->
|
||||
|
||||
## Purpose
|
||||
|
||||
This module owns the OpenTelemetry instrument bundle emitted by the
|
||||
`vm.Context` sandbox host. Instruments are bound lazily against the
|
||||
current global `MeterProvider` so packages downstream may install a
|
||||
real exporter (Prometheus, OTLP, in-memory test reader) and observe
|
||||
the bundle without restarting the process. The bundle is cached after
|
||||
first build so the hot proxy path never reaches the meter registry
|
||||
twice.
|
||||
|
||||
## Features
|
||||
|
||||
- Four named instruments: a boot histogram, two refusal counters
|
||||
(`eval_rejected_total`, `module_import_rejected_total`), and the
|
||||
shared `plugin.permission_denied_total` counter whose name matches
|
||||
`api-sandbox-permissions` so dashboards aggregate cleanly.
|
||||
- Lazy binding via `getSandboxVmInstruments()` so tests may install a
|
||||
fresh `MeterProvider` and then call `resetSandboxVmInstruments()` to
|
||||
drop the cache.
|
||||
- All metric names are namespaced under `sandbox_vm.*` (except the
|
||||
cross-package denial counter), making them easy to filter at the
|
||||
collector.
|
||||
|
||||
## Usage: Basic
|
||||
|
||||
```ts
|
||||
import { getSandboxVmInstruments } from "@suaveplan/api-sandbox-vm/otel/instruments";
|
||||
|
||||
const instruments = getSandboxVmInstruments();
|
||||
instruments.evalRejectedTotal.add(1, { kind: "direct" });
|
||||
```
|
||||
|
||||
## Usage: Advanced
|
||||
|
||||
Install a real in-memory provider for assertions:
|
||||
|
||||
```ts
|
||||
import {
|
||||
AggregationTemporality,
|
||||
InMemoryMetricExporter,
|
||||
MeterProvider,
|
||||
PeriodicExportingMetricReader,
|
||||
} from "@opentelemetry/sdk-metrics";
|
||||
import { metrics } from "@opentelemetry/api";
|
||||
import {
|
||||
getSandboxVmInstruments,
|
||||
resetSandboxVmInstruments,
|
||||
} from "@suaveplan/api-sandbox-vm/otel/instruments";
|
||||
|
||||
const exporter = new InMemoryMetricExporter(AggregationTemporality.DELTA);
|
||||
const reader = new PeriodicExportingMetricReader({
|
||||
exporter,
|
||||
exportIntervalMillis: 1_000,
|
||||
});
|
||||
const provider = new MeterProvider({ readers: [reader] });
|
||||
metrics.setGlobalMeterProvider(provider);
|
||||
resetSandboxVmInstruments();
|
||||
|
||||
const instruments = getSandboxVmInstruments();
|
||||
instruments.permissionDeniedTotal.add(1, {
|
||||
plugin: "demo",
|
||||
capability: "fetch",
|
||||
});
|
||||
await reader.forceFlush();
|
||||
const collected = exporter.getMetrics();
|
||||
```
|
||||
|
||||
## API Reference
|
||||
|
||||
- `getSandboxVmInstruments(): SandboxVmInstruments` — return the
|
||||
lazily-built instrument bundle. Calling multiple times returns the
|
||||
same frozen reference until `resetSandboxVmInstruments()` is invoked.
|
||||
- `resetSandboxVmInstruments(): void` — drop the cache; the next
|
||||
`getSandboxVmInstruments()` call re-binds against the (possibly new)
|
||||
global `MeterProvider`.
|
||||
- `interface SandboxVmInstruments` — fully-typed instrument bundle.
|
||||
|
||||
## Implementation Notes
|
||||
|
||||
The module never reads any environment variable at import time and
|
||||
never side-effects the global `MeterProvider`. Caching uses a
|
||||
module-private `let` rather than a `WeakMap` because the lifecycle of
|
||||
the bundle is naturally process-scoped (there is no second
|
||||
`MeterProvider` instance to dispatch to unless the consumer resets the
|
||||
cache deliberately). The `permission_denied_total` counter
|
||||
intentionally uses the same name as the one in
|
||||
`api-sandbox-permissions`; both packages contribute to the same OTLP
|
||||
series so the consumer sees one denial total regardless of whether the
|
||||
decision was made in this package's default checker or in the richer
|
||||
implementation.
|
||||
Reference in New Issue
Block a user