How the Harness Integration Connects to External Agents in magnitudedev/magnitude
The harness integration in magnitudedev/magnitude connects to external agents through a HarnessConnection service that implements a uniform API for listing, detecting, launching, and syncing external harnesses via the HarnessConnectorRegistry.
The magnitudedev/magnitude repository implements a sophisticated bridge between client-side code and external AI agents (harnesses) such as pi, opencode, and hermes. This harness integration provides a type-safe, effectful abstraction layer that allows the CLI to discover, validate, and communicate with external binaries through a consistent interface built on Effect-TS.
Core Architecture of the Harness Connection Service
The HarnessConnection Interface
At the heart of the integration lies the HarnessConnection service, defined in client-common/src/harness-connections/service.ts. This interface exposes methods for list, connect, launch, sync, and disconnect operations. The implementation ensures that all operations are wrapped in Effect-TS Effect types, providing functional error handling and composability.
The service uses a connection lock (withConnectionLock) and a mutation semaphore to guarantee consistency when multiple CLI instances access the shared connections.json manifest file simultaneously.
Service Factory Functions
The entry point for creating a connection service is makeHarnessConnection() located in cli/src/harness-connections/service.ts at lines 53-60. This factory checks for development environments and delegates to makeHarnessConnectionService():
export const makeHarnessConnection = Effect.suspend(() => {
const root = process.env.MAGNITUDE_PI_DEVELOPMENT_ROOT
if (root === undefined) return makeHarnessConnectionService()
// ...
return makeHarnessConnectionService(piDevelopmentConnectionOptions(root))
})
For production environments, it returns a standard service instance; for development, it configures specific connection options for the local Magnitude PI development root.
The Connection Lifecycle for External Agents
Step 1: Connector Registry Discovery
Before connecting to any external agent, the service initializes a HarnessConnectorRegistry via makeHarnessConnectorRegistry in cli/src/harness-connections/registry.ts. This registry maintains a catalog of all available external harness implementations, including pi, opencode, and hermes.
Each connector implements the HarnessConnector contract with required methods: detect, connect, launch, and sync, plus an optional companion handler for complex agent setups.
Step 2: Installation Detection
Before establishing any connection, the service executes the detect function (referenced in service.ts at lines 94-98) to verify the harness executable exists on the system. This search uses harnessExecutableSearchPath to locate binaries and returns a HarnessInstallation object describing the binary path and version.
If detection fails, the connection process halts with a typed error, preventing attempts to connect to uninstalled agents.
Step 3: Model Resolution
For Magnitude-owned harnesses, the service queries available AI models through discoverMagnitudeModels (lines 55-59 in service.ts). This creates an inference client via makeInferenceClient().listModels() and transforms the results into HarnessModel objects using toHarnessModel, giving external agents a structured list of available capabilities.
Step 4: Establishing the Connection
The connect(harnessId, options) method orchestrates the full connection sequence:
- Retrieves the connector from the registry
- Verifies harness installation via
detect - Validates the requested
modelIdexists in the available models - Reads the persisted manifest from
connections.json - Constructs a
HarnessConnectionSpeccontaining models, selected model, and installation details - Optionally installs skills or startup scripts
- Invokes the connector's
connectmethod (orcompanion.reconcile/connectfor companion-enabled harnesses) - Atomically updates
connections.jsonwith the new state
This implementation spans lines 45-73 in cli/src/harness-connections/service.ts.
Step 5: Launching and Managing Processes
Once connected, the launch(harnessId, modelId) method (lines 21-26) generates a HarnessLaunchPlan. For external agents, this plan specifies the exact command line, arguments, and environment variables required to spawn the harness process. The CLI uses this plan to execute the external binary with the correct configuration.
The sync operation (lines 30-38) refreshes the manifest with current model availability, while disconnect (lines 86-94) removes harness entries and executes connector-specific cleanup logic.
Implementing External Agent Connectors
External agents integrate by implementing the HarnessConnector interface in files under cli/src/harness-connections/connectors/. The Open-Code harness in connectors/opencode.ts demonstrates this pattern:
export const openCodeProviderConfig: HarnessConnector = {
id: "opencode",
name: "OpenCode",
detect: (searchPath) => { /* check for opencode binary */ },
connect: (spec) => { /* establish RPC or process connection */ },
launch: (modelId, installation) => { /* return HarnessLaunchPlan */ },
// optional companion handling
}
These connectors register automatically with the HarnessConnectorRegistry, making them available to list and connect calls throughout the CLI.
Practical Implementation Examples
Creating a Connection from the CLI
To instantiate the harness connection service in development or production scripts:
import { makeHarnessConnection } from "./harness-connections/service"
const connection = await Effect.runPromise(makeHarnessConnection)
const list = await Effect.runPromise(connection.list)
This pattern appears in scripts/dev-pi.ts and cli/src/commands/connections-runtime.ts, demonstrating how the CLI bootstraps the harness integration.
Connecting to a Specific External Agent
To initiate a connection with configuration options:
await Effect.runPromise(
connection.connect("opencode", {
model: Option.some("gpt-4"),
installSkill: true,
launchOnStartup: false,
})
)
This triggers the full connection flow, ultimately invoking openCodeProviderConfig.connect with the provided HarnessConnectionSpec.
Launching a Harness Process
To start an external agent process for a specific model:
const launchPlan = await Effect.runPromise(connection.launch("pi", "pi-gpt"))
// launchPlan contains: command, executable, args, env
The returned HarnessLaunchPlan provides the CLI with the exact executable path and args array needed to spawn the process using standard Node.js child process APIs.
Summary
- The harness integration in magnitudedev/magnitude uses the
HarnessConnectionservice to bridge client code and external agents through a unified API. - Effect-TS powers all operations, ensuring type-safe error handling and concurrency control via connection locks and semaphores.
- The HarnessConnectorRegistry in
cli/src/harness-connections/registry.tsmaintains a catalog of available connectors likeopencode,pi, andhermes. - Each connector implements
detect,connect, andlaunchmethods to handle binary discovery, connection establishment, and process spawning. - The system persists connection state in
connections.json, managed atomically to prevent corruption during concurrent CLI access.
Frequently Asked Questions
What is the HarnessConnection service in Magnitude?
The HarnessConnection service is the core abstraction in magnitudedev/magnitude that manages relationships between the CLI and external AI agents. Defined in client-common/src/harness-connections/service.ts and implemented in cli/src/harness-connections/service.ts, it provides a functional interface using Effect-TS for listing, connecting, launching, and disconnecting external harnesses.
How does Magnitude detect external harness installations?
Magnitude uses the detect method on each HarnessConnector to locate executables via harnessExecutableSearchPath. This function returns a HarnessInstallation object containing the binary path, or fails if the harness is not found on the system. This detection runs automatically before any connect or launch operation.
What is the role of the HarnessConnectorRegistry?
The HarnessConnectorRegistry acts as a factory and catalog for all external agent implementations. Located in cli/src/harness-connections/registry.ts, it aggregates all available connectors (such as those in connectors/opencode.ts) and provides the HarnessConnection service with the specific implementation needed to communicate with each external agent type.
How does Magnitude handle concurrent connections to external agents?
The service implements a connection lock (withConnectionLock) and a mutation semaphore around all manifest operations. When multiple CLI instances attempt to modify connections.json simultaneously, these synchronization primitives ensure atomic updates and prevent race conditions that could corrupt the connection state.
Have a question about this repo?
These articles cover the highlights, but your codebase questions are specific. Give your agent direct access to the source. Share this with your agent to get started:
curl -s "https://instagit.com/install.md" Maintain an open-source project? Get it listed too →