Loading image...Kiro

Product

  • About Kiro
  • Agents
  • IDE
  • CLI
  • Web
  • Mobile
  • Crew
  • Pricing
  • Downloads

For

  • Enterprise
  • Startups
  • Students

Community

  • Overview
  • Ambassadors
  • Case studies
  • Discord
  • Events
  • Powers
  • Shop
  • Showcase

Resources

  • Docs
  • Blog
  • Changelog
  • FAQs
  • Videos
  • Report a bug
  • Suggest an idea
  • Billing support

Social

Site TermsLicenseResponsible AI PolicyLegalPrivacy PolicyCookie Preferences
Kiro
  • Agents
  • Enterprise
  • Pricing
  • Docs
SIGN INDOWNLOADS
Kiro

Get Started

InstallationAuthenticationYour first project

Models

OverviewAvailable modelsReasoning effortAWS GovCloud (US) models

Features

How Kiro worksLocal command sandboxACP integrations
Specs
Steering
Hooks
MCP
Permissions
Custom agents
Workflows
Agent Skills
Powers
Cloud sessionsMemoryCompactionKiroignoreCheckpoints and rewind
Built-in tools
Configuration scopes

IDE 1.x

What's new in 1.0
Setup & First Run
Editor
Chat
Experimental
Troubleshooting0.x reference

CLI

Setup & First RunChoose an agent harness
Terminal UI
Chat
Fullscreen modeVoice modeHeadless modeACPAuto complete
Experimental
Troubleshooting
Upgrade from CLI 2.x
2.x reference

Crew

Quick startInstallationRunning 24/7
Chat
Agent Capabilities
Features
Subagents
Scheduling
Artifacts
Agent backends (Preview)
Multi-instance
Task Runner
Workflows
Memory
Knowledge
Snapshot & restore
Browser
Computer Use
Interfaces
Apps
System & storageConfigurationSecurityTroubleshooting

Web

Setup & First RunIdentity Center
Connect your repositories
Working with the agent
Autonomous modeScheduleConfiguration Sync
Sandbox

Mobile - Preview

Overview

Commands and Reference

CLI commandsSlash commandsBuilt-in toolsExit codesSettings

Billing

OverviewManaging your subscriptionUpgrading your planDowngrading your planCancelling your planPurchasing add-on creditsManaging your paymentsManaging usage notificationsManaging your taxesContacting billing supportDeleting your accountRelated questions

Enterprise

ConceptsOnboarding quickstart
Connecting your identity provider
Deployment optionsSubscribe your teamManage subscriptions
Governance
Monitor and track
SettingsManaged updatesTLS inspection compatibilityBillingIAMSupported regions
AWS GovCloud (US)

Privacy and Security

OverviewData protectionCode referencesCompliance validationInfrastructure securityIAM permissionsFirewalls, proxies, and data perimetersVPC endpoints (AWS PrivateLink)

Guides

OverviewRunning Kiro in the cloud
Language support
Learn by playing

Migration

Migrating from Q DeveloperMigrating from VSCodeUpgrading from Q CLI
  1. Docs
  2. Crew
  3. Features
  4. Multi-instance
View as Markdown

Multi-instance

View as Markdown

Run Kiro Crew on remote development hosts, EC2 instances, home servers, or disposable Fargate tasks and reach them from one local dashboard. Long-lived instances expose a loopback Gateway through an SSH or AWS SSM port forward. Fargate exposes a task-scoped turn API through AWS SSM, with no inbound network rule.

Opt-in. Off by default.

Remote crew sessions (Preview)

Set instances.enabled to true and restart the Gateway, connect a crew under Settings → Remote Crew, then enable Settings → Developer → Feature Previews → Remote crew sessions. A remote crew is another machine you have connected, not one of your agents.

With the preview on, the Sessions list puts Local first, then one collapsible group per connected crew. Each group header carries an Online, Reconnecting, Error, or Offline badge, so you can see which machines are reachable before you open a session. Collapsing a group hides its rows without changing your selection. A dashboard with no connected crews shows no group headers.

Opening a session from a crew group opens a window onto that crew's own session. The transcript, the running state, and any pending approval are read from the peer through the hub's proxy, and every action (send, stop, approve, continue, regenerate, rewind) calls the peer's own route. Nothing from the session is stored on this machine beyond an in-memory cache.

Both machines must run the same Kiro Crew version. On a mismatch the window names the version each side runs; update one so they match.

