All notable changes to this project will be documented in this file.

The format is based on Keep a Changelog, and this project adheres to Semantic Versioning.

Entries for unreleased work are not written here directly. Each issue drops a fragment in changelog.d/; the fragments are assembled into a version section at release. See that README for the format and for when a change warrants an entry at all.

[0.10.0] 2026-10-11

Minor release: a setup option on the persistence bridge chooses which adapter call spans are emitted, and by default an adapter call span is emitted only inside an enclosing span.

Added

  • A setup option, adapter_calls: :nested_only | :all, chooses whether a statifier_persistence.adapter.call span is emitted only inside an enclosing span (:nested_only) or for every adapter call (:all).

Changed

  • Adapter call spans outside an enclosing span are no longer emitted under the default option, adapter_calls: :nested_only; pass adapter_calls: :all to OpentelemetryStatifier.Persistence.setup/1 to keep every adapter call span.

[0.9.2] 2026-10-08

Patch release: documentation only. No module, function, event or attribute changes; the published docs gain a page on upgrading a host from 0.6 to 0.9.

Added

  • An "Upgrading a host from 0.6 to 0.9" page, published in the docs under an "Upgrading" group and shipped in the package: what a host changes for each minor from 0.6 to 0.9 and for the 0.9.1 patch, saying NONE where a host changes nothing.

Changed

  • The README's Documentation map links the upgrading page.

[0.9.1] 2026-10-05

Patch release: documentation only. No module, function, event or attribute changes; the published docs gain two pages, a sidebar grouped by kind of page, and a README rewritten as an introduction.

Added

  • A how-to guide, "How to see a chart execution as a trace", published in the docs and shipped in the package: find one chart execution in a tracing backend, follow its macrostep spans by their links, and read a macrostep's span events.
  • An explanation page, "Why spans and links are shaped this way", published in the docs and shipped in the package: why each macrostep is one span and the root of its own trace, and why links stitch an execution together.

Changed

  • The HexDocs sidebar groups the extra pages by kind of page, under "How-to guides" and "Explanation".
  • The README is rewritten as an introduction: what the package is, why it exists, the install pin, one basic-usage example of a library loan with the spans it exports, and a Documentation map grouped by Learn, Do, Look up and Understand. The longer integration walkthroughs it carried now live behind links to the module pages that document them.

[0.9.0] 2026-09-28

Minor release: the persistence bridge exports statifier_persistence's batch migration span, so a migrate_batch/3 call becomes one span carrying the report's counts, with the spans and migrated events of the executions it moves nested inside it.

Added

  • OpentelemetryStatifier.Persistence bridges statifier_persistence's batch migration span: a migrate_batch/3 call becomes a statifier_persistence.execution.migrate_batch span carrying the report's counts as attributes, and each execution it moves lands on it as a migrated span event.

Changed

  • Inside a statifier_persistence migrate_batch/3 call, the statifier_persistence.execution.lock and statifier_persistence.adapter.call spans each execution's turn opens now nest under the batch span, where they were the roots of their own traces, and each migrated execution is a migrated span event on the batch span, where it was a zero-duration root span of its own.

[0.8.0] 2026-09-27

Minor release: the Oban bridge covers statifier_oban 0.15's deferred invoke event, a step that raises records an exception span event, and the migrated point's statifier_persistence.dropped attribute becomes a sorted string array, absent when a migration drops no state - a host that reads dropped changes how it reads it.

Added

  • OpentelemetryStatifier.Oban bridges [:statifier_oban, :invoke, :deferred], the event statifier_oban 0.15 emits when an invoke handler defers its answer: it becomes a statifier_oban.invoke.deferred span of its own, like the other delivery-seam events, and is the last span this bridge produces for that invocation.
  • A statifier_persistence step that raises, throws or exits now records an exception span event on its step span, carrying exception.type and the narrowed frames as exception.stacktrace, so a tracing backend's exception view shows the failure.

