Communication Protocol
Relevant source files
The following files were used as context for generating this wiki page:
- Packages/src/Editor/Server/FrameParser.cs
- Packages/src/TypeScriptServer~/src/utils/content-length-framer.ts
- Packages/src/Editor/Api/JsonRpcProcessor.cs
- Packages/src/Editor/Server/MessageReassembler.cs
- Packages/src/ARCHITECTURE.md
- Packages/src/TypeScriptServer~/README.md
- Packages/src/TypeScriptServer~/src/constants.ts
The uLoopMCP system employs a multi-layered communication architecture to connect external LLM-powered development tools (MCP Clients) with the Unity Editor. This protocol facilitates remote execution of commands, such as compiling code, running tests, and manipulating scene objects, enabling an autonomous development loop driven by AI.
The communication is split into two primary segments. First, MCP Clients communicate with a TypeScript-based server using the standard Model Context Protocol (MCP) over stdio. Second, this TypeScript server acts as a bridge, communicating with a C# TCP server running inside the Unity Editor. This second segment uses a custom TCP-based protocol built on JSON-RPC, which is the focus of this document.
Sources: Packages/src/ARCHITECTURE.md
System Architecture
The overall system consists of three main components: MCP Clients, the TypeScript Server, and the Unity Editor. The communication flows from the client, through the TypeScript server, to the Unity Editor, and back.
The following diagram illustrates the high-level architecture and communication flow.
Sources: Packages/src/ARCHITECTURE.md
TypeScript Server to Unity Editor Communication
Communication between the TypeScript server and the Unity Editor occurs over a local TCP socket. Messages are structured as JSON-RPC 2.0 requests and responses. To handle the stream-based nature of TCP, a Content-Length framing protocol is used to delineate individual messages.
Sources: Packages/src/ARCHITECTURE.md, Packages/src/TypeScriptServer~/README.md
Message Framing
All JSON-RPC messages are prepended with a Content-Length header. This ensures that the receiving end can read the exact number of bytes for a complete JSON message, preventing issues with fragmented packets or multiple messages in a single TCP read.
The frame structure is as follows:
| Part | Format | Description |
|---|---|---|
| Header | Content-Length: {size}\r\n\r\n | Specifies the size of the JSON payload in bytes. |
| Payload | { "jsonrpc": "2.0", ... } | The UTF-8 encoded JSON-RPC message. |
Sources: Packages/src/Editor/Server/FrameParser.cs:12-14, Packages/src/TypeScriptServer~/src/utils/content-length-framer.ts:8-13
The diagram below shows how a JSON payload is framed before being sent over the TCP stream.
On the C# (Unity) side, the FrameParser class uses a regular expression to extract the Content-Length from the header.
// Packages/src/Editor/Server/FrameParser.cs:12-14
private static readonly Regex HeaderRegex = new Regex(
@"Content-Length: (?<length>\d+)\r\n\r\n",
RegexOptions.Compiled);
Message Reassembly and Parsing
On the Unity side, incoming data from the TCP socket is managed by the MessageReassembler class. This class is crucial for handling cases where TCP packets are fragmented and a complete message does not arrive in a single read operation.
The process is as follows:
- The
MessageReassemblerbuffers incoming byte data. - It continuously tries to parse a complete frame (header + payload) from its buffer using the
FrameParser. - If a complete frame is found, it's passed on for processing, and the corresponding bytes are removed from the buffer.
- If the buffer contains an incomplete frame, it waits for more data to arrive.
This ensures that only complete and valid JSON messages are passed to the JSON-RPC processor.
The following class diagram shows the relationship between the key components in the message reassembly and parsing process.
JSON-RPC Processing
Once a complete JSON message is extracted, it is handed over to the JsonRpcProcessor. This class is responsible for:
- Deserializing the JSON string into a
JsonRpcRequestobject. - Validating the request (checking for
jsonrpc,method,id). - Invoking the corresponding tool or method based on the
methodproperty. - Handling the asynchronous execution of the tool.
- Constructing a
JsonRpcResponse(orJsonRpcError) and serializing it back to a JSON string to be sent back to the TypeScript server.
Sources: Packages/src/Editor/Api/JsonRpcProcessor.cs
An example of a JSON-RPC request to run a compilation is shown below.
{
"jsonrpc": "2.0",
"id": 1,
"method": "compile",
"params": {
"forceRecompile": false
}
}
Sources: Packages/src/TypeScriptServer~/README.md
The following sequence diagram illustrates the entire lifecycle of a request from the moment raw data arrives at the Unity TCP server until a response is sent.
Protocol Constants
The communication protocol relies on several constants defined in both the C# and TypeScript codebases to ensure consistency.
| Constant | Value | Description | Source File |
|---|---|---|---|
JSONRPC.VERSION | "2.0" | The version of the JSON-RPC protocol used. | Packages/src/TypeScriptServer~/src/constants.ts:40-42 |
UNITY_TCP_PORT_ENV_KEY | UNITY_TCP_PORT | Environment variable to specify the TCP port. | Packages/src/Editor/Config/McpConstants.cs:26 |
UNITY_CONNECTION.DEFAULT_PORT | "8700" | The default TCP port used for communication. | Packages/src/TypeScriptServer~/src/constants.ts:34-38 |
UNITY_CONNECTION.DEFAULT_HOST | "127.0.0.1" | The default host (localhost). | Packages/src/TypeScriptServer~/src/constants.ts:34-38 |
Summary
The communication protocol between the uLoopMCP TypeScript server and the Unity Editor is a robust system designed for reliable, asynchronous command execution. It leverages the standard JSON-RPC 2.0 format for message content and implements a custom Content-Length framing layer to ensure message integrity over TCP. On the Unity side, a MessageReassembler handles fragmented data, while the JsonRpcProcessor orchestrates request handling and tool execution. This architecture provides a solid foundation for extending the system with new tools and capabilities for AI-driven development within Unity.