IPC & Type Bindings
Relevant source files
The following files were used as context for generating this wiki page:
The Keynobi project utilizes a robust Inter-Process Communication (IPC) architecture to bridge its Rust-based backend with its SolidJS frontend. This system relies on Tauri 2.0's invoke and emit patterns, supported by automated type generation to ensure type safety across the language boundary.
The architecture is designed for "AI-first" development, where the IPC layer not only serves the internal UI but also exposes functionality through a Model Context Protocol (MCP) server for external AI agents like Claude Code.
Sources: AGENTS.md:6-15, README.md:120-135
Architecture Overview
Keynobi's IPC system is divided into two primary communication paths:
- Frontend-Backend IPC: Standard Tauri command invocation and event listening.
- External Agent IPC: A stdio-based MCP server that translates AI tool calls into internal service actions.
The following diagram illustrates the relationship between the various components and the IPC flow:
The diagram shows how both the Frontend and AI Agents interact with shared core services via different IPC protocols.
Sources: README.md:162-185, src-tauri/src/services/mcp_server.rs:41-75
Type Safety and Code Generation
To maintain synchronization between Rust models and TypeScript interfaces, the project uses the ts-rs crate. This allows Rust structs to define their TypeScript equivalents automatically during the build/test process.
Binding Workflow
- Rust Definition: Models are defined in
src-tauri/src/models/with#[derive(TS)]. - Generation: Running
npm run generate:bindings(which executescargo test) populates thesrc/bindings/directory. - Consumption: Frontend code imports types exclusively from
@/bindings.
Sources: AGENTS.md:14-15, 62-65, src/bindings/index.ts:1-13
Key Data Structures
| Type | Description | Source File |
|---|---|---|
LogEntry | Represents a single log line with levels and timestamps. | src/bindings/index.ts:16 |
ProjectEntry | Contains metadata for registered Android projects. | src/bindings/index.ts:47 |
BuildLine | A structured line of output from a Gradle build process. | src/bindings/index.ts:21 |
ProcessedEntry | Enriched logcat entry including package names and crash IDs. | src/bindings/index.ts:55 |
Command Pattern (Invoke)
Tauri commands are implemented as thin wrappers in Rust that validate inputs and delegate business logic to services.
Example: File System Commands
The backend exposes several commands for project management, such as opening folders and detecting Gradle roots.
#[tauri::command]
pub async fn open_project(
app_handle: tauri::AppHandle,
path: String,
state: State<'_, FsState>,
) -> Result<String, AppError> {
// ... validation and delegation ...
}
Sources: src-tauri/src/commands/file_system.rs:77-81
Frontend Wrappers
The tauri-api.ts file provides strongly-typed async wrappers for these commands, abstracting the raw invoke calls.
| API Function | IPC Command | Purpose |
|---|---|---|
openProject(path) | open_project | Opens and canonicalizes a project path. |
runGradleTask(task, onLine) | run_gradle_task | Starts a build and provides a stream channel. |
listAdbDevices() | list_adb_devices | Polls connected Android devices. |
Sources: src/lib/tauri-api.ts:17-21, 140-144, 219-221
Event Pattern (Emit/Listen)
For high-frequency or asynchronous data like build logs and logcat streams, the system uses Tauri Events.
Batching and Performance
To prevent UI thread flooding, the backend batches events. For example, adb logcat events are emitted in 100ms batches from the Rust layer.
The sequence shows the transition from individual log lines to a batched IPC emission.
Sources: README.md:191-193, src/lib/tauri-api.ts:316-318
Model Context Protocol (MCP) Integration
The MCP server provides an alternative IPC interface for AI tools. It operates over stdio using JSON-RPC 2.0.
Server Modes
- GUI Mode: Started via the
start_mcp_servercommand, sharing state with the active window. - Headless Mode: Launched with the
--mcpCLI flag, operating independently of the UI.
Tool Registration
Tools are registered in Rust using macros from the rmcp crate, defining the schema and parameters exposed to the AI.
| Tool Name | Parameters | Description |
|---|---|---|
run_gradle_task | task, variant | Executes Gradle commands via the build runner. |
get_logcat_entries | count, min_level, tag | Retrieves filtered logs from the ring buffer. |
install_apk | device_serial, apk_path | Deploys an APK to a specific device. |
Sources: src-tauri/src/services/mcp_server.rs:18-35, 150-165, 345-356
Summary
Keynobi's IPC and type binding system provides a unified interface for both human users (via the SolidJS frontend) and AI agents (via the MCP server). By leveraging ts-rs for automated type generation and Tauri's optimized communication channels, the project maintains a high degree of technical accuracy and performance across the Rust-TypeScript boundary.