Cua Docs

SDK, MCP, and process hosting

How Cua Driver separates its typed application contract, agent protocol, and desktop process identity.

Cua Driver has two caller interfaces and two execution topologies. They solve different problems:

  • The SDK is a typed application API for Python, TypeScript, and Rust.
  • MCP is the runtime-neutral agent protocol exposed by the Cua Driver server.
  • A same-process runtime performs desktop work inside the importing app.
  • A daemon runtime performs desktop work in a long-lived process with a stable operating-system identity.

These dimensions form a grid, but only two cells are primary:

Typed SDKMCP / CLI
Same processPrimary for client applicationsNot a separate public client mode
DaemonCompatibility or app-shared runtimePrimary for agents and short-lived CLI calls

The SDK adds unique value in the same-process cell: typed records and direct calls across the generated native boundary without a socket. If application code talks to the same daemon as an agent, the SDK is mainly a typed compatibility adapter over that existing daemon.

One typed contract#

The public typed CuaDriver SDK contract is canonical:

private platform implementations
              |
              v
public typed CuaDriver SDK contract
       |          |          |
       v          v          v
   Rust apps   UniFFI      MCP server adapter
              /    \             |
          Python  TypeScript   agents and CLI

The MCP server is downstream of the same public SDK contract as an application. It does not maintain a second implementation of desktop tools. MCP remains valuable because it standardizes discovery, calls, results, tasks, and transport for agent runtimes; the generated language SDKs are for applications embedding the native runtime.

Why the daemon still exists#

External agents and CLI calls are short-lived or run outside the desktop app that owns permissions. A daemon gives them a stable execution identity, long-lived session state, and one controlled gateway to the physical desktop.

On macOS, Accessibility and Screen Recording grants attach to an application identity and responsibility chain. The standalone CuaDriver.app daemon keeps that identity stable across CLI and agent reconnects. A signed app that needs to expose MCP can instead spawn a private daemon directly so the child reuses the app's TCC grants.

On Windows, a daemon can remain in the logged-in interactive session while an SSH or service-side client cannot access that desktop. On every platform, it also owns cleanup for recordings, cursors, policy, and per-session state when a client disconnects.

Why embedded applications may choose either topology#

Apps such as signed Electron desktop clients may want their own permission row and onboarding. If only the app calls Cua Driver, CuaDriver.create() runs the runtime in that permission-owning process. If external agents must connect, the app can host a private daemon and publish its MCP connection. Both routes consume the same typed behavior; the difference is lifecycle and process identity, not a different action implementation.

See Process model for platform details and Expose MCP from a desktop app for the hosted-daemon procedure.

Agent SDK integration is intentionally asymmetric#

Agent SDKNative application callbacksExternal MCP route
Claude Agent SDKSupported in Python and TypeScript through its in-process custom-tool serverSupported in Python and TypeScript
Codex SDKNo direct custom-tool callback boundarySupported in Python and TypeScript

Claude's in-process custom-tool server is an adapter inside the host application; the callbacks still call the native Cua Driver SDK directly. Codex uses cua-driver mcp because MCP is its supported tool-extension boundary. Generating another language client would not add a new capability.

See Use Cua Driver with Claude Agent SDK and Use Cua Driver with Codex SDK.