Skip to content

Bridge API

Generic WebSocket bridge for non-Python DCCs. Implements the server-side of the dcc-mcp-core WebSocket JSON-RPC 2.0 bridge protocol.

Exported symbols: DccBridge, BridgeError, BridgeConnectionError, BridgeTimeoutError, BridgeRpcError, BridgeRetryPolicy, BridgeTransportStrategy, BridgeFallbackClient, ReverseBridgeRequest, ReverseBridgeSession

DccBridge

WebSocket bridge server that waits for a DCC plugin to connect.

Constructor

ParameterTypeDefaultDescription
hoststr"localhost"Bind address for the WebSocket server
portint9001Port for the WebSocket server
timeoutfloat30.0Default timeout in seconds for call()
server_namestr"dcc-mcp-server"Name advertised in the hello_ack handshake
server_versionstr | Nonepackage versionVersion advertised in hello_ack

Properties

PropertyTypeDescription
endpointstrWebSocket endpoint URL (e.g. "ws://localhost:9001")

Methods

MethodReturnsDescription
connect(wait_for_dcc=False)NoneStart the WebSocket server
call(method, **params)AnySynchronous RPC to the DCC plugin (thread-safe)
disconnect()NoneShut down the WebSocket server
is_connected()boolWhether a DCC plugin has completed the handshake
python
from dcc_mcp_core import DccBridge

# Context manager
with DccBridge(port=9001) as bridge:
    info = bridge.call("ps.getDocumentInfo")
    layers = bridge.call("ps.listLayers", include_hidden=True)

Exceptions

ExceptionParentDescription
BridgeErrorExceptionBase class for all DccBridge errors
BridgeConnectionErrorBridgeErrorDCC plugin not connected or connection lost
BridgeTimeoutErrorBridgeErrorCall timed out
BridgeRpcErrorBridgeErrorDCC plugin returned JSON-RPC error; attributes: .code, .message, .data

Resilience And Fallback

Adapters with multiple bridge paths can wrap them in a fallback client:

python
from dcc_mcp_core import BridgeFallbackClient, BridgeRetryPolicy, BridgeTransportStrategy

class WebSocketTransport(BridgeTransportStrategy):
    name = "websocket"
    def connect(self): ...
    def disconnect(self): ...
    def is_connected(self): ...
    def call(self, method, **params): ...

client = BridgeFallbackClient(
    [WebSocketTransport(), NamedPipeTransport()],
    retry_policy=BridgeRetryPolicy(attempts=3, initial_delay_secs=0.1),
)
result = client.call("scene.info")

BridgeRetryPolicy centralizes attempts and exponential backoff so DCC adapters do not each invent slightly different retry loops.

Reverse Bridge Sessions

Some plugin runtimes cannot host a listener or keep inbound sockets open. For those cases, the host can enqueue work and let the plugin poll:

python
from dcc_mcp_core import ReverseBridgeSession

session = ReverseBridgeSession(timeout=30)

# Host side
result = session.call("ps.document.info", include_layers=True)

# Plugin side
request = session.next_request(timeout=1.0)
if request is not None:
    response = run_in_host(request.method, **request.params)
    session.submit_response(request.id, result=response)

The request envelope can be serialized with request.to_jsonrpc() when the polling transport is HTTP, a named pipe, or an application-specific queue.

Released under the MIT License.