Expand description
subms-otel - OpenTelemetry bridge for the subms perf harness.
Wires the harness’s SubMsObserver hook + the post-bench
SubMsBenchSummary + the SubMsTimer timeline into OpenTelemetry
Histogram / Span emission, without the harness itself ever pulling in
the OTEL dependency tree.
§Feature flags
Capability features:
bridge(default) - always-available bridge: post-hoc helpers,CompositeObserver, counter + gauge surface constants, the reference-drift recorder.observer- both [OtelObserver] (sync) and [OtelObserverAsync] (hand-rolled SPSC ring; target overhead < 300 ns peron_record).exemplars- per-bucket tail-debug exemplar reservoir ([ExemplarReservoir]). Configurable K; default K = 5.tracing- span emission per stage record + W3C TraceContext parent inheritance ([TracingObserver]).
Bootstrap:
autoconfig- env-driven one-line SDK wiring + runtime observer registry.
Exporter helpers (independent; pick what you ship):
exporter-otlp- [OtlpBuilder] + [ExporterOtlpHelper].exporter-prometheus- [PrometheusBuilder] + [ExporterPrometheusHelper].exporter-stdout- [ExporterStdoutHelper].
Both observers honour the same semantic-conventions table:
| Attribute key | Source |
|---|---|
subms.workload | ctx.workload / summary.workload |
subms.lang | ctx.lang / summary.lang |
subms.stage | ctx.stage / stage name |
subms.stage.kind | ctx.stage_kind.as_str() |
subms.recipe.slug | meta["subms.recipe.slug"] |
subms.recipe.category | meta["subms.recipe.category"] |
subms.workload.feature | meta["subms.workload.feature"] |
subms.workload.entries | inputs["entries"] |
subms.workload.seed | inputs["seed"] |
subms.host | meta["host"] |
subms.hardware.tier | meta["hardware_tier"] |
subms.crate.version | meta["crate_version"] |
Inputs and meta arrive only via on_summarize (the harness’s
ObservationCtx is intentionally minimal). The sync observer therefore
emits with just workload, lang, stage, and stage.kind per record;
on_summarize re-emits the whole histogram bucket set under the fuller
attribute set. The async observer caches the latest summary’s inputs+meta
between drain passes and applies them to drained samples once available.
Structs§
- Composite
Observer - Holds a list of inner observers and forwards every event to each. Lets a
consumer combine, e.g., an [
crate::OtelObserver] with a custom Prometheus impl and a logging observer at once. - Observation
Ctx - Context passed to
SubMsObserver::on_recordfor each recorded sample. - Reference
Divergence Recorder - Hold a single Counter instrument so a recipe wiring repeated cross-checks
doesn’t pay for a fresh
u64_counterbuild per divergence. Internally cached; cloning is cheap (the counter is reference-counted in OTEL). - SubMs
Bench Summary - Typed summary of one bench run. Mirrors the on-disk JSON downstream tooling persists per workload.
- SubMs
Otel Resource - Static helper carrying the detected resource set.
- SubMs
Stage Summary - Per-stage summary. The counterpart of one
stages.<name>entry in the subms JSON contract. - SubMs
Timer - Autostart stopwatch with named checkpoints. Not thread-safe; use one per task or synchronise externally.
- SubMs
Timer Checkpoint - A single named milestone captured by
SubMsTimer::mark/SubMsTimer::lap/SubMsTimer::stop.
Enums§
- SubMs
Stage Kind - What kind of operation a stage records. Observers use this to choose histogram bucket boundaries that fit the measurement scale.
Constants§
- DROPPED_
TOTAL_ COUNTER_ NAME - Counter name for back-pressure-dropped samples. Promoted from the async observer’s private constant so dashboards can wire it directly.
- EXEMPLARS_
KEPT_ COUNTER_ NAME - Counter name incremented when a sample is retained by an
[
ExemplarReservoir]. - HISTOGRAM_
NAME - Canonical name for the per-stage latency histogram. Consumers filter on this in Grafana / dashboards.
- HISTOGRAM_
UNIT - Canonical unit for the latency histogram. Seconds is OTEL convention for duration measurements - we emit ns / 1e9 to satisfy it.
- IN_
FLIGHT_ GAUGE_ NAME - ObservableGauge name published by [
OtelObserverAsync] tracking the current channel depth. - OPS_
TOTAL_ COUNTER_ NAME - Counter name incremented on every
on_recordregardless of which observer surface received the sample. - REFERENCE_
DIVERGENCE_ COUNTER_ NAME - Counter name surfaced to OTEL. Stable across versions.
Traits§
- SubMs
Observer - Hook a sibling crate (or downstream consumer) can register against a
[
SubMsPerfHarness] to react to every recorded sample plus the post-bench summary. Both methods default to a no-op so adding methods to the trait later is non-breaking.
Functions§
- attributes_
from_ ctx - Build the OTEL attribute set for a hot-path record. Just the harness
identity the
ObservationCtxcarries - inputs and meta arrive later via the summary. - attributes_
from_ summary - Build the full attribute set for a stage when we have the post-bench summary. Pulls workload + lang + stage from the summary and folds in any of the canonical inputs/meta keys that are present.
- divergence_
attributes - Build the attribute set carried by every divergence Counter emission.
- export_
summary - Export every stage of a
SubMsBenchSummaryas a Histogram emission on the givenMeter. Each percentile (p50, p99, p999, max, mean, stddev) and the downsampled chronological samples are recorded as histogram values under the stage’s full attribute set. - export_
timer - Export a
SubMsTimertimeline as a parent span + one child span per checkpoint. Span start times are reconstructed asnow - elapsed_nsso the timing offsets the timer captured are preserved end-to-end. - histogram_
boundaries - Histogram bucket boundaries (in seconds) keyed off the stage kind. Adapter
code applies these when first constructing the
Histograminstrument for a given stage kind. - record_
reference_ divergence - One-shot helper for recipes that don’t want to hold a
ReferenceDivergenceRecorder. Builds the counter on the fly; cheap enough for the cross-check call site but allocates a fresh instrument every call - if you call this in a tight loop, build aReferenceDivergenceRecorderonce and reuse it.