Changed

  • The statifier_persistence.dropped attribute of a migration's statifier_persistence.execution.migrated point is now a sorted string array of the dropped state ids, as statifier.configuration is, instead of one inspect/1 string; a host that parsed or matched that string queries the array's elements instead.
  • A migration that drops no state carries no statifier_persistence.dropped attribute, because the OpenTelemetry API refuses an empty array; it carried the string "[]" before, so a host that matched that string checks for the attribute's absence instead.

[0.7.0] 2026-09-26

Minor release: the persistence bridge covers the four events statifier_persistence 0.19 added, so OpentelemetryStatifier.Persistence.events/0 names four more.

Added

  • OpentelemetryStatifier.Persistence bridges the four events statifier_persistence 0.19 emits that it did not: a step that raised, threw or exited closes its statifier_persistence.execution.step span with an error status, an error.communication re-entry lands as a statifier_persistence.execution.step.reentered span event on the step span, and an execution migrated or unparked becomes a point like the other lifecycle events.

[0.6.0] 2026-09-13

Minor release: the bridge follows statifier_persistence's execution rename. The step span is now statifier_persistence.execution.step and the bridge subscribes to the [:statifier_persistence, :execution, ...] events, so the durable floor moves to statifier_persistence 0.12.

Changed

  • Breaking for OpentelemetryStatifier.Persistence span names. statifier_persistence retired run as the noun naming the durable record (its ADR-0011), so the bridge moves to the :execution event prefix in lockstep: the step span is now statifier_persistence.execution.step (was statifier_persistence.run.step), the lock span is statifier_persistence.execution.lock, and the lifecycle point spans are statifier_persistence.execution.created / .terminated / .discarded. statifier_persistence.adapter.call, .identity.refused, .effect.failed, .drive.turns_exhausted and the .child.* seam keep their names. The run_id-shaped metadata keys arrive as execution_id, parent_execution_id and child_execution_id, so the attributes they become are statifier_persistence.execution_id and friends. Update saved queries, dashboards and alerts that name the old spans or attributes.
  • The durable floor is statifier_persistence 0.12: there is no dual emit upstream, so below 0.12 the six renamed event names are attached to names that release does not emit and the spans they carry simply stop - no statifier_persistence.execution.step, no .execution.lock, and no .execution.created / .terminated / .discarded. Upgrade statifier_persistence and this package together.
  • Below that floor the ten names that did not move still arrive and still become spans, in two shapes. The nine point events - identity.refused, effect.failed, drive.turns_exhausted and the six child.* events - land as unparented root spans instead of as span events on the step. adapter.call is not one of them: it carries a duration, so it is always a span of its own back-dated by that duration, nested in the step span when one is open and a root when none is - except that a host which declared its own span through OpentelemetryStatifier.Parent.register/2 still parents it, which the nine point events do not read. The other two families (OpentelemetryStatifier.setup/1's statechart events and OpentelemetryStatifier.Oban) are unaffected.
  • OpentelemetryStatifier.Persistence.events/0 returns 16 names, not 14: [:statifier_persistence, :child, :recorded] and [..., :child, :settled] are bridged. They were added upstream after statifier_persistence 0.5.0 and had gone unbridged because this package's drift check was pinned to that release.

[0.5.0] 2026-09-06

Minor release: the bridge now covers statifier_oban's fan-out events, so a chunk child's spans are reachable from the dispatch that planned them. The test-only statifier_oban requirement moves to ~> 0.9, because the fan-out events this release bridges are 0.9.0's.

Added

  • OpentelemetryStatifier.Oban bridges statifier_oban's three fan-out events. invoke.fan_out and invoke.child_started become roots linked to the trace that planned the invocation, so every chunk child is reachable from the parent's dispatch by a link edge rather than only by a shared statifier.session_id; invoke.unstarted_cancelled carries no caller context and lands as a span event on the span open where the sweep ran, putting its count in the trace either way.

[0.4.1] 2026-09-06

Patch release: an Oban scheduling point emitted under a durable driver now lands on the step span open in the emitting process instead of rooting a trace of its own.

Changed

  • 2026-09-06: corrects the 0.3.0 entry for OpentelemetryStatifier.Oban.setup/0,1. A scheduling event lands on the macrostep span that armed it when the session is stepping in the emitting process, and on the step span open there under a durable driver.

Fixed

  • A statifier_oban scheduling event now falls back to the step span open in the emitting process when scope is a host's durable run id, instead of rooting a trace of its own.

[0.4.0] 2026-09-02

Minor release: a host with its own durable stepper can now declare the parent span, and a subscriber can resolve an open macrostep span by key.

Added

  • OpentelemetryStatifier.Parent.register/2, unregister/1 and within/3 let a host with its own durable stepper declare the span its macrostep spans nest inside, the way statifier_persistence's step span already does.
  • OpentelemetryStatifier.SpanContext.lookup/2 resolves the open macrostep span for a (session_id, macrostep) pair to its W3C trace and span ids, so a statifier_ui subscriber can be wired to it as an :otel_context producer directly.

Fixed

  • The macrostep span now carries statifier.driver, so a backend can tell a durable macrostep from a session-hosted one.

[0.3.0] 2026-09-01

Minor release: the bridge now covers the family sibling packages.

Added

  • Adds OpentelemetryStatifier.Persistence.setup/0,1, bridging the fourteen [:statifier_persistence, ...] events into a statifier_persistence.run.step span with the storage, lock and lifecycle detail inside it.
  • Adds OpentelemetryStatifier.Oban.setup/0,1, bridging the eleven [:statifier_oban, ...] events: scheduling events onto the macrostep span that armed them, and each delivery event as its own span linked to the arming trace through caller_context.

Changed

  • A macrostep span now nests inside the statifier_persistence.run.step span around it, instead of always rooting its own trace. With no sibling setup attached, nothing changes.

[0.2.0] 2026-09-01

Minor release: the bridge tracks the statifier 2.4 line.

Changed

  • The statifier requirement moves from ~> 2.0 to ~> 2.4, the release whose published guides carry the design this bridge implements. Anyone reading the engine's docs/opentelemetry.md alongside the bridge now reads the version the bridge is built and tested against.

[0.1.2] 2026-08-27

Patch release: refreshes the published documentation with worked examples. No code changes.

Changed

  • README gains a worked card-authorization example - chart, setup, the four macrostep spans it exports, and an invoke handler for myapp:authorize - plus a signup-wizard A/B example showing why chart vocabulary lands in attributes rather than span names. Every snippet is executed by the suite.

[0.1.1] 2026-08-24

Patch release: brings the published documentation to the shared statifier docs standard. No code changes.

Changed

  • The hexdocs no longer publish the repo's ADRs, and mix docs completes with zero warnings (CHANGELOG.md is on the undefined-reference skip list for its changelog.d link).
  • README gains the standard badge row (CI, hex.pm version and downloads, hex docs, license), and the License section links to the LICENSE file by absolute GitHub URL so the link also works on hexdocs.

[0.1.0] 2026-08-22

First release: the OpenTelemetry bridge for the statifier statechart engine, built on its public :telemetry events only. A statechart macrostep is a span; effect and trace telemetry events are span events on it; each macrostep roots its own trace, stitched to its neighbors with span links. The design is recorded upstream in statifier-ex's docs/opentelemetry.md and st-ADR-0062.

Added

  • OpentelemetryStatifier.setup/1, which attaches the bridge to statifier's session telemetry and emits a statifier.macrostep span per macrostep.
  • Records the effect, trace, :interpret, :unroutable, and :halt telemetry events as span events on the open macrostep span, and links each macrostep span to the session's previous macrostep and (for an invoked child's :initialize macrostep) to the invoking parent's open span. Datamodel values are excluded unless setup/1 receives record_datamodel_values: true.
  • Cleans up the span table over the session lifecycle: :terminate removes the session's rows (ending a still-open macrostep span with an error status), and a periodic sweep does the same for sessions whose process died without a :terminate, so a brutal kill orphans no open span and leaks no rows. With trace: false the bridge degrades to macrostep-grained spans with effect-level span events, no configuration needed.