One agent, every surface: how we built the Kiro agent harness - Kiro<br>Back to all posts<br>Early on in building Kiro, we started talking about what agentic development should feel like across a developer’s day. The picture we kept coming back to was one where sessions move between your laptop, a cloud sandbox, and back again without friction. You close your laptop at the end of the day and your Kiro session keeps running in the cloud. You check on it from your phone while you grab coffee. You open the Kiro IDE the next morning and pick up where you left off. You start a project in Kiro on the web, add context in the Kiro IDE, keep working in the Kiro CLI where you’re already running tests and iterating in the terminal, and check on progress from Slack. Agentic development should be one continuous conversation across every surface you work in.<br>Earlier this year, we realized that our agent architecture was preventing us from moving toward that vision. At the time, the Kiro IDE, CLI, and web clients each ran their own purpose-built agent with its own session format, tool set, and configuration model. Easily moving between sessions and environments requires a single agent that works the same way regardless of which client you’re using or where it’s running. In our client-dedicated agent architecture, a session that started in one client couldn’t move to another because the agents didn’t share enough common ground. This post covers how we consolidated those three agent codebases into a single Kiro agent harness (built, naturally, using Kiro itself) and the architecture decisions that make our vision now within reach.<br>Three diverging harnesses
When we started building Kiro, we optimized for speed and experimentation. We encouraged each client team to build their own agent harness. The agent harness is the orchestration layer that manages the agent loop, tool execution, sub-agent delegation, session management, configuration loading, and communication with the model. The IDE team built theirs in TypeScript to fit the Code OSS extension model, the CLI team built theirs in Rust for performance, and the web team built theirs in Python to stay close to the latest agent research.<br>Having separate harnesses let each team ship independently and iterate fast, but it also meant that each team made different choices. Session storage worked differently across clients. The permission systems were designed independently and used incompatible syntax: the CLI used regex-based allowedCommands/deniedCommands, while the IDE used prefix matching for trustedCommands and substring matching for its denylist. Compaction strategies diverged. Sub-agent context sharing followed different models. Custom agents worked differently in each client. Feature sets split too: spec-driven development and powers existed only in the IDE, while plan mode and code intelligence existed only in the CLI.<br>Implementation cost compounded over time. Every new capability had to be built and maintained three times, sometimes resulting in slightly varying agent behaviors. Bugs had to be fixed three times. Users experienced inconsistencies depending on which client they chose. Our vision of sessions moving across clients and compute was architecturally impossible because there was no shared session format, no shared tool set, and no shared configuration model. We considered agreeing on agent behavior contracts across clients and implementing them in each of the three harnesses, in order to maintain each team’s independence and individual speed. However, interface alignment also introduces coordination overhead that grows with every new feature. Every new feature needs a spec, three implementations, and ongoing validation that they behave identically.<br>The inflection point came as we prepared to publicly launch Kiro on the web. Rather than launch Kiro on the web with its own separate agent and continue paying that compounding implementation cost, we decided to build a single agent harness that combined the best of what each team had learned. A single harness eliminates duplication across teams and lets us invest all of our effort in one place.<br>Kiro agent harness architecture
A key architectural decision we made early was to build the harness as a standalone server process, not a library compiled into each client. We saw from earlier attempts that shared libraries don’t enforce a strong enough boundary. Client code ends up calling internal methods that weren’t intended to be exported, or layering its own agent logic on top of the library. Then you’re back to diverging implementations. A standalone process makes the separation real. The harness and clients don’t need to share a language or runtime, so each client can stay in whatever stack fits its platform.<br>Now, instead of three tightly coupled client-agent pairs:<br>Loading code example...
We have a clean separation between clients and a single agent harness:<br>Loading code example...
The Kiro agent harness is a...