Auto-connect behavior is under Settings → Remote Crew → Auto-connect crews.

Chats from the retired turn relay

Before 0.9, the Chat on a crew preview ran each turn of a local chat on the selected remote crew through a turn relay while the transcript stayed on this machine. That relay no longer exists. A chat an older build ran through it still opens, read-only: sending, regenerating, and any other action that would start a turn is refused with a notice that the chat ran on a remote crew. To continue that work, open the crew's own session through Remote crew sessions.

Enable remote crews

bash
kirocrew config set instances.enabled true

The Gateway reads instances.enabled at startup, so restart it after changing the value. On restart it creates the instance registry and starts managing eligible connections.

Connection methods

SSH

Use a hostname, user@host, or SSH config alias. Authentication must work without an interactive prompt, normally through ssh-agent or a configured identity file.

AWS SSM

Use an EC2 instance ID or SSM managed-instance ID with an AWS profile and region. The local machine needs the AWS CLI and Session Manager plugin, and the remote instance needs SSM Agent plus the required IAM permissions. The connection uses port forwarding and requires no inbound SSH rule.

AWS Fargate

Fargate is intended for disposable remote workers. The remote crew runs as an ECS task and is reached through an SSM forward to its turn API, with no public listener or embedded remote dashboard. Configure the Fargate placement, digest-pinned image, and secret references in the optional fargate block of cloud.json; the Cloud surface shows the connection and task state.

A task lives for six hours by default. Set fargate.task_ttl_seconds to choose a different positive lifetime. The runtime admits at most ten Fargate crew tasks at once; this safety ceiling is fixed rather than a cloud.json setting.

The laptop that connects needs the AWS CLI and Session Manager plugin. Fargate uses the same owner-only remote-crew controls as the other connection methods.

Pin an EC2 launch to a subnet

With instances.enabled on, the built-in EC2 launch form under Settings → Remote Crew accepts an optional Subnet ID. Supplying one places the crew in that subnet and its VPC. Kiro Crew checks for a NAT or internet-gateway route before launch and stops with the missing route named when the subnet has no internet egress.

How it works

┌── Hub gateway (this host) ──┐ │ /instances page (React) │ │ ├─ tab strip: Home · A · B │ │ ├─ warm <iframe>s per tab │ http://127.0.0.1:<local_port>/?token=… │ └─ Manage panel │ add / connect / diagnose / restart / remove │ │ │ instances/ package │ │ ├─ registry │ ~/.kiro/crew/instances.json │ ├─ port_allocator │ loopback ports from base 7778 │ ├─ token_mint │ ssh <host> kirocrew token → JWT (never logged) │ ├─ ssh_tunnel_manager │ supervised ssh -N -L, probe, self-heal, refresh │ └─ diagnostics │ ssh → remote-dashboard → local-forward ladder └──────────────────────────────┘ │ ssh -N -L 127.0.0.1:<local>:127.0.0.1:<remote> ▼ ┌── Remote gateway ────────────┐ │ kirocrew gateway bound to │ │ 127.0.0.1:<remote_port> │ └──────────────────────────────┘

Each instance you add produces a supervised ssh -N -L child. The tunnel forwards 127.0.0.1:<local> → remote 127.0.0.1:<remote>. The hub mints a dashboard token on the remote over SSH and embeds the remote dashboard in an iframe at the loopback URL.

The lifecycle

  1. Connect — POST /api/instances/{id}/connect allocates a loopback port, mints a token on the remote over SSH, starts ssh -N -L, waits until the local forward accepts a connection, then returns the live status
  2. Warm set — by default the warm set sizes itself automatically for eligible instances, capped at 8; set instances.warm_set_cap to a positive value for a fixed limit. Warm instances keep a live tunnel + WebSocket. Connecting beyond the cap lazily evicts the least-recently-used
  3. Health probe — while connected, a probe polls the loopback forward every 30 s; after 3 consecutive failures it tears the child down so recovery fires
  4. 2-tier self-heal — on unexpected exit: tier 1 rebuilds the tunnel reusing the existing token; tier 2 re-mints the token then rebuilds. Capped at 8 attempts with capped-exponential backoff (~2 min window)
  5. Proactive token refresh — a per-instance loop re-mints the token at 0.8 of its TTL, ahead of the ~20h cap
  6. Diagnose / restart — ?diagnose=1 runs a failure-probe ladder on demand; POST .../restart restarts the remote gateway over SSH

Adding an instance

Open Settings → Remote Crew, select Add remote crew, and choose the connection method.

MethodTarget fields
SSHHostname, user@host, or SSH config alias, plus the remote Gateway port
AWS SSMEC2 instance ID (i-*) or managed-instance ID (mi-*), AWS profile, region, and optional run-as user
FargateThe registered ECS task target created by the Cloud launch flow, plus AWS profile and region

All methods take a display name. Long-lived SSH and SSM Gateways also use a dashboard-token lifetime. A value beginning with - or a target that does not match its method is refused before a child process starts.

Remote host types

Development host or home server

Use your SSH config alias or user@hostname. Authentication must succeed non-interactively through ssh-agent or configured keys.

EC2 and other key-based hosts

Configure an SSH alias on the hub, then use that alias as the SSH target:

Host my-ec2 HostName ec2-1-2-3-4.compute-1.amazonaws.com User ec2-user IdentityFile ~/.ssh/my-key.pem ProxyJump bastion-host

For an EC2 instance with no inbound SSH port, choose AWS SSM directly or use an SSM ProxyCommand in the SSH alias.

Prerequisites on the hub:

  • A passphrase-less key or an ssh-agent holding it (BatchMode won't prompt)
  • kirocrew installed and a gateway running on the EC2 instance's loopback port

What's supported

NeedStatusHow
Custom login user✅user@host or ssh-config User
FQDN / IP✅direct ssh_host value
Identity file (-i)⚠️ via ssh config onlyIdentityFile in a Host block
Non-22 SSH port⚠️ via ssh config onlyPort in a Host block
Bastion / ProxyJump⚠️ via ssh config onlyProxyJump / ProxyCommand
SSM-only instances⚠️ via ssh config onlyProxyCommand with aws ssm start-session

Crews reached through another crew

A remote dashboard can expose remote crews of its own. When you connect one inside that pane, your local dashboard adopts it as a top-level switcher tab. The tab is indented under the parent crew whose SSH tunnel carries it, and becomes unavailable when that parent is down.

A chain supports two hops, from your dashboard through one SSH-connected crew to another. One parent can carry at most eight chained crews. Removing the parent removes its chained entries from your dashboard.

Managing instances

The Manage panel gives you these per-instance actions:

  • Connect — open a tunnel + iframe
  • Disconnect — tear down the tunnel
  • Diagnose — run the failure-probe ladder and report the first broken link
  • Restart — restart the remote gateway over SSH (service-aware)
  • Edit — change name / host / port / TTL
  • Remove — disconnect then delete

Security model

Every route in /api/instances/* is gated by _guard():

  • Deny-by-default — reject Slack-origin requests (403)
  • Owner-only — require request["user"] (authenticated dashboard session)
  • Feature-gated — require instances.enabled: true
  • SEL-audited — every call (success and denial) emits an audit event

Beyond the guard:

  • Loopback-only forwards — ssh -N -L 127.0.0.1:<local>:127.0.0.1:<remote>
  • No local shell — ssh is always invoked with an argv list; ssh_host cannot inject local shell syntax
  • Charset-validated inputs — ssh_host and remote_bin rejected if they contain shell metacharacters or lead with -
  • Short-lived tokens — ≤20 h, returned only in-memory to the caller, never logged, never in list/status payloads
  • postMessage origin check — the parent validates every embedded-frame event.origin against the exact http://127.0.0.1:<port> of a currently-warm tunnel before trusting an unread-count message

Configuration

For instances.enabled and the other multi-instance settings, see Configuration.

Troubleshooting

SymptomFix
/instances shows "multi-instance management is off"instances.enabled is false — set it and restart
Iframe is blankCSP frame-src relaxation only applies to active tunnel ports; ensure the instance is connected
Connect fails with SSH auth errorRefresh your SSH credentials (re-add key to ssh-agent); tunnels self-heal once SSH is restored
Connect failsUse Diagnose — the ladder reports the first broken link (ssh_unreachable, remote_down, or tunnel_down)
Instance keeps droppingHealth probe + 2-tier self-heal retry over ~2 min; if it gives up, diagnosis runs automatically. Check the remote gateway and SSH stability
An instance silently disappeared from the warm setLRU-evicted (warm set full). Raise instances.warm_set_cap or reconnect on demand
Page updated: October 20, 2026
Agent backends (Preview)
Task Runner