Skip to content
Agoraby Olimpia
Esc
↑↓navigate↵open⌘Jpreview
On this page

Workflows

End-to-end tool sequences for common agent tasks in Agora, from testing a web app to running parallel subagents and passing a CAPTCHA.

Each recipe shows the tool calls in order. Arguments are abbreviated; see the MCP tools reference for the full list. With a cursor token, the workspace argument is not needed.

Test a web app

browser_open(url: "http://127.0.0.1:3000")        → target, and what is visible
browser_fill(target, ref: "e4", text: "test@example.com")
browser_fill(target, ref: "e5", text: "...", submit: true)
browser_audit(target)                              → overflow, contrast, labels, SEO, LCP/CLS, broken links
browser_emulate(target, width: 390, height: 844, mobile: true)
browser_audit(target)                              → the same checks on mobile
browser_emulate(target, width: 0, height: 0)       → reset
cursor_complete(result: {issues: [...]})           → if you are a subagent

Each fill and click returns what changed on screen, so you do not need a snapshot between steps. Take a browser_screenshot only for a visual issue the audit cannot describe.

Extract data from a page

browser_open(url: "https://example.com/pricing")
browser_eval(target, expression: "[...document.querySelectorAll('.plan')].map(p => ({name: p.querySelector('h3').textContent, price: p.querySelector('.price').textContent}))")

browser_eval returns the JSON value in one call. If the page loads data late, call browser_wait(target, selector: ".plan") first.

Fan out parallel subagents

cursor_spawn(name: "acme",   goal: "Open https://acme.com/pricing and return the plans as JSON",
             permissions: ["browser"], launch: {adapter: "claude", model: "claude-haiku-5-5", effort: "low"})
cursor_spawn(name: "globex", goal: "Open https://globex.com/pricing and return the plans as JSON", ...)
cursor_spawn(name: "initech", goal: "...", ...)
cursor_wait(ids: ["cur_a", "cur_b", "cur_c"], timeout_ms: 600000)
                                                   → status, result and usage of each child

Spawn every child before waiting. Give each a self-contained goal; children do not see your conversation. Each child opens its own window, and children launched by Agora use the shared board to avoid duplicate work. To stop one early, cursor_control(id, op: "cancel").

Split a list of work items

When children share one list (pages to review, rows to check), let them coordinate through the board instead of assigning items yourself:

board_read()                                       → current claims and posts
board_post(kind: "claim", topic: "audit /settings")
                                                   → fails if another cursor holds or finished it: pick another item
... do the work ...
board_post(kind: "finding", topic: "audit /settings", text: "Save button has no label")
board_post(kind: "done", topic: "audit /settings")

Log in with help from a human

browser_open(url: "https://app.example.com/login")
browser_fill(target, ref: "e3", text: "<email the user gave you>", submit: true)
                                                   → CHALLENGE DETECTED, or an MFA prompt
human_request(reason: "Solve the CAPTCHA and enter the MFA code on app.example.com, then return control")
events_wait(types: "control.returned", wait_ms: 30000)
                                                   → repeat on timeout
browser_snapshot(target)                           → continue in the same tab, now logged in

Tell the user where to take control: the dashboard, the viewer URL from agora open <workspace>, or the Paseo panel. The login is kept in the workspace’s browser profile, so later sessions start logged in.

Drive a desktop app

desktop_launch(command: "gimp", args: ["/var/lib/agora-apps/input.png"])
desktop_windows()                                  → window id and geometry
desktop_screenshot(window: <id>, max_width: 1024)  → orient once
desktop_key(keys: "ctrl+shift+e")
desktop_type(text: "output.png")
desktop_key(keys: "Return")
desktop_screenshot(window: <id>)                   → check the result

Coordinates in a screenshot match desktop_click unless max_width scaled the image. Use control_surface(op: "acquire", surface: "win:<id>", ttl_ms: 60000) if other cursors might type into the same window. The program must be installed on the Agora host.

Branch a logged-in session

Requires the workspace permission.

workspace_op(op: "checkpoint", snapshot: true)     → tabs, layout, cursors and a copy of the profile
workspace_op(op: "fork", name: "experiment")       → a new workspace with a copy of the profile and home

Work in the fork without touching the original session. suspend and resume keep a workspace on disk and reopen its tabs.

Parallel development with worktrees

cursor_spawn(name: "fix-header", goal: "Fix the header overflow on mobile and run the tests",
             permissions: ["browser", "process"],
             worktree: {repo: "/srv/app", branch: "fix-header", base: "main"},
             launch: {adapter: "claude"})

The child gets its own git worktree and a port range (PORT, AGORA_PORT_BASE, AGORA_PORTS), so several children can run dev servers side by side and test them in their own tabs.

Last updated on

Was this page helpful?