Skip to content

Add Claude Managed Agents integration - #1

Closed
cj-ant wants to merge 3 commits into
mainfrom
cj/claude-managed-agents-integration
Closed

cj-ant wants to merge 3 commits into
mainfrom
cj/claude-managed-agents-integration

Conversation

@cj-ant

@cj-ant cj-ant commented Jul 23, 2026

Copy link
Copy Markdown
Owner

What this adds

A new integration, @ag-ui/claude-managed-agents, that bridges Claude Managed Agents (Anthropic's hosted agent sessions) to the AG-UI protocol. It sits next to the existing claude-agent-sdk integration, which wraps the local Claude Code SDK. This one wraps the hosted sessions API, so an app that runs its agents on Managed Agents gets an AG-UI endpoint with no extra glue.

ManagedAgentsAgent extends AbstractAgent. Each AG-UI thread maps to one managed session, and each run drives one turn of that session while translating its event stream into AG-UI events.

Event mapping

Managed Agents event AG-UI events
agent.message with event_delta previews TEXT_MESSAGE_START / CONTENT / END (previews reconciled against the buffered message)
agent.thinking REASONING_START / REASONING_END
agent.tool_use, agent.mcp_tool_use and results TOOL_CALL_* and TOOL_CALL_RESULT (server executed, display only)
agent.custom_tool_use for a frontend tool TOOL_CALL_*, then the run finishes so the client can execute it
agent.custom_tool_use for a backend tool TOOL_CALL_* and TOOL_CALL_RESULT, result posted back to the session
session.error (terminal) RUN_ERROR with the error type as code
session.status_idle with end_turn RUN_FINISHED

Human in the loop with frontend tools

Tools in RunAgentInput.tools are registered on the session as custom tools. When the agent calls one, the run emits the tool call and finishes while the session parks in requires_action. The client runs the tool and starts the next run with a role: "tool" message. The adapter forwards it as user.custom_tool_result on the same session and streams the continuation. Backend tools (server side handlers) run inline and post their result back.

What is in the PR

  • integrations/claude-managed-agents/typescript: the package (ManagedAgentsAgent, turn translator, pluggable session store, tool helpers), 27 unit tests against a scripted fake client, and an examples server plus an idempotent provisioning script (setup:examples) that creates one agent per Dojo feature.
  • Dojo wiring: menu.ts, agents.ts, env.ts (CLAUDE_MANAGED_AGENTS_URL, port 8024), regenerated files.json, prep and run scripts.
  • Release enrollment: release.config.json scope, nx.json, the three workflow scope dropdowns, and the config allowlist entry for tsdown.config.ts.
  • render.yaml service (pinned to one instance since the default store is in memory) and the framework table row in the root README.md.

Verified

Provisioned the example agents in a test workspace and drove the example server end to end:

  • Agentic chat streams reasoning and text through to RUN_FINISHED.
  • Backend tool: TOOL_CALL_*, then TOOL_CALL_RESULT from the server handler, then the agent's summary.
  • Frontend tool round trip: run 1 parks after TOOL_CALL_*, run 2 posts the tool result to the same session and it resumes to end_turn.
  • Probes: malformed body (400), unknown route (404), empty run (early RUN_ERROR, no session created), overlapping runs on one thread (second rejected), client disconnect (a user.interrupt reaches the session).

Notes for review

  • TypeScript only for a first version. A Python variant can follow the same pattern later.
  • No Dojo e2e spec yet. Every other integration's e2e suite runs against llmock, but here the model loop runs at Anthropic, so there is no local model call to intercept. Open to ideas on how the maintainers would like this covered.
  • The default SessionStore is in memory. It is pluggable so a deployment can persist thread to session mappings.

@github-actions

github-actions Bot commented Jul 23, 2026 •

Copy link
Copy Markdown

Python Preview Packages — Publish Failed

Preview publish failed for commit 26cbf23.
See the workflow run for details.

working-directory: integrations/langroid/python
run: uv run python -m unittest discover tests -v

claude-managed-agents-python:
- name: Detect fork PR
id: fork-check
run: |
if [[ "${{ github.event_name }}" == "pull_request" && \
id: fork-check
run: |
if [[ "${{ github.event_name }}" == "pull_request" && \
"${GITHUB_EVENT_PULL_REQUEST_HEAD_REPO_FULL_NAME}" != "${{ github.repository }}" ]]; then
Bridge Claude Managed Agents (Anthropic's hosted agent sessions) to
the AG-UI protocol. Each AG-UI thread maps to one managed session;
each run drives one turn of that session and translates its event
stream into AG-UI events. Provided in three languages with matching
behavior:

- TypeScript (@ag-ui/claude-managed-agents): a ManagedAgentsAgent
  AbstractAgent plus an examples server.
- Python (ag-ui-claude-managed-agents): a ManagedAgentsAgent yielding
  ag_ui.core events plus a FastAPI endpoint helper.
- .NET (AGUI.ClaudeManagedAgents): a ManagedAgentsAgent on the AG-UI
  .NET abstractions plus a MapManagedAgentsAgent endpoint extension.

Event mapping covers streamed text with preview reconciliation,
reasoning start and end, built-in and MCP tool calls with results,
backend custom tools with server-side handlers, and frontend tools
(RunAgentInput.tools): a frontend tool call parks the session and
ends the run, and the next run's tool message resumes it. Also typed
session errors, tool-confirmation policy, per-thread run
serialization, interrupt on disconnect or timeout, an optional scope
that partitions thread state per caller, and split sends so tool
results resume a parked session before follow-up user messages.

Registers all three variants in the Dojo (menu, agents, env,
generated files, prep and run scripts), the release config and
workflow scope dropdowns, a Python unit-test job, a .NET
build-and-test workflow, the config allowlist, the Render blueprint,
and the README framework table.
@cj-ant
cj-ant force-pushed the cj/claude-managed-agents-integration branch from a1db8d7 to 773f847 Compare July 23, 2026 18:56
cj-ant added 2 commits July 23, 2026 19:02
Extract shared helpers in the TypeScript turn (text-message emits,
answering a custom tool use) and a runError builder plus a
hasUserText predicate in the agent, removing repeated event casts and
the duplicated tool-result posting path. Name the tool-name, tool
description, tool-result, search-preview, and parked-retry constants
in place of magic numbers, and mirror the same named constants in the
Python core. No behavior change.
Bring the TypeScript and .NET suites up to parity with Python
(73/76/78 tests) and fix the issues review turned up across the
claude-managed-agents integration:

- Key the per-thread run gate by session-store identity: agents
  sharing a store serialize runs per thread (even across instances),
  while per-caller stores keep one caller's runs from blocking or
  interfering with another's.
- Bound best-effort sends (tool results, confirmations, interrupts)
  by a 15s timeout instead of unbounded non-cancellable calls, and
  post the interrupt before releasing the busy gate so an immediate
  resend is not killed by a stale interrupt.
- Answer a backend tool call on every teardown path: race the
  handler against the abort signal, branch on real cancellation
  state instead of exception type, and observe abandoned handler
  tasks so late faults are never unobserved.
- Give every RUN_ERROR a stable code (run_in_progress, empty_run,
  tool_result_without_session, nothing_to_send, turn_timeout,
  run_failed) in all three ports.
- Converge port behavior: original-order abandoned-tool results, no
  empty text deltas, error text included in tool results, last-write-
  wins tool name collisions, shared named constants, and rename the
  option to managedAgentId/managed_agent_id/ManagedAgentId so it no
  longer shadows the AG-UI agentId.
- Raise the Python floor to anthropic>=0.119.0 (the sessions API
  surface the code uses), regenerate both uv.lock files against
  public PyPI, move @anthropic-ai/sdk to peerDependencies to match
  sibling integrations, and drop unused uvicorn/pydantic deps.
- Remove the scope/ownerId option: thread state is keyed by thread
  ID like the other integrations, with a security section in each
  README covering authentication and per-caller store partitioning.
- Fix the README demo link, align the dotnet unit workflow naming,
  add the llmock fallback to the dotnet dojo run entry, and
  regenerate files.json.
@cj-ant

cj-ant commented Jul 25, 2026

Copy link
Copy Markdown
Owner Author

Superseded by the upstream PR: ag-ui-protocol#2247. Closing this fork-internal review PR.

@cj-ant cj-ant closed this Jul 25, 2026
mme pushed a commit that referenced this pull request Jul 29, 2026
CPK-7718 #1: crewai 1.0.0 deleted crewai.utilities.events (event bus, flow/
method lifecycle events, listener base moved to crewai.events; BaseEvent is
no longer re-exported at the root and lives at <events>.base_events). New
_capabilities.py resolves each symbol trying the 1.x home first, then the 0.x
home, runs the probe ONCE at import, caches it, and warns (with the version
that unlocks a gap) on any missing capability. crewai.__version__ is used
only for warning text, never as a code-path gate.

events.py / sdk.py now import BaseEvent / crewai_event_bus from the probe.
Also fixes a pre-existing E713 (not-in) in sdk.py.
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.

2 participants