Nova Agent - Browser automation agent for Nova QA platform
Project description
Nova Agent
Last analyzed: 2026-07-05
qanova-agent는 사용자의 로컬 환경에서 실행되는 Testvera 브라우저 자동화 Agent CLI다. 사용자는 Agent를 등록해 토큰을 저장하고, nova-agent start로 Gateway에 연결한다. Runner는 Gateway를 통해 Agent에 DOM 추출, script 실행, browser primitive command를 보내고 Agent는 로컬 Playwright 브라우저에서 이를 수행한다.
기술 스택
| 영역 | 사용 기술 |
|---|---|
| Runtime | Python 3.11+ |
| CLI | Typer, Rich |
| Browser | Playwright |
| WebSocket | websockets |
| Models/settings | Pydantic, pydantic-settings, python-dotenv |
| Serialization | orjson |
| Logging | structlog |
| HTTP/pairing/update check | urllib, pip/pipx |
| Test | pytest, pytest-asyncio |
실행 책임
Agent는 로컬 브라우저 실행과 Gateway 메시지 응답만 담당한다. AI 호출과 DB 업데이트는 Runner가 담당한다.
- 사용자 브라우저에서 Agent 등록 페이지 열기
- 웹 pairing 승인 후 1회 발급된 token을
~/.nova-agent/token에 저장 - Gateway
/ws/agent에Authorization: Bearer ...헤더로 연결 - Gateway registration 이후 system info 전송
- heartbeat 주기 전송
- job assignment 수락 또는 pool full 거절
- job별 browser session 생성/정리
- entry URL navigation
- DOM 추출과 screenshot 전송
- Runner가 보낸 Playwright script 실행
- Runner 공통 엔진이 보내는 browser primitive command 실행
- step/job 완료, 실패, 취소 message 전송
- reconnect 시 active job reset 알림
CLI 명령
| 명령 | 설명 |
|---|---|
nova-agent --version |
현재 Agent 버전 출력 |
nova-agent login |
pairing code로 FE Agent 등록 화면을 열고 승인된 token을 자동 저장 |
nova-agent start |
Gateway에 연결하고 job 대기 |
nova-agent doctor |
token, Gateway URL, 선택적 Playwright browser 준비 상태 진단 |
nova-agent test-connection |
Gateway 인증과 Agent 등록 handshake를 1회 테스트 |
nova-agent logs |
최근 Agent 로그 출력 |
nova-agent status |
token 저장 여부와 경로 표시 |
nova-agent version-check |
설치된 Agent와 PyPI 최신 버전 비교 |
nova-agent logout |
저장된 token 삭제 |
nova-agent update |
pip 또는 pipx로 최신 qanova-agent 패키지 설치 |
nova-agent install-deps |
Linux에서 Playwright system dependency 설치 |
start 옵션:
| 옵션 | 설명 |
|---|---|
--headless/--no-headless |
브라우저 headless 여부 |
--gateway-url, -g |
Gateway WebSocket URL override |
--pool-size, -p |
동시 browser 수, 1-10 |
--verbose, -v |
DEBUG logging |
login 옵션:
| 옵션 | 설명 |
|---|---|
--url, -u |
Frontend URL override |
--api-url |
pairing session을 만들 API base URL override |
--pairing-timeout |
브라우저 승인 대기 시간, 기본 600초 |
--manual |
구버전 서버용 수동 token 복사/붙여넣기 fallback |
doctor 옵션:
| 옵션 | 설명 |
|---|---|
--gateway-url, -g |
검증할 Gateway WebSocket URL override |
--check-browser |
Playwright Chromium 설치/실행 준비 상태 확인 |
test-connection 옵션:
| 옵션 | 설명 |
|---|---|
--gateway-url, -g |
테스트할 Gateway WebSocket URL override |
logs 옵션:
| 옵션 | 설명 |
|---|---|
--lines, -n |
출력할 최근 로그 라인 수, 기본 80 |
--path |
로그 파일 경로만 출력 |
설정과 token 저장
기본 설정은 src/nova_agent/settings.py에 있다. 환경 변수 prefix는 NOVA_다. NOVA_ENV=dev이면 프로젝트 .env, 기본 prod이면 .env.prod를 읽는다.
| 설정 | 기본값/설명 |
|---|---|
NOVA_GATEWAY_URL |
기본 wss://agent-gw.qanova.kr/ws/agent |
NOVA_API_URL |
기본 https://api.qanova.kr/api/v1 |
NOVA_FRONTEND_URL |
기본 https://qanova.kr |
NOVA_AGENT_REGISTER_PATH |
기본 /agent/register |
NOVA_HEADLESS |
기본 true |
NOVA_VIEWPORT_WIDTH, NOVA_VIEWPORT_HEIGHT |
기본 1920x1080 |
NOVA_POOL_SIZE |
기본 1 |
NOVA_HEARTBEAT_INTERVAL |
기본 30초 |
NOVA_CONNECTION_TIMEOUT |
기본 10초 |
NOVA_RECONNECT_DELAY |
기본 5초 |
NOVA_MAX_RECONNECT_ATTEMPTS |
기본 0, 무제한 |
NOVA_JOB_TIMEOUT |
job idle timeout, 기본 300초 |
NOVA_SCRIPT_TIMEOUT |
script timeout, 기본 30초 |
NOVA_ACTION_TIMEOUT |
단일 action timeout, 기본 10초 |
NOVA_MAX_SCREENSHOT_BYTES |
WebSocket으로 전송할 screenshot 원본 byte 상한, 기본 8MB, 0이면 제한 없음 |
NOVA_MAX_DOM_ELEMENTS |
WebSocket으로 전송할 interactive DOM element 상한, 기본 1000 |
NOVA_MAX_DOM_TEXT_CHARS |
DOM element별 text/value 최대 문자 수, 기본 200 |
NOVA_MAX_DOM_HTML_CHARS |
fallback raw HTML 최대 문자 수, 기본 30000, 0이면 raw HTML 생략 |
NOVA_LOCAL_AGENT_ALLOW_EXECUTE_SCRIPT |
Agent 기본 execute_script 허용 여부, 기본 true |
NOVA_LOCAL_AGENT_ALLOW_BROWSER_EVALUATE, NOVA_LOCAL_AGENT_ALLOW_BROWSER_CONTENT |
Agent 기본 browser evaluate/content 허용 여부, 기본 true |
NOVA_LOCAL_AGENT_ALLOW_STORAGE_STATE, NOVA_LOCAL_AGENT_ALLOW_ADD_COOKIES |
Agent 기본 storage/cookie primitive 허용 여부, 기본 true |
NOVA_LOCAL_AGENT_ALLOW_CDP |
Agent 기본 CDP primitive 허용 여부, 기본 false |
NOVA_LOCAL_AGENT_RESTRICT_NAVIGATION |
Agent 기본 navigation origin 제한 여부, 기본 false |
token은 ~/.nova-agent/token에 저장되고 권한은 0600으로 설정된다. ~/.nova-agent 디렉터리는 0700으로 수선되며, config directory 또는 token 파일이 symlink이면 읽기/쓰기를 거부한다. token path가 일반 파일이 아니어도 거부한다. token은 Gateway의 Agent JWT 검증에 사용된다.
Agent 로그는 ~/.nova-agent/agent.log에 rotating file로 저장된다. 기본 보관 정책은 파일당 5MB, backup 3개다. nova-agent logs로 최근 로그를 확인할 수 있다.
Local Agent가 execute_script 또는 위험 browser primitive(evaluate, content, storage_state, add_cookies, cdp_send, cdp_detach)를 허용/차단할 때 job/step/command id와 policy key를 structured log로 남긴다. script 본문, cookie 값, storage state 같은 민감 payload는 로그에 남기지 않는다. Runner가 job_assign.config.security_policy를 보내면 그 값이 우선하며, 누락된 policy key는 위 NOVA_LOCAL_AGENT_* 기본값을 따른다.
Local Agent가 dom_extracted, script_result, primitive browser screenshot 결과에 screenshot을 첨부할 때 screenshot 원본 byte가 NOVA_MAX_SCREENSHOT_BYTES를 넘으면 base64 본문을 생략하고 omitted=true, reason=too_large, original_bytes, max_bytes metadata만 전송한다. Runner는 screenshot이 없는 결과도 처리할 수 있어 대형 payload로 인한 WebSocket 불안정을 줄인다.
DOM payload는 interactive element 중심이며 NOVA_MAX_DOM_ELEMENTS, NOVA_MAX_DOM_TEXT_CHARS, NOVA_MAX_DOM_HTML_CHARS로 크기를 제한한다. Agent는 dom.payload_limits에 적용된 제한과 element_limit_reached, html_truncated, html_chars metadata를 함께 전송한다.
시작 흐름
- 사용자가
nova-agent login을 실행한다. - CLI가 API
POST /agent-pairings로 10분짜리 pairing session을 만들고 pairing code를 표시한다. - CLI가
FRONTEND_URL + /agent/register?pairingId=...&code=...를 브라우저로 연다. - 사용자가 웹앱에서 프로젝트와 Agent 이름을 선택하고 pairing code를 승인한다.
- CLI가 API
GET /agent-pairings/{pairingId}?code=...를 poll하다가 완료 응답의 token을 1회 수신한다. - CLI가 token을
~/.nova-agent/token에 저장한다. token은 브라우저에 표시되지 않는다. - pairing API가 없거나 브라우저 handoff 전에 생성 응답이 유효하지 않으면
nova-agent login은 수동 token 입력 방식으로 fallback한다. 명시적으로 수동 방식을 쓰려면nova-agent login --manual을 사용한다. API가429 Too Many Requests를 반환하면Retry-After안내를 표시하고 종료한다. 이 경우 수동 token 입력으로 자동 fallback하지 않는다. 승인 완료 응답에 token이 없으면 token을 저장하지 않고 명확한 오류로 종료한다. - 사용자가
nova-agent start를 실행한다. - CLI가 업데이트를 확인하고 Playwright Chromium 설치를 보장한다.
BrowserPool과JobManager를 생성한다.AgentWebSocketClient가 Agent token을 Authorization 헤더로 보내 Gateway에 연결한다.- Gateway의
registered메시지를 받으면 OS/arch/version/python/browser 정보를register메시지로 보낸다. - heartbeat와 message loop가 시작되고 job을 기다린다.
WebSocket protocol
Agent가 Gateway로 보내는 주요 메시지:
registerheartbeatjob_acceptedjob_assign_failedstep_starteddom_extractedscript_resultbrowser_command_resultstep_completedgoal_achievedjob_completederror
Gateway/Runner에서 Agent로 들어오는 주요 메시지:
registeredregister_ackheartbeat_ackjob_assignextract_domexecute_scriptbrowser_commandnext_stepjob_cancelgoal_achieved
goal_achieved는 Agent 내부에서 check_goal 결과처럼 처리되어 step 완료로 이어진다.
내부 구조
| 경로 | 설명 |
|---|---|
src/nova_agent/cli.py |
Typer CLI, login/start/status/logout/update/install-deps |
src/nova_agent/settings.py |
env 기반 runtime settings |
src/nova_agent/config.py |
token/config directory 관리 |
src/nova_agent/constants.py |
protocol constant, timeout constant |
src/nova_agent/websocket/client.py |
Gateway 연결, reconnect, heartbeat/message loop |
src/nova_agent/websocket/handlers.py |
message type별 handler |
src/nova_agent/websocket/heartbeat.py |
heartbeat loop |
src/nova_agent/executor/job_manager.py |
job session lifecycle, message execution, response 전송 |
src/nova_agent/executor/job_session.py |
job별 browser/session state |
src/nova_agent/executor/script_runner.py |
Runner가 보낸 script 실행 |
src/nova_agent/browser/pool.py |
동시 browser pool |
src/nova_agent/browser/manager.py |
Playwright browser/context/page, cookie/localStorage/header/test access key 설정 |
src/nova_agent/browser/dom_extractor.py |
Cloud Runner DomParserService와 맞춘 DOM extraction |
src/nova_agent/models |
job/message/dom model |
src/nova_agent/utils |
system info, domain matcher, logging |
Job lifecycle
job_assign수신- Browser pool slot 확인
- slot 없으면
job_assign_failedwithPOOL_FULL - slot 있으면 browser manager acquire
- scenario, steps, config, environment variables로
JobSession생성 job_accepted전송- entry URL로 navigation
- shared engine managed job이면 Runner가
extract_dom/browser_command로 주도 - legacy flow면 Agent가 첫 step 시작
- script/command 실행 중 새 tab/popup과 page close를 감지해 active page 복구
- terminal 또는 cancel 시 session cleanup과 browser release
BrowserManager 기능
BrowserManager는 Playwright Chromium/Firefox/WebKit 중 config browser type을 사용하고, 지원하지 않는 값은 Chromium으로 fallback한다.
지원 기능:
- viewport 설정
- headless, slow_mo, JS heap size, dev shm option
- storage_state, cookie, localStorage 적용
- extra HTTP headers
- test access key header를 route interception으로 주입
- permission grant
- network throttling
- popup/new page active page 전환
- dialog/download/network/console event capture
- DOM extraction용 page access
- browser primitive command 실행
Runner와 Cloud 모드의 동작 차이를 줄이기 위해 DOM extractor는 Cloud Runner의 selector/attribute/metadata extraction 정책을 따라간다.
로컬 개발
python -m venv .venv
source .venv/bin/activate
pip install -e ".[dev]"
python -m playwright install chromium
nova-agent --version
dev Gateway를 사용할 때:
NOVA_ENV=dev nova-agent start --gateway-url ws://localhost:9100/ws/agent --no-headless --verbose
prod 기본 URL은 secure WebSocket이므로 local Gateway에는 반드시 override가 필요하다.
테스트
pytest
현재 테스트는 browser, CLI, WebSocket 동작을 중심으로 구성되어 있다. message protocol이나 job manager를 바꾸면 Gateway/Runner 쪽 테스트와 함께 검증한다.
변경 시 같이 봐야 하는 프로젝트
| Agent 변경 | 같이 확인 |
|---|---|
| message payload/type 변경 | qanova-agent-gateway/gateway/models/message.py, qanova-runner/gateway_client |
| token/JWT 처리 변경 | qanova-api AgentController/token 발급, Gateway jwt validator |
| browser config 변경 | Runner AgentJobCoordinator._build_agent_browser_config |
| DOM extraction 변경 | Runner services/dom 및 learning prompt/parser |
| pool/full/cancel 정책 변경 | Gateway runner handler, Runner AgentJobCoordinator |
운영/사용자 지원 메모
사용자가 인증 오류를 겪으면 token 만료/삭제/agent DB 비활성화/project mismatch를 먼저 확인한다. CLI는 401/403을 받으면 재연결하지 않고 종료하도록 되어 있다.
브라우저 설치 실패는 Playwright browser 또는 Linux system dependency 문제일 가능성이 높다. nova-agent install-deps와 python -m playwright install chromium을 확인한다.
Local Agent는 사용자의 로컬 네트워크와 브라우저 상태에 영향을 받는다. Cloud Runner에서 성공하는 시나리오가 Local Agent에서 실패하면 viewport, cookie/storage_state, test access key header, popup/tab 전환, 브라우저 권한을 우선 비교한다.
Project details
Release history Release notifications | RSS feed
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distribution
Built Distribution
Filter files by name, interpreter, ABI, and platform.
If you're not sure about the file name format, learn more about wheel file names.
Copy a direct link to the current filters
File details
Details for the file qanova_agent-0.3.10.tar.gz.
File metadata
- Download URL: qanova_agent-0.3.10.tar.gz
- Upload date:
- Size: 81.7 kB
- Tags: Source
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.12.13
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
74205af55b6b38409485d3b39a58b0ec06fa195d3106edf3ed1f206ed2da6b51
|
|
| MD5 |
647e09a18b634bc9e7a7d9958dd8b941
|
|
| BLAKE2b-256 |
6e3961b4003802043755affbcbe38c339c55f3fb3329e493bd8d5e8a98dffc74
|
File details
Details for the file qanova_agent-0.3.10-py3-none-any.whl.
File metadata
- Download URL: qanova_agent-0.3.10-py3-none-any.whl
- Upload date:
- Size: 75.9 kB
- Tags: Python 3
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.12.13
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
e07eeaeff7d47eaaf210c4c2c5ab5fe1de731d4abef0b9c35067111fd8323c50
|
|
| MD5 |
3606f9f5aa190abc33f538e0c8cfaf31
|
|
| BLAKE2b-256 |
5bb96d7cabb781dd6537341d48e62e74b8d139a8ab7a9e06553a669f716327cc
|