Conversation
ReferenceId and Context.referenceHierarchy were resolved from two disjoint sources, so they disagreed on every span in any environment where a project id exists. Prefer the innermost referenceHierarchy entry, then an explicitly stamped referenceId attribute, and only then the agentId attribute (which carries a project id from resolve_project_id()). Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
There was a problem hiding this comment.
Copilot review overview
🟢 Approval recommended
All reviewed changes align with the intended fix and regression coverage.
Review effort: Lite
Findings: None
What changed in this PR
Fixes span conversion so top-level ReferenceId matches the innermost reference hierarchy entry instead of the project ID.
Changes:
- Prioritizes the hierarchy leaf, then
referenceId, thenagentId. - Reuses parsed hierarchy data for ID resolution and context.
- Adds regression tests for precedence and ID mismatches.
| File | Description |
|---|---|
packages/uipath-platform/tests/services/test_span_utils.py |
Updates and expands reference ID resolution tests. |
packages/uipath-platform/tests/services/test_reference_context.py |
Adds hierarchy and ReferenceId consistency tests. |
packages/uipath-platform/src/uipath/platform/common/_span_utils.py |
Implements hierarchy-aware reference ID resolution. |
💡 Add a code-review agent skill or configure MCP servers for context-aware, tailored reviews. Learn more in the docs.
0.2.32 is already published to PyPI, so the release job rejects it. Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
The runtime stamps referenceId and pushes that same id onto the reference hierarchy, so the leaf is a consequence of the reference id, not its source. Reading the leaf first misattributes a span whenever a service fails to push its own entry: the hierarchy is still non-empty and its leaf holds the *caller's* id, so the span would be filed under the caller. Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
|
|
Superseded.
No change to |



ReferenceIdwas resolved from a source unrelated to the id the runtime actually stamps, so it disagreed with both thereferenceIdattribute and thereferenceHierarchyon every span.uipath-agents-pythonagent.py:135-151takes one id —agent_definition.id, elseUIPATH_PROCESS_UUID— and uses it for both thereferenceIdattribute and the("agent", agent_id, …)hierarchy entry. Those two always agreed._span_utils.pywroteattributes_dict["agentId"] = resolve_project_id()— a project id (uipath.json#id→UIPATH_AGENT_ID→UIPATH_PROJECT_ID→PROJECT_KEY, the same helpertelemetry/_track.pyuses to reportproject_id) — then computedreference_id = agentId or referenceId. Theorordering meant the project id always beat the agent id the runtime had stamped.referenceIdattribute → hierarchy leaf →agentId.referenceIdfirst, not the leaf: the runtime stampsreferenceIdand pushes that same id onto the hierarchy, so the leaf is a consequence of the reference id, not its source. When a service fails to push its own entry (agent.py:149-150falls back toparent_ctxon a non-UUID id), the hierarchy is still non-empty and its leaf holds the caller's id — deriving from it would file the span under maestro instead of the agent.uipath-langchain-python'slanggraphentry, which otherwise falls through to the project id and diverges the same way.agentIdas a span attribute is untouched; only the top-levelReferenceIdchanges, and only for spans carrying areferenceIdattribute or a hierarchy. Producers that emit neither keep the current behaviour.Why it went unnoticed
resolve_project_id()returnsNonein a bare local checkout (nouipath.json#id, no env vars), soreference_idfell through toreferenceIdand matched.uipath initthen backfillsuipath.json#id— withstr(uuid.uuid4())when neitherUIPATH_PROJECT_IDnor.uipath/.telemetry.json#ProjectKeyis present (cli_init.py:436,445). From that point on a random GUID outranks the real agent id on every emitted span.Behaviour
With
uipath.json#id = 1111…,agent.json#id = 2222…, caller3333…:referenceId+ hierarchy)1111…2222…1111…2222…1111…2222…(not3333…)referenceId1111…1111…unchangedTests
TestReferenceIdResolutionasserted the old precedence and were updated; the class docstring now states the source/consequence relationship and whyagentIdis last.referenceId.TestReferenceIdMatchesHierarchyLeafpins the invariant end-to-end against a populated project id.uipath-platformsuite green; ruff + mypy clean.Note
agentIdas a span attribute still carries a project id (_span_utils.py:471). That is a separate pre-existing naming problem and is deliberately out of scope here — changing what the backend receives foragentIdis a bigger call than this fix.🤖 Generated with Claude Code