Nova Agent
Nova is a browser-control layer for LLM agents, built directly on the Chrome DevTools Protocol (CDP). It exposes navigation, observation, clicking, typing and page-surveying as a small HTTP API that any model or agent runtime can call.
This repository contains the runtime code, not model weights.
Status
Early / experimental. The CDP bridge and the observation layer work. Everything described under "Roadmap" is not implemented yet.
What it actually does
| Capability | Status |
|---|---|
Attach to a running Chrome via CDP (:9222) |
Working |
| Navigate, wait for load, settle | Working |
| Observe page (URL, title, element counts) | Working |
| Click / type by CSS selector | Working |
survey β dump forms, inputs and buttons to a route cache |
Working |
Route recall across sessions (nova-routes.json) |
Working |
| Autonomous multi-step task execution | Partial, LLM-driven |
| Payment / commerce flows | Not verified |
| Self-replication | Not implemented |
Architecture
LLM / agent runtime
β HTTP (localhost:4243)
βΌ
nova-bridge.mjs ββββ WebSocket βββββΆ Chrome CDP (localhost:9222)
β
βββ .agent-state/nova-routes.json (learned page structure)
The bridge has no external dependencies β it uses Node 18+ built-in fetch
and WebSocket.
Why CDP instead of a screenshot loop
Most agent browser tooling either (a) drives a headless browser it owns, or (b) screenshots the screen and guesses at pixel coordinates. Nova attaches to the user's already-running, already-authenticated Chrome and reads the real DOM. That means:
- No separate login/session state to manage
- Structured page data instead of pixels, so the model selects elements rather than coordinates
surveypersists page structure, so a second visit to the same page needs no re-discovery
Quick start
# 1. Start Chrome with the debug port open
chrome --remote-debugging-port=9222
# 2. Start the bridge
node nova-bridge.mjs
# JACO Nova Bridge -> http://localhost:4243 (CDP :9222)
# 3. Drive it
curl localhost:4243/health
curl localhost:4243/observe
curl -X POST localhost:4243/navigate -d '{"url":"https://example.com"}'
curl -X POST localhost:4243/survey -d '{"label":"example-home"}'
Endpoints
| Method | Path | Body |
|---|---|---|
| GET | /health |
β |
| GET | /targets |
β |
| GET | /observe |
β |
| POST | /navigate |
{url, settleMs?} |
| POST | /click |
{selector, settleMs?} |
| POST | /type |
{selector, text, settleMs?} |
| POST | /survey |
{label?} |
Files
nova-bridge.mjsβ the CDP bridge (HTTP β CDP)nova-autonomous-agent.mjsβ task loop that drives the bridgenova-terminal.htmlβ local monitoring UI
Security notes
Nova drives a real, logged-in browser. Treat it accordingly:
- Bind the bridge to
127.0.0.1only (it does, by default). Do not expose port 4243. - CDP on
:9222grants full control of the browser profile to anything that can reach it. - Run it against a dedicated Chrome profile, not your primary one.
- There is no authentication on the bridge. Anything local can call it.
Known limitations
click/typerequire a CSS selector; there is no "click the button that says X" (:contains()is not valid CSS andquerySelectorwill throw on it).- Selector-based typing sets
.valueand firesinput/change. Some React and Vue inputs ignore this and need real key events instead. - One tab at a time; it picks the first non-
chrome://page target. - Errors come back as
{ok:false, error}with a 500 β there is no retry logic.
Roadmap
- Text-based element targeting (accessibility tree rather than CSS)
- Real key-event typing for framework-controlled inputs
- Multi-tab / multi-instance orchestration
- Auth on the bridge
License
MIT