Override span fields

Replace the displayed input, output, name, or metadata on a span and verify the exported result.

Respan normally captures span input and output from function arguments and return values. Use update_current_span() when the trace should display a sanitized, condensed, or domain-specific representation instead.

Prerequisites

$pip install respan-ai
$export RESPAN_API_KEY="YOUR_RESPAN_API_KEY"

Override input and output

This complete example creates a manual task span, computes an internal result, writes safe display values to the span, checks that the update succeeded, and flushes the exporter.

Python
1import json
2import os
3
4from opentelemetry.semconv_ai import SpanAttributes
5from respan import Respan, get_client
6
7respan = Respan(
8 api_key=os.environ["RESPAN_API_KEY"],
9 app_name="support-triage",
10)
11client = get_client()
12
13
14def classify_support_ticket(raw_ticket: dict) -> dict:
15 # Your application can keep a richer internal result.
16 internal_result = {
17 "category": "billing",
18 "priority": "high",
19 "internal_notes": "Customer included private invoice details.",
20 }
21
22 displayed_input = {
23 "ticket_id": raw_ticket["ticket_id"],
24 "text": "[redacted]",
25 }
26 displayed_output = {
27 "category": internal_result["category"],
28 "priority": internal_result["priority"],
29 }
30
31 with client.start_span("classify_support_ticket", kind="task"):
32 updated = client.update_current_span(
33 attributes={
34 SpanAttributes.TRACELOOP_ENTITY_INPUT: json.dumps(displayed_input),
35 SpanAttributes.TRACELOOP_ENTITY_OUTPUT: json.dumps(displayed_output),
36 },
37 respan_params={
38 "metadata": {"data_policy": "redacted"},
39 },
40 )
41 if not updated:
42 raise RuntimeError("No active Respan span was available to update")
43
44 return internal_result
45
46
47result = classify_support_ticket(
48 {
49 "ticket_id": "ticket_demo_001",
50 "text": "Private invoice and payment details",
51 }
52)
53respan.flush()
54print(result)

The application receives the full internal_result, but the exported span displays only these safe values:

1{
2 "input": {
3 "ticket_id": "ticket_demo_001",
4 "text": "[redacted]"
5 },
6 "output": {
7 "category": "billing",
8 "priority": "high"
9 },
10 "metadata": {
11 "data_policy": "redacted"
12 }
13}

Verify in Respan

  1. Run the script and wait for respan.flush() to complete.
  2. Open Logs → Spans.
  3. Search for classify_support_ticket and open the span.
  4. Confirm that Input contains ticket_demo_001 and [redacted].
  5. Confirm that Output contains only category and priority; internal_notes must not appear.
  6. Confirm that metadata includes data_policy=redacted.

Do not set a manual output inside a @workflow or @task function and assume it will win. Decorators automatically capture the function return value after the function finishes, which can overwrite an output attribute set earlier. Use a manual start_span() when the exported output must differ from the returned value, or return the same sanitized value you want captured.

Override only the input in a decorated function

When automatic output capture is correct, you can keep the decorator and override only the displayed input:

Python
1import json
2
3from opentelemetry.semconv_ai import SpanAttributes
4from respan import get_client, workflow
5
6
7@workflow(name="summarize_ticket")
8def summarize_ticket(private_text: str) -> dict:
9 get_client().update_current_span(
10 attributes={
11 SpanAttributes.TRACELOOP_ENTITY_INPUT: json.dumps(
12 {"text": "[redacted]"}
13 )
14 }
15 )
16 return {"summary": "Billing question received."}

Troubleshooting

  • update_current_span() returns False. The call ran outside an active span, or tracing is disabled. Move it inside start_span(), @workflow, or @task and confirm RESPAN_API_KEY is set.
  • The output still shows the function return value. A decorator captured the return after your manual update. Use the manual-span pattern above.
  • Input or output is missing. Serialize structured values with json.dumps(...); OpenTelemetry attributes must be strings or supported scalar/array values.
  • The span is not visible yet. Call respan.flush() before a short-lived script exits, then confirm the project and environment associated with the API key.

You can also update an already-ingested span with the Update Span API.