Robert Brennanandopenhands 8482aeda26 Add multi-step onboarding modal (#257)
* Add multi-step onboarding modal with agent/backend/LLM/hello steps

Adds a four-step welcome flow that appears on first visit (gated by an
`openhands-onboarded` localStorage flag) on the home route:

  0. Choose Agent — OpenHands selectable, Claude Code & Codex disabled
     with a "coming soon" note
  1. Check Backend — embeds the existing backend edit form, plus a
     live connection banner driven by useBackendsHealth
  2. Set up LLM — embeds the existing LlmSettingsScreen
  3. Say hello — pre-filled greeting input that launches a fresh
     conversation with no workspace

Each step lives in its own panel; advancing slides the rail
horizontally for the slide-in-from-the-right animation. A top progress
bar reflects the current step.

Also extracts a reusable BackendForm out of BackendFormModal so the
backend step can render the same form inline, and adds an
`onSaveSuccess` hook to LlmSettingsScreen so the onboarding flow can
auto-advance after saving.

Tests: 14 new tests cover the progress bar, completion hook, agent
chooser, and full modal navigation.

Co-authored-by: openhands <openhands@all-hands.dev>

* Fix onboarding slide rail layout & promote 'coming soon' note

Two related fixes for the onboarding modal:

1. Slide rail was using `width: 400%` + `translateX(-N * 100%)` on the
   rail itself. CSS translate percentages are relative to the
   *element's own* width, so on step 2 the rail shifted by its full
   2240px width — pushing all step content off-screen and leaving an
   empty modal sized to the tallest step. Reworked the rail so each
   slide now translates by `(index - currentStep) * 100%` of its own
   width, with inactive slides absolute-positioned (`inset-0`) inside
   a relative parent. Active slide drives the modal height; inactive
   slides no longer contribute vertical space, eliminating the
   funky-overhang behavior.

2. Moved the 'Support for other agents coming soon!' note from a tiny
   italic line at the bottom of the agent step to a prominent
   primary-tinted callout pinned to the top, with a Sparkles icon and
   bumped-up typography.

Tests assert per-slide transforms and active state instead of a
single rail transform; existing flow tests still cover the full
0 → 3 progression.

Co-authored-by: openhands <openhands@all-hands.dev>

* Polish onboarding LLM step: embed inline + default to Anthropic/Opus

The third onboarding step embedded `LlmSettingsScreen` as-is, which
brought along the screen's sticky `bg-base` save bar. In the modal
that rendered as a dark stripe overlapping the rest of the form, and
the existing per-step Next button created a confusing duplicate CTA
alongside Save Changes.

- Add an `embedded` prop to `SdkSectionPage` (and forward it through
  `LlmSettingsScreen`) that drops the sticky positioning + contrast
  background so the Save button just sits inline at the bottom of
  the form, blending with the modal panel.

- Add an `initialValueOverrides` prop to `SdkSectionPage` that wins
  over `useSettings`-derived defaults and pre-marks the overridden
  keys dirty so the Save button is enabled on mount. Use it from the
  onboarding LLM step to pin the model to
  `anthropic/claude-opus-4-5-20251101` per the spec, instead of the
  global OpenHands-prefixed default.

- Drop the redundant `onboarding-llm-next` button. Saving is now the
  primary advance action via the existing `onSaveSuccess` hook; a
  small "Skip for now" link remains for users who want to fill this
  in later.

Onboarding modal test updated to drive step 2 to step 3 via the skip
link.

Co-authored-by: openhands <openhands@all-hands.dev>

* Drive LLM step's save from the onboarding Next button

The previous polish pass left the LLM settings form's "Save Changes"
button visible inside the onboarding modal, with a separate "Skip for
now" link doing the advancing. That's the wrong shape for an
onboarding flow — every other step has a single primary Next button at
the modal footer, and the user expects clicking Next to commit the
form and advance.

- Add `hideSaveButton` and `onSaveControlChange` props to
  `SdkSectionPage` (forwarded through `LlmSettingsScreen`). The first
  suppresses the built-in Save button + the `pb-20` placeholder it
  reserved; the second hands the parent a stable `save()` callback
  plus `{ isSaving, isDirty }` state so it can render its own button.

- Rebuild `SetupLlmStep`'s footer as a single primary "Next" button
  matching the Backend step. Clicking Next:
    * triggers `saveControl.save()` if there are dirty fields;
      `onSaveSuccess` (wired to `onNext`) advances when the mutation
      resolves successfully.
    * falls through to `onNext()` when nothing is dirty, so users
      with already-configured settings aren't blocked.
  The Next button stays disabled while a save is in flight.

- Drop the previously-added "Skip for now" affordance — Next now
  covers the no-dirty-fields case.

- Restore the test selector to `onboarding-llm-next` so the modal
  test continues to drive step 2 → 3 the way users will.

Co-authored-by: openhands <openhands@all-hands.dev>

---------

Co-authored-by: openhands <openhands@all-hands.dev>
2026-05-10 11:25:50 -07:00
2026-04-24 17:33:22 -04:00

agent-canvas

Warning

This project is in sandbox phase. It may be vibecoded, untested, or out of date. OpenHands takes no responsibility for the code or its support. Learn more.

Agent Canvas is a web frontend for managing agents. You can:

  • ⌨️ prompt them manually
  • 🕐 run them on a schedule
  • ⚡ trigger them automatically—e.g. from Slack or GitHub.

Agents can run anywhere:

  • 🧑‍💻 on your laptop
  • 🖥️ on a remote virtual machine
  • ☁️ in our hosted cloud
  • 🏢 or inside your company’s infrastructure

You can work with any agent (e.g. Claude Code, Codex) or connect directly to an LLM (e.g. Anthropic, OpenAI, Gemini, Mistral, Minimax, Kimi).

If you have questions or feedback, please open a GitHub issue or join the #proj-agent-canvas channel in Slack

Quickstart

Prerequisites:

  • Node.js 22.12.x or later
  • npm
  • Docker

Set $PROJECT_PATH to the directory on your machine where your projects live (e.g. /path/to/your/projects). The agent server will mount this directory so the agent can read and edit your code.

export PROJECT_PATH=/path/to/your/projects
git clone https://github.com/OpenHands/agent-canvas.git
cd agent-canvas
npm install
npm run dev:docker

Access the UI at http://localhost:8000

Without Docker

Warning

This runs the agent-server directly on the machine you're installing on--the agent will have full access to your filesystem!

Prerequisites:

  • Node.js 22.12.x or later
  • npm
  • uv (for running the agent server via uvx)
git clone https://github.com/OpenHands/agent-canvas.git
cd agent-canvas
npm install
npm run dev:dangerously-dockerless

Access the UI at http://localhost:8000

Architecture

Agent Canvas is powered by the OpenHands Agent Server, a REST API for running multiple agents on a single machine. Each Agent Server runs on a single host/port; the Agent Canvas can connect to multiple Agent Servers and easily flip between them.

You can run an Agent Server anywhere:

  • Directly on your laptop (be careful!)
  • Inside a Docker container
  • On a dedicated machine like a Mac Mini
  • On a virtual machine in the cloud
  • Inside a Kubernetes Pod
  • Inside OpenHands Cloud (our commercial offering)

The Agent Server is often paired with an Automation Server, which lets you set up agents that run on a schedule or in response to events.

image

More documentation

For contributor and developer workflows, including frontend-only mode, mock mode, environment variables, and build/test commands, see DEVELOPMENT.md.

S
Languages
TypeScript 93.7%
JavaScript 4.7%
Python 0.9%
Shell 0.3%
CSS 0.2%
Other 0.1%