Skip to content

Implement 0040 open-span metadata update#96

Merged
chris-colinsky merged 1 commit into
mainfrom
feature/0040-open-span-augmentation
May 29, 2026
Merged

Implement 0040 open-span metadata update#96
chris-colinsky merged 1 commit into
mainfrom
feature/0040-open-span-augmentation

Conversation

@chris-colinsky

Copy link
Copy Markdown
Member

Summary

  • Mid-invocation set_invocation_metadata now emits a MetadataAugmentationEvent on the engine's serial observer queue; both OTel and Langfuse observers match the augmenter's lineage tuple (namespace, attempt_index, fan_out_index, branch_name) against their open observations and apply the entries in place (span.set_attribute / observation.update(metadata=...)). Outermost-serial also fires trace.update. Sibling instances and ancestors above the innermost containment are skipped per spec sec 3.4.
  • _StackKey widened to include branch_name in both observers so concurrent same-named inner nodes across sibling parallel-branches branches no longer collide; LLM event payload picks up calling_branch_name.
  • Shared tuple-prefix helpers extracted to src/openarmature/observability/lineage.py.
  • Conformance: activate fixture 028's mid-invocation rejection case and 034 outermost-serial via the Langfuse harness; 029/030 stay deferred with documented fixture-shape gaps. Pre-existing fixture 005 flake fixed by resetting the OTel global tracer Once primitive before set_tracer_provider.
  • Two coord threads opened: discuss-augmentation-nested-lineage-scope (nested fan-out / parallel-branch lineage chain shape) and discuss-otel-parallel-branches-dispatch-span (per-branch dispatch span on the OTel mapping).

Test plan

  • uv run pyright clean
  • uv run pytest tests/unit/ tests/conformance/ -q (948 pass, 81 skipped)
  • New unit tests: outermost-serial, fan-out per-instance isolation, parallel-branches sibling-skip, outside-invocation no-op, empty-entries no-op (OTel + Langfuse)
  • New conformance: 028 mid-invocation case + 034 outermost-serial fixture
  • Spec submodule pin unchanged (v0.31.0)

Mid-invocation set_invocation_metadata now emits a
MetadataAugmentationEvent on the engine's serial observer queue.
Both observers match the augmenter's lineage tuple
(namespace, attempt_index, fan_out_index, branch_name) against
their open observations and apply the entries in place:
span.set_attribute on OTel, observation.update(metadata=...) on
Langfuse. Outermost-serial also fires trace.update so the augmented
keys land at trace.metadata.<key>. Sibling instances and ancestors
above the innermost containment are skipped per spec sec 3.4.

OTel's open-span _StackKey widened to include branch_name so
concurrent same-named inner nodes across sibling parallel-branches
branches no longer collide. Same widening on the Langfuse observer
plus the LLM event payload's calling_branch_name field. Shared
tuple-prefix helpers extracted to observability/lineage.py.

Conformance: activate 028's mid-invocation rejection case (helper
raises at the call site on a reserved key) and 034 outermost-serial
fixture via the Langfuse harness. Fix the pre-existing 005 flake by
resetting the OTel global tracer Once primitive before
set_tracer_provider. 029 and 030 stay deferred with documented
fixture-shape gaps; the augmentation mechanism itself is covered
end-to-end by new unit tests in test_observability_otel and
test_observability_langfuse.

Two coord threads opened for follow-up: nested fan-out lineage
scope and parallel-branches per-branch dispatch span shape.
Copilot AI review requested due to automatic review settings May 29, 2026 23:20
Comment thread src/openarmature/graph/observer.py
Comment thread src/openarmature/graph/observer.py
Comment thread src/openarmature/observability/correlation.py
Comment thread src/openarmature/observability/metadata.py Dismissed
Comment thread src/openarmature/observability/metadata.py

Copilot AI left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

Implements proposal 0040 mid-invocation metadata augmentation. set_invocation_metadata now emits a new MetadataAugmentationEvent through the engine's serial observer queue; the OTel and Langfuse observers apply the augmented entries in place to open spans/observations whose lineage covers the calling context (per spec §3.4 scoping). The observer _StackKey is widened with branch_name to disambiguate concurrent same-named inner nodes across sibling parallel branches.

Changes:

  • New MetadataAugmentationEvent (frozen dataclass, exported from openarmature.graph) + delivery plumbing in the observer worker that bypasses the phase filter for augmentation events.
  • OTel and Langfuse observers gain _handle_metadata_augmentation, a shared lineage.py prefix-helpers module, branch-aware _StackKey, and calling_branch_name in LlmEventPayload.
  • Conformance: activate fixture 028 mid-invocation rejection case and 034 outermost-serial via the Langfuse harness; fixtures 029/030 stay deferred with documented reasons; pre-existing fixture 005 flake fixed via direct reset of the OTel _TRACER_PROVIDER_SET_ONCE primitive.

Reviewed changes

Copilot reviewed 25 out of 25 changed files in this pull request and generated no comments.

Show a summary per file
File Description
src/openarmature/graph/events.py Defines MetadataAugmentationEvent; adds to __all__.
src/openarmature/graph/init.py Re-exports MetadataAugmentationEvent.
src/openarmature/graph/observer.py Updates Observer protocol/_QueuedItem to event union; routes augmentation events past phase filter and prepare_sync.
src/openarmature/observability/correlation.py Widens dispatch ContextVar typing to the event union.
src/openarmature/observability/metadata.py Emits MetadataAugmentationEvent through current dispatch after merging entries.
src/openarmature/observability/lineage.py New shared tuple-prefix helpers.
src/openarmature/observability/llm_event.py Adds calling_branch_name to LLM event payload.
src/openarmature/llm/providers/openai.py Populates calling_branch_name on the LLM event.
src/openarmature/observability/otel/observer.py Widens _StackKey with branch_name; adds augmentation-target collection and in-place set_attribute.
src/openarmature/observability/langfuse/observer.py Mirrors OTel: branch-aware key, update_trace/observation.update augmentation.
examples/* Examples updated to accept the union and isinstance-narrow.
tests/unit/test_observer.py, test_drain.py, test_runtime_errors.py Observer signatures updated to the union.
tests/unit/test_observability_otel.py New outermost-serial / fan-out / parallel-branches / no-op / outside-invocation tests.
tests/unit/test_observability_langfuse.py New trace+node-update, fan-out per-instance, no-op, outside-invocation tests.
tests/conformance/test_observability.py Activates 028 augment-rejection case; adds OTel _TRACER_PROVIDER_SET_ONCE reset before set_tracer_provider.
tests/conformance/test_observability_langfuse.py Activates 034; adds augment-middleware builders for fan-out / parallel branches; subgraph-key normalization; fixture-level subgraph folding into cases.
tests/conformance/test_fixture_parsing.py Updates 029/030/034 deferral notes.
tests/conformance/test_conformance.py, tests/conformance/adapter.py Adapter observer ignores MetadataAugmentationEvent.

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

@chris-colinsky chris-colinsky merged commit 9368940 into main May 29, 2026
7 checks passed
@chris-colinsky chris-colinsky deleted the feature/0040-open-span-augmentation branch May 29, 2026 23:47
chris-colinsky added a commit that referenced this pull request May 30, 2026
Extends the observability spec.4 reserved exact-key-name set from 21
to 24 entries with `branch_name`, `detached`, and
`detached_from_invocation_id`. These three are top-level Langfuse
metadata keys the observer mapping already writes; without
reservation a caller key matching one would silently shadow the
OA-emitted field at the boundary, the same hazard 0041 closed for
its 20 names.

Also relocates `observation.metadata.detached: true` from the
detached-side dispatch observation onto the parent-side dispatching
observation in the main trace (link observation for detached
subgraphs; parent fan-out node observation for detached fan-outs),
matching the .4.2 row 0042 added and the corresponding fixture 033
assertions.

Bumps the spec pin from v0.31.0 to v0.34.0, absorbing 0042 plus the
two textual additions in v0.32.0 (Gemini wire-format mapping, 0038,
not yet implemented) and v0.33.0 (sessions capability, 0020, not
yet implemented). Updates `conformance.toml` accordingly: 0040
flipped not-yet to implemented (shipped in PR #96); 0042 added as
implemented; 0020 and 0038 added as not-yet. Defers the 10 new
Gemini conformance fixtures in both the cross-capability parser
and the LLM-provider harness to match the not-yet status.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants