@tangle-network/browser-agent-driver 0.23.0 → 0.24.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +357 -126
- package/dist/brain/index.d.ts +6 -0
- package/dist/brain/index.d.ts.map +1 -1
- package/dist/brain/index.js +43 -12
- package/dist/brain/index.js.map +1 -1
- package/dist/memory/knowledge.d.ts +6 -0
- package/dist/memory/knowledge.d.ts.map +1 -1
- package/dist/memory/knowledge.js +15 -0
- package/dist/memory/knowledge.js.map +1 -1
- package/dist/run-state.d.ts +4 -0
- package/dist/run-state.d.ts.map +1 -1
- package/dist/run-state.js +2 -0
- package/dist/run-state.js.map +1 -1
- package/dist/runner/goal-decomposer.d.ts +38 -0
- package/dist/runner/goal-decomposer.d.ts.map +1 -0
- package/dist/runner/goal-decomposer.js +125 -0
- package/dist/runner/goal-decomposer.js.map +1 -0
- package/dist/runner/parallel-runner.d.ts +61 -0
- package/dist/runner/parallel-runner.d.ts.map +1 -0
- package/dist/runner/parallel-runner.js +133 -0
- package/dist/runner/parallel-runner.js.map +1 -0
- package/dist/runner/pattern-extractor.d.ts +40 -0
- package/dist/runner/pattern-extractor.d.ts.map +1 -0
- package/dist/runner/pattern-extractor.js +122 -0
- package/dist/runner/pattern-extractor.js.map +1 -0
- package/dist/runner/runner.d.ts.map +1 -1
- package/dist/runner/runner.js +109 -6
- package/dist/runner/runner.js.map +1 -1
- package/dist/types.d.ts +32 -0
- package/dist/types.d.ts.map +1 -1
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -1,18 +1,40 @@
|
|
|
1
1
|
# @tangle-network/browser-agent-driver
|
|
2
2
|
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
3
|
+
General-purpose agentic browser automation. Completes real user outcomes on any website — search, extract, fill forms, compare prices, navigate complex UIs.
|
|
4
|
+
|
|
5
|
+
**91.3% on WebVoyager (590 tasks, 15 sites) at $0.09/task.** 100% on held-out competitive bench. 95.7% on WebbBench-50 (excl. DataDome sites). Default model: `gpt-5.4`.
|
|
6
|
+
|
|
7
|
+
## Table of Contents
|
|
8
|
+
|
|
9
|
+
- [Install](#install)
|
|
10
|
+
- [Quick Start](#quick-start)
|
|
11
|
+
- [How It Works](#how-it-works)
|
|
12
|
+
- [Features](#features)
|
|
13
|
+
- [Vision + DOM Hybrid](#vision--dom-hybrid)
|
|
14
|
+
- [Stealth & Anti-Bot](#stealth--anti-bot)
|
|
15
|
+
- [CAPTCHA Solving](#captcha-solving)
|
|
16
|
+
- [Parallel Tab Execution](#parallel-tab-execution)
|
|
17
|
+
- [Multi-Model Orchestration](#multi-model-orchestration)
|
|
18
|
+
- [Design Audit](#design-audit)
|
|
19
|
+
- [Wallet & DeFi Testing](#wallet--defi-testing)
|
|
20
|
+
- [Configuration](#configuration)
|
|
21
|
+
- [CLI Reference](#cli-reference)
|
|
22
|
+
- [SDK / Library Usage](#sdk--library-usage)
|
|
23
|
+
- [Test Suites](#test-suites)
|
|
24
|
+
- [Drivers](#drivers)
|
|
25
|
+
- [Benchmarks](#benchmarks)
|
|
26
|
+
- [GitHub Action](#github-action)
|
|
27
|
+
- [Development](#development)
|
|
6
28
|
|
|
7
29
|
## Install
|
|
8
30
|
|
|
9
|
-
### CLI
|
|
31
|
+
### CLI (recommended)
|
|
10
32
|
|
|
11
33
|
```bash
|
|
12
34
|
curl -fsSL https://raw.githubusercontent.com/tangle-network/browser-agent-driver/main/scripts/install.sh | sh
|
|
13
35
|
```
|
|
14
36
|
|
|
15
|
-
Installs the `bad` command
|
|
37
|
+
Installs the `bad` command, downloads Chromium, adds PATH. Requires Node.js 20+.
|
|
16
38
|
|
|
17
39
|
Or via npm:
|
|
18
40
|
|
|
@@ -30,167 +52,389 @@ pnpm add -D playwright
|
|
|
30
52
|
|
|
31
53
|
## Quick Start
|
|
32
54
|
|
|
33
|
-
###
|
|
55
|
+
### CLI
|
|
56
|
+
|
|
57
|
+
```bash
|
|
58
|
+
# Run a task
|
|
59
|
+
bad run --goal "Find the cheapest flight from NYC to London on Jan 15" \
|
|
60
|
+
--url https://www.google.com/travel/flights
|
|
61
|
+
|
|
62
|
+
# With vision (screenshot-based decisions)
|
|
63
|
+
bad run --goal "Compare MacBook Air prices" --url https://apple.com \
|
|
64
|
+
--observation-mode hybrid
|
|
65
|
+
|
|
66
|
+
# Test suite from case file
|
|
67
|
+
bad run --cases ./my-tests.json --concurrency 4
|
|
68
|
+
|
|
69
|
+
# Authenticated session
|
|
70
|
+
bad run --goal "Check account settings" --url https://app.example.com \
|
|
71
|
+
--storage-state .auth/session.json
|
|
72
|
+
|
|
73
|
+
# With proxy (residential or SOCKS5)
|
|
74
|
+
bad run --goal "Search hotels in Tokyo" --url https://booking.com \
|
|
75
|
+
--proxy http://user:pass@proxy.example.com:port
|
|
76
|
+
```
|
|
77
|
+
|
|
78
|
+
### SDK
|
|
34
79
|
|
|
35
80
|
```typescript
|
|
36
81
|
import { chromium } from 'playwright'
|
|
37
82
|
import { PlaywrightDriver, BrowserAgent } from '@tangle-network/browser-agent-driver'
|
|
38
83
|
|
|
39
|
-
const browser = await chromium.launch()
|
|
84
|
+
const browser = await chromium.launch({ channel: 'chrome' })
|
|
40
85
|
const page = await browser.newPage()
|
|
41
86
|
const driver = new PlaywrightDriver(page)
|
|
42
87
|
|
|
43
|
-
const
|
|
88
|
+
const agent = new BrowserAgent({
|
|
44
89
|
driver,
|
|
45
|
-
config: {
|
|
90
|
+
config: {
|
|
91
|
+
model: 'gpt-5.4',
|
|
92
|
+
observationMode: 'hybrid', // vision + DOM
|
|
93
|
+
plannerEnabled: true, // plan-then-execute
|
|
94
|
+
},
|
|
46
95
|
})
|
|
47
96
|
|
|
48
|
-
const result = await
|
|
49
|
-
goal: '
|
|
50
|
-
startUrl: 'https://
|
|
51
|
-
maxTurns: 30,
|
|
97
|
+
const result = await agent.run({
|
|
98
|
+
goal: 'Find the top 3 trending repositories on GitHub',
|
|
99
|
+
startUrl: 'https://github.com/trending',
|
|
52
100
|
})
|
|
53
101
|
|
|
54
|
-
console.log(result.success,
|
|
102
|
+
console.log(result.success, result.reason)
|
|
55
103
|
await browser.close()
|
|
56
104
|
```
|
|
57
105
|
|
|
58
|
-
###
|
|
59
|
-
|
|
60
|
-
```bash
|
|
61
|
-
# single task
|
|
62
|
-
bad run --goal "Sign up for account" --url http://localhost:3000
|
|
63
|
-
|
|
64
|
-
# test suite from case file
|
|
65
|
-
bad run --cases ./cases.json
|
|
66
|
-
|
|
67
|
-
# authenticated session
|
|
68
|
-
bad run --goal "Open settings" --url https://app.example.com \
|
|
69
|
-
--storage-state ./.auth/session.json
|
|
70
|
-
|
|
71
|
-
# speed-optimized mode
|
|
72
|
-
bad run --cases ./cases.json --mode fast-explore
|
|
73
|
-
|
|
74
|
-
# evidence-rich mode for signoff
|
|
75
|
-
bad run --cases ./cases.json --mode full-evidence
|
|
76
|
-
```
|
|
77
|
-
|
|
78
|
-
## Config File
|
|
106
|
+
### Config File
|
|
79
107
|
|
|
80
|
-
Create `
|
|
108
|
+
Create `bad.config.ts` (or `.js`, `.mjs`) in your project root:
|
|
81
109
|
|
|
82
110
|
```typescript
|
|
83
111
|
import { defineConfig } from '@tangle-network/browser-agent-driver'
|
|
84
112
|
|
|
85
113
|
export default defineConfig({
|
|
114
|
+
provider: 'openai',
|
|
86
115
|
model: 'gpt-5.4',
|
|
116
|
+
observationMode: 'hybrid',
|
|
117
|
+
plannerEnabled: true,
|
|
87
118
|
headless: true,
|
|
88
119
|
concurrency: 4,
|
|
89
120
|
maxTurns: 30,
|
|
90
|
-
timeoutMs: 300_000,
|
|
91
121
|
outputDir: './test-results',
|
|
92
|
-
|
|
122
|
+
|
|
123
|
+
// Per-role model routing (Gen 28)
|
|
124
|
+
models: {
|
|
125
|
+
planner: { model: 'claude-opus-4-6', provider: 'anthropic' },
|
|
126
|
+
executor: { model: 'gpt-4.1-mini' },
|
|
127
|
+
verifier: { model: 'gpt-4.1-mini' },
|
|
128
|
+
supervisor: { model: 'gpt-5.4' },
|
|
129
|
+
},
|
|
130
|
+
|
|
131
|
+
// Parallel tabs for compound goals (Gen 21)
|
|
132
|
+
parallelTabs: { enabled: true, maxTabs: 3 },
|
|
133
|
+
|
|
134
|
+
// Proxy for anti-bot bypass
|
|
135
|
+
proxy: 'http://user:pass@proxy:port', // or set BAD_PROXY_URL env
|
|
136
|
+
|
|
137
|
+
// Supervisor for stuck detection
|
|
138
|
+
supervisor: { enabled: true, useVision: true },
|
|
93
139
|
})
|
|
94
140
|
```
|
|
95
141
|
|
|
96
|
-
Auto-detected by CLI and
|
|
142
|
+
Auto-detected by CLI and SDK. CLI flags override config values.
|
|
97
143
|
|
|
98
|
-
##
|
|
144
|
+
## How It Works
|
|
145
|
+
|
|
146
|
+
```
|
|
147
|
+
Goal → DOM Planner (1 LLM call with screenshot)
|
|
148
|
+
→ N deterministic steps (click, type, fill, navigate)
|
|
149
|
+
→ If deviation: vision per-action loop
|
|
150
|
+
→ Observe (a11y tree + screenshot + SoM labels)
|
|
151
|
+
→ LLM decides action (ref-based, coordinate, or label)
|
|
152
|
+
→ Execute + verify expected effect
|
|
153
|
+
→ Recovery on failure (strategy shift, form reset retry, search fallback)
|
|
154
|
+
→ Goal verification (LLM or fast-path with script evidence)
|
|
155
|
+
→ Complete with structured result
|
|
156
|
+
```
|
|
157
|
+
|
|
158
|
+
Recovery is automatic: cookie consent, modal blockers, A-B-A-B oscillation loops, form field resets, date picker stalls, and CAPTCHA challenges are handled before the agent continues.
|
|
159
|
+
|
|
160
|
+
## Features
|
|
161
|
+
|
|
162
|
+
### Vision + DOM Hybrid
|
|
163
|
+
|
|
164
|
+
The agent sees BOTH a screenshot and the accessibility tree. Screenshots show visual layout, SoM labels mark interactive elements with numbered badges, and the a11y tree provides precise `@ref` IDs for targeting.
|
|
165
|
+
|
|
166
|
+
Three observation modes:
|
|
167
|
+
- **`dom`** — a11y tree only (fastest, cheapest)
|
|
168
|
+
- **`vision`** — screenshot + coordinates only
|
|
169
|
+
- **`hybrid`** — both (default for benchmarks, most reliable)
|
|
170
|
+
|
|
171
|
+
### Stealth & Anti-Bot
|
|
172
|
+
|
|
173
|
+
Built-in evasion for Cloudflare, Akamai, and most WAF systems:
|
|
174
|
+
|
|
175
|
+
- **System Chrome** (`channel: 'chrome'`) — real TLS/JA3/HTTP2 fingerprint, not bundled Chromium
|
|
176
|
+
- **Patchright** — Playwright fork that patches CDP protocol leaks
|
|
177
|
+
- **Mouse humanization** — Bezier curve movement (8-15 points), gaussian click offset
|
|
178
|
+
- **Browser fingerprint** — navigator.webdriver, plugins, languages, WebGL, canvas noise, screenX/Y fix
|
|
179
|
+
- **GPU rendering** — `--use-gl=desktop` for real WebGL fingerprint
|
|
180
|
+
- **Resource blocking** — 99+ analytics/tracking domains blocked
|
|
181
|
+
|
|
182
|
+
Unblocks 9/13 previously-blocked sites on WebbBench-50 with zero configuration.
|
|
183
|
+
|
|
184
|
+
### CAPTCHA Solving
|
|
185
|
+
|
|
186
|
+
Automatic CAPTCHA detection and solving during runs:
|
|
187
|
+
|
|
188
|
+
- **reCAPTCHA v2** — checkbox click + image grid solver (LLM vision-based)
|
|
189
|
+
- **Cloudflare Turnstile** — checkbox behavioral click
|
|
190
|
+
- **Google "unusual traffic"** — detected and solver attempted
|
|
99
191
|
|
|
100
192
|
```typescript
|
|
101
|
-
|
|
193
|
+
// Enabled by default. To configure:
|
|
194
|
+
{ captcha: { enabled: true, maxAttempts: 5 } }
|
|
195
|
+
```
|
|
102
196
|
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
{ type: 'element-visible', selector: '[data-testid="user-menu"]' },
|
|
112
|
-
],
|
|
113
|
-
},
|
|
114
|
-
])
|
|
197
|
+
### Parallel Tab Execution
|
|
198
|
+
|
|
199
|
+
For compound goals ("compare X vs Y", "find 5 items matching criteria"), the agent decomposes the goal and runs sub-tasks in parallel browser tabs.
|
|
200
|
+
|
|
201
|
+
```typescript
|
|
202
|
+
{
|
|
203
|
+
parallelTabs: { enabled: true, maxTabs: 3 },
|
|
204
|
+
}
|
|
115
205
|
```
|
|
116
206
|
|
|
117
|
-
|
|
207
|
+
The GoalDecomposer (1 cheap LLM call) classifies goals as simple or compound. Simple goals run as before. Compound goals get split into sub-goals, each running in its own tab via `Promise.all`, with results merged by the EvidenceMerger.
|
|
118
208
|
|
|
119
|
-
|
|
209
|
+
### Multi-Model Orchestration
|
|
120
210
|
|
|
121
|
-
|
|
211
|
+
Different agent roles can use different models for optimal cost/quality:
|
|
122
212
|
|
|
123
|
-
|
|
213
|
+
```typescript
|
|
214
|
+
{
|
|
215
|
+
models: {
|
|
216
|
+
planner: { model: 'claude-opus-4-6', provider: 'anthropic' }, // best reasoning
|
|
217
|
+
executor: { model: 'gpt-4.1-mini' }, // cheap, follows plans
|
|
218
|
+
verifier: { model: 'gpt-4.1-mini' }, // structured yes/no
|
|
219
|
+
supervisor: { model: 'gpt-5.4' }, // strategic recovery
|
|
220
|
+
},
|
|
221
|
+
}
|
|
222
|
+
```
|
|
124
223
|
|
|
125
|
-
|
|
224
|
+
Each role falls back to the main `model` when not configured. The planner needs top-tier reasoning; the executor just follows instructions.
|
|
126
225
|
|
|
127
|
-
|
|
226
|
+
### Design Audit
|
|
128
227
|
|
|
129
|
-
|
|
228
|
+
Vision-powered design quality analysis with closed-loop improvement:
|
|
130
229
|
|
|
131
230
|
```bash
|
|
132
|
-
# Audit any URL
|
|
231
|
+
# Audit any URL
|
|
133
232
|
bad design-audit --url https://your-app.com
|
|
134
233
|
|
|
135
234
|
# Multi-page crawl with cross-page systemic detection
|
|
136
235
|
bad design-audit --url https://your-app.com --pages 10
|
|
137
236
|
|
|
138
|
-
#
|
|
139
|
-
bad design-audit --url http://localhost:3000
|
|
140
|
-
|
|
141
|
-
|
|
237
|
+
# Auto-fix: dispatch findings to a coding agent
|
|
238
|
+
bad design-audit --url http://localhost:3000 --evolve claude-code --project-dir ~/my-app
|
|
239
|
+
```
|
|
240
|
+
|
|
241
|
+
Reports rank **Top Fixes by ROI** — the highest-leverage changes scored by `(impact * blast / effort)`. Multi-page systemic findings collapse automatically.
|
|
142
242
|
|
|
143
|
-
|
|
144
|
-
bad design-audit --url http://localhost:3000 --evolve "aider --message"
|
|
243
|
+
### Wallet & DeFi Testing
|
|
145
244
|
|
|
146
|
-
|
|
147
|
-
|
|
245
|
+
Built-in MetaMask integration for DeFi app testing:
|
|
246
|
+
|
|
247
|
+
```bash
|
|
248
|
+
pnpm wallet:setup # download MetaMask
|
|
249
|
+
pnpm wallet:onboard # automate first-run wizard
|
|
250
|
+
pnpm wallet:anvil # start Anvil mainnet fork (100 ETH + 10 WETH + 10k USDC)
|
|
251
|
+
pnpm wallet:validate # run wallet test suite
|
|
148
252
|
```
|
|
149
253
|
|
|
150
|
-
|
|
254
|
+
Supports connect, swap, supply workflows across Uniswap, Aave, SushiSwap, 1inch.
|
|
151
255
|
|
|
152
|
-
|
|
256
|
+
## Configuration
|
|
153
257
|
|
|
154
|
-
|
|
258
|
+
| Option | Type | Default | Description |
|
|
259
|
+
|--------|------|---------|-------------|
|
|
260
|
+
| `provider` | string | `'openai'` | LLM provider |
|
|
261
|
+
| `model` | string | `'gpt-5.4'` | LLM model |
|
|
262
|
+
| `observationMode` | string | `'dom'` | `'dom'`, `'vision'`, or `'hybrid'` |
|
|
263
|
+
| `plannerEnabled` | boolean | `false` | Plan-then-execute mode |
|
|
264
|
+
| `headless` | boolean | `true` | Run browser headless |
|
|
265
|
+
| `maxTurns` | number | `30` | Max turns per task |
|
|
266
|
+
| `proxy` | string | — | Proxy URL (also `BAD_PROXY_URL` env) |
|
|
267
|
+
| `models` | object | — | Per-role model overrides |
|
|
268
|
+
| `parallelTabs` | object | — | `{ enabled, maxTabs }` |
|
|
269
|
+
| `supervisor` | object | — | `{ enabled, useVision, model }` |
|
|
270
|
+
| `captcha` | object | — | `{ enabled, maxAttempts }` |
|
|
271
|
+
| `goalVerification` | boolean | `true` | Verify goal before accepting |
|
|
272
|
+
| `vision` | boolean | `true` | Send screenshots to LLM |
|
|
273
|
+
| `concurrency` | number | `1` | Parallel test cases |
|
|
274
|
+
|
|
275
|
+
See [Configuration Reference](./docs/guides/configuration.md) for all options.
|
|
155
276
|
|
|
156
|
-
|
|
277
|
+
## CLI Reference
|
|
157
278
|
|
|
158
279
|
```bash
|
|
159
|
-
bad
|
|
280
|
+
bad run [options] # Run tasks
|
|
281
|
+
bad design-audit [options] # Design quality analysis
|
|
282
|
+
bad view <run-dir> # Open session viewer
|
|
283
|
+
bad competitive [options] # Head-to-head framework comparison
|
|
160
284
|
```
|
|
161
285
|
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
|
|
165
|
-
|
|
166
|
-
|
|
286
|
+
### Run options
|
|
287
|
+
|
|
288
|
+
| Flag | Description |
|
|
289
|
+
|------|-------------|
|
|
290
|
+
| `--goal "..."` | Natural language goal |
|
|
291
|
+
| `--url URL` | Starting URL |
|
|
292
|
+
| `--cases file.json` | Test case file |
|
|
293
|
+
| `--mode fast-explore\|full-evidence` | Run mode |
|
|
294
|
+
| `--model MODEL` | LLM model |
|
|
295
|
+
| `--provider openai\|anthropic\|google` | LLM provider |
|
|
296
|
+
| `--observation-mode dom\|vision\|hybrid` | Observation mode |
|
|
297
|
+
| `--headless` | Run headless (default) |
|
|
298
|
+
| `--proxy URL` | Residential/SOCKS5/HTTP proxy |
|
|
299
|
+
| `--profile default\|stealth\|benchmark-webvoyager` | Launch profile |
|
|
300
|
+
| `--concurrency N` | Parallel cases |
|
|
301
|
+
| `--show-cursor` | Animated cursor overlay in screenshots |
|
|
302
|
+
| `--live` | Real-time SSE viewer |
|
|
303
|
+
|
|
304
|
+
## SDK / Library Usage
|
|
305
|
+
|
|
306
|
+
```typescript
|
|
307
|
+
import {
|
|
308
|
+
// Core
|
|
309
|
+
BrowserAgent,
|
|
310
|
+
PlaywrightDriver,
|
|
311
|
+
SteelDriver,
|
|
312
|
+
TestRunner,
|
|
313
|
+
|
|
314
|
+
// Config
|
|
315
|
+
defineConfig,
|
|
316
|
+
|
|
317
|
+
// Types
|
|
318
|
+
type AgentConfig,
|
|
319
|
+
type Scenario,
|
|
320
|
+
type AgentResult,
|
|
321
|
+
type Turn,
|
|
322
|
+
|
|
323
|
+
// Multi-actor (parallel users)
|
|
324
|
+
MultiActorSession,
|
|
325
|
+
|
|
326
|
+
// Design audit
|
|
327
|
+
runDesignAudit,
|
|
328
|
+
|
|
329
|
+
// CAPTCHA
|
|
330
|
+
detectCaptcha,
|
|
331
|
+
solveCaptcha,
|
|
332
|
+
} from '@tangle-network/browser-agent-driver'
|
|
333
|
+
```
|
|
334
|
+
|
|
335
|
+
### Multi-Actor Sessions
|
|
336
|
+
|
|
337
|
+
```typescript
|
|
338
|
+
import { MultiActorSession } from '@tangle-network/browser-agent-driver'
|
|
339
|
+
|
|
340
|
+
const session = await MultiActorSession.create(browser, {
|
|
341
|
+
actors: {
|
|
342
|
+
admin: { storageState: '.auth/admin.json' },
|
|
343
|
+
user: {},
|
|
344
|
+
},
|
|
345
|
+
agentConfig: { model: 'gpt-5.4', observationMode: 'hybrid' },
|
|
346
|
+
})
|
|
347
|
+
|
|
348
|
+
// Sequential
|
|
349
|
+
await session.actor('admin').run({ goal: 'Create project', startUrl: '/admin' })
|
|
167
350
|
|
|
168
|
-
|
|
351
|
+
// Parallel
|
|
352
|
+
await session.parallel(
|
|
353
|
+
['admin', { goal: 'Monitor dashboard', startUrl: '/admin' }],
|
|
354
|
+
['user', { goal: 'Submit form', startUrl: '/app' }],
|
|
355
|
+
)
|
|
169
356
|
|
|
170
|
-
|
|
357
|
+
await session.close()
|
|
358
|
+
```
|
|
171
359
|
|
|
172
|
-
|
|
360
|
+
## Test Suites
|
|
173
361
|
|
|
174
362
|
```typescript
|
|
175
|
-
import {
|
|
363
|
+
import { TestRunner } from '@tangle-network/browser-agent-driver'
|
|
364
|
+
|
|
365
|
+
const runner = new TestRunner({
|
|
366
|
+
driver,
|
|
367
|
+
config: { model: 'gpt-5.4', observationMode: 'hybrid' },
|
|
368
|
+
concurrency: 4,
|
|
369
|
+
})
|
|
176
370
|
|
|
177
|
-
|
|
371
|
+
const results = await runner.runSuite([
|
|
372
|
+
{
|
|
373
|
+
id: 'login',
|
|
374
|
+
goal: 'Log in with test@example.com / password123',
|
|
375
|
+
startUrl: 'https://app.example.com/login',
|
|
376
|
+
},
|
|
377
|
+
{
|
|
378
|
+
id: 'create-project',
|
|
379
|
+
goal: 'Create a new project called "Test Project"',
|
|
380
|
+
startUrl: 'https://app.example.com/projects',
|
|
381
|
+
},
|
|
382
|
+
])
|
|
383
|
+
```
|
|
178
384
|
|
|
179
|
-
|
|
385
|
+
## Drivers
|
|
386
|
+
|
|
387
|
+
The agent loop is decoupled from the browser via the `Driver` interface:
|
|
388
|
+
|
|
389
|
+
```typescript
|
|
390
|
+
// Local Playwright (default)
|
|
391
|
+
const driver = new PlaywrightDriver(page)
|
|
392
|
+
|
|
393
|
+
// Steel cloud browser (anti-bot, residential proxies, CAPTCHA)
|
|
180
394
|
const driver = await SteelDriver.create({
|
|
181
395
|
apiKey: process.env.STEEL_API_KEY,
|
|
182
396
|
sessionOptions: { useProxy: true, solveCaptcha: true },
|
|
183
397
|
})
|
|
184
|
-
|
|
185
|
-
|
|
186
|
-
|
|
398
|
+
|
|
399
|
+
// Any Driver implementation works
|
|
400
|
+
const agent = new BrowserAgent({ driver, config })
|
|
187
401
|
```
|
|
188
402
|
|
|
189
|
-
|
|
403
|
+
## Benchmarks
|
|
190
404
|
|
|
191
|
-
|
|
405
|
+
| Benchmark | Score | Cost | Notes |
|
|
406
|
+
|-----------|-------|------|-------|
|
|
407
|
+
| **WebVoyager** (590 tasks, 15 sites) | 91.3% | $0.09/task | Full run, Gen 25 |
|
|
408
|
+
| **Competitive** (10 real-web sites) | 100% | $0.03/task | Held-out, never optimized |
|
|
409
|
+
| **WebbBench-50** (50 diverse sites) | 88% raw, 95.7% excl. DataDome | — | Held-out generalization |
|
|
410
|
+
|
|
411
|
+
### Competitive position
|
|
192
412
|
|
|
193
|
-
|
|
413
|
+
| Agent | WebVoyager | Cost/task |
|
|
414
|
+
|-------|-----------|-----------|
|
|
415
|
+
| Surfer-2 | 97.1% | $1-5 |
|
|
416
|
+
| Magnitude | 93.9% | ~$0.10 |
|
|
417
|
+
| **bad** | **91.3%** | **$0.09** |
|
|
418
|
+
| OpenAI Operator | 87% | ChatGPT Pro |
|
|
419
|
+
|
|
420
|
+
### Running benchmarks
|
|
421
|
+
|
|
422
|
+
```bash
|
|
423
|
+
# WebVoyager full 590
|
|
424
|
+
node scripts/run-scenario-track.mjs \
|
|
425
|
+
--cases bench/external/webvoyager/cases.json \
|
|
426
|
+
--config bench/scenarios/configs/vision-hybrid.mjs \
|
|
427
|
+
--model gpt-5.4 --modes fast-explore --concurrency 5 \
|
|
428
|
+
--out agent-results/webvoyager-full
|
|
429
|
+
|
|
430
|
+
# Multi-rep validation (≥3 reps required for any claim)
|
|
431
|
+
node scripts/run-multi-rep.mjs \
|
|
432
|
+
--cases bench/scenarios/cases/my-cases.json \
|
|
433
|
+
--config bench/scenarios/configs/vision-hybrid.mjs \
|
|
434
|
+
--reps 3 --out agent-results/my-validation
|
|
435
|
+
```
|
|
436
|
+
|
|
437
|
+
## GitHub Action
|
|
194
438
|
|
|
195
439
|
```yaml
|
|
196
440
|
- uses: tangle-network/browser-agent-driver/.github/actions/design-audit@main
|
|
@@ -198,57 +442,44 @@ Drop bad design-audit into any PR pipeline:
|
|
|
198
442
|
url: ${{ steps.deploy.outputs.preview_url }}
|
|
199
443
|
pages: 5
|
|
200
444
|
fail-on-score-below: '6.5'
|
|
201
|
-
evolve: claude-code
|
|
445
|
+
evolve: claude-code
|
|
202
446
|
openai-api-key: ${{ secrets.OPENAI_API_KEY }}
|
|
203
447
|
```
|
|
204
448
|
|
|
205
|
-
|
|
449
|
+
Posts Top Fixes as a PR comment, uploads full report as artifact, optionally fails on score regressions.
|
|
206
450
|
|
|
207
|
-
##
|
|
208
|
-
|
|
209
|
-
- [Configuration Reference](./docs/guides/configuration.md) — all config options
|
|
210
|
-
- [CLI Reference](./docs/guides/cli.md) — commands, modes, profiles, auth
|
|
211
|
-
- [Design Audit](./docs/guides/design-audit.md) — vision-powered design quality + ROI-ranked closed-loop improvement
|
|
212
|
-
- [Memory System](./docs/guides/memory.md) — trajectory store, app knowledge, selector cache
|
|
213
|
-
- [Benchmarks & Experiments](./docs/guides/benchmarks.md) — tiered gates, AB specs, research cycles
|
|
214
|
-
- [Wallet & EVM Apps](./docs/guides/wallet.md) — MetaMask, DeFi testing, RPC interception, Anvil forks
|
|
215
|
-
- [Providers](./docs/guides/providers.md) — OpenAI, Anthropic, Codex CLI, Claude Code, sandbox backend
|
|
216
|
-
- [Reporters & Sinks](./docs/guides/reporters.md) — JUnit, HTML, webhooks, custom sinks
|
|
217
|
-
- [Custom Drivers](./docs/guides/custom-drivers.md) — implement the `Driver` interface
|
|
218
|
-
|
|
219
|
-
## Research
|
|
220
|
-
|
|
221
|
-
- [Operating Roadmap](./docs/roadmap/browser-agent-ops.md)
|
|
222
|
-
- [Competitive Analysis](./docs/research/competitor-analysis-2026-03.md)
|
|
223
|
-
- [Reliability Runbook](./RELIABILITY.md)
|
|
224
|
-
|
|
225
|
-
## Skills
|
|
226
|
-
|
|
227
|
-
Ships Codex skills under `skills/` for test execution discipline and agent-friendly UX conventions.
|
|
451
|
+
## Session Viewer
|
|
228
452
|
|
|
229
453
|
```bash
|
|
230
|
-
|
|
454
|
+
bad view audit-results/stripe.com-1775502457141
|
|
231
455
|
```
|
|
232
456
|
|
|
233
|
-
|
|
234
|
-
|
|
235
|
-
Versioning and releases are automated via [Changesets](https://github.com/changesets/changesets).
|
|
457
|
+
Web UI with per-turn screenshots, action JSON, reasoning, element highlights. Pair with `--show-cursor` for animated cursor recordings.
|
|
236
458
|
|
|
237
|
-
|
|
238
|
-
|
|
239
|
-
**Maintainers:** when PRs with changesets merge to `main`, the [changesets workflow](./.github/workflows/changesets.yml) automatically opens (or updates) a "Release: version packages" PR that bumps `package.json` and writes `CHANGELOG.md`. Merging that PR pushes a `browser-agent-driver-vX.Y.Z` git tag, which fires the existing [`release.yml`](./.github/workflows/release.yml) and [`publish-npm.yml`](./.github/workflows/publish-npm.yml) workflows that create the GitHub release tarball and publish to npm with provenance.
|
|
459
|
+
## Guides
|
|
240
460
|
|
|
241
|
-
|
|
461
|
+
- [Configuration Reference](./docs/guides/configuration.md)
|
|
462
|
+
- [CLI Reference](./docs/guides/cli.md)
|
|
463
|
+
- [Design Audit](./docs/guides/design-audit.md)
|
|
464
|
+
- [Memory System](./docs/guides/memory.md)
|
|
465
|
+
- [Benchmarks & Experiments](./docs/guides/benchmarks.md)
|
|
466
|
+
- [Wallet & EVM Apps](./docs/guides/wallet.md)
|
|
467
|
+
- [Providers](./docs/guides/providers.md)
|
|
468
|
+
- [Custom Drivers](./docs/guides/custom-drivers.md)
|
|
242
469
|
|
|
243
470
|
## Development
|
|
244
471
|
|
|
245
472
|
```bash
|
|
246
|
-
pnpm build
|
|
247
|
-
pnpm test
|
|
248
|
-
pnpm lint
|
|
249
|
-
pnpm check:boundaries
|
|
473
|
+
pnpm build # TypeScript → dist/
|
|
474
|
+
pnpm test # 993 tests
|
|
475
|
+
pnpm lint # type-check
|
|
476
|
+
pnpm check:boundaries # architecture boundaries
|
|
250
477
|
```
|
|
251
478
|
|
|
479
|
+
## Publishing
|
|
480
|
+
|
|
481
|
+
Automated via [Changesets](https://github.com/changesets/changesets) + OIDC trusted publishing. Add a changeset with `pnpm changeset`, merge the auto-generated release PR, and npm publish fires automatically with provenance attestation.
|
|
482
|
+
|
|
252
483
|
## License
|
|
253
484
|
|
|
254
485
|
Dual-licensed under MIT and Apache 2.0. See [LICENSE](./LICENSE).
|
package/dist/brain/index.d.ts
CHANGED
|
@@ -67,6 +67,12 @@ export declare class Brain {
|
|
|
67
67
|
private scoutModelName?;
|
|
68
68
|
private scoutProvider?;
|
|
69
69
|
private scoutUseVision;
|
|
70
|
+
private plannerModel?;
|
|
71
|
+
private plannerProvider?;
|
|
72
|
+
private verifierModel?;
|
|
73
|
+
private verifierProvider?;
|
|
74
|
+
private supervisorModel?;
|
|
75
|
+
private supervisorProvider?;
|
|
70
76
|
private sandboxBackendType?;
|
|
71
77
|
private sandboxBackendProfile?;
|
|
72
78
|
private sandboxBackendProvider?;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/brain/index.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAGH,OAAO,KAAK,EAAE,YAAY,EAAE,aAAa,EAAsB,MAAM,IAAI,CAAC;AAC1E,OAAO,KAAK,EAAE,MAAM,EAAE,SAAS,EAAE,WAAW,EAAE,aAAa,EAAE,gBAAgB,EAAE,IAAI,EAAY,MAAM,aAAa,CAAC;AAuXnH,MAAM,WAAW,aAAa;IAC5B,MAAM,EAAE,MAAM,CAAC;IACf,WAAW,CAAC,EAAE,MAAM,EAAE,CAAC;IACvB,GAAG,EAAE,MAAM,CAAC;IACZ,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,IAAI,CAAC,EAAE,MAAM,EAAE,CAAC;IAChB,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,cAAc,CAAC,EAAE,MAAM,CAAC;IACxB,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,YAAY,CAAC,EAAE,MAAM,CAAC;IACtB;;;;;OAKG;IACH,oBAAoB,CAAC,EAAE,MAAM,CAAC;IAC9B,6EAA6E;IAC7E,wBAAwB,CAAC,EAAE,MAAM,CAAC;IAClC,kFAAkF;IAClF,SAAS,CAAC,EAAE,MAAM,CAAC;CACpB;AAED,MAAM,WAAW,iBAAiB;IAChC,KAAK,EAAE,MAAM,CAAC;IACd,UAAU,EAAE,MAAM,CAAC;IACnB,SAAS,EAAE,MAAM,EAAE,CAAC;IACpB,MAAM,EAAE,MAAM,EAAE,CAAC;IACjB,WAAW,EAAE,MAAM,EAAE,CAAC;IACtB,GAAG,EAAE,MAAM,CAAC;IACZ,UAAU,CAAC,EAAE,MAAM,CAAC;CACrB;AAED,MAAM,WAAW,uBAAuB;IACtC,QAAQ,EAAE,MAAM,CAAC;IACjB,SAAS,EAAE,MAAM,CAAC;IAClB,UAAU,EAAE,MAAM,CAAC;IACnB,GAAG,EAAE,MAAM,CAAC;IACZ,UAAU,CAAC,EAAE,MAAM,CAAC;CACrB;AAKD,qBAAa,KAAK;IAChB,OAAO,CAAC,UAAU,CAAoC;IACtD,OAAO,CAAC,QAAQ,CAA0G;IAC1H,OAAO,CAAC,SAAS,CAAS;IAC1B,OAAO,CAAC,oBAAoB,CAAU;IACtC,OAAO,CAAC,YAAY,CAAC,CAAS;IAC9B,OAAO,CAAC,WAAW,CAAC,CAA0G;IAC9H,OAAO,CAAC,cAAc,CAAC,CAAS;IAChC,OAAO,CAAC,OAAO,CAAC,CAAS;IACzB,OAAO,CAAC,KAAK,CAAU;IACvB,OAAO,CAAC,OAAO,CAAsB;IACrC,OAAO,CAAC,eAAe,CAAS;IAChC,OAAO,CAAC,aAAa,CAAU;IAC/B,OAAO,CAAC,cAAc,CAA8B;IACpD,OAAO,CAAC,eAAe,CAA8B;IACrD,OAAO,CAAC,YAAY,CAAS;IAC7B,OAAO,CAAC,gBAAgB,CAAU;IAClC,OAAO,CAAC,eAAe,CAAC,CAAS;IACjC,OAAO,CAAC,YAAY,CAAS;IAC7B,OAAO,CAAC,cAAc,CAAC,CAAS;IAChC,OAAO,CAAC,aAAa,CAAC,CAA0G;IAChI,OAAO,CAAC,cAAc,CAAU;
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/brain/index.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAGH,OAAO,KAAK,EAAE,YAAY,EAAE,aAAa,EAAsB,MAAM,IAAI,CAAC;AAC1E,OAAO,KAAK,EAAE,MAAM,EAAE,SAAS,EAAE,WAAW,EAAE,aAAa,EAAE,gBAAgB,EAAE,IAAI,EAAY,MAAM,aAAa,CAAC;AAuXnH,MAAM,WAAW,aAAa;IAC5B,MAAM,EAAE,MAAM,CAAC;IACf,WAAW,CAAC,EAAE,MAAM,EAAE,CAAC;IACvB,GAAG,EAAE,MAAM,CAAC;IACZ,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,IAAI,CAAC,EAAE,MAAM,EAAE,CAAC;IAChB,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,cAAc,CAAC,EAAE,MAAM,CAAC;IACxB,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,YAAY,CAAC,EAAE,MAAM,CAAC;IACtB;;;;;OAKG;IACH,oBAAoB,CAAC,EAAE,MAAM,CAAC;IAC9B,6EAA6E;IAC7E,wBAAwB,CAAC,EAAE,MAAM,CAAC;IAClC,kFAAkF;IAClF,SAAS,CAAC,EAAE,MAAM,CAAC;CACpB;AAED,MAAM,WAAW,iBAAiB;IAChC,KAAK,EAAE,MAAM,CAAC;IACd,UAAU,EAAE,MAAM,CAAC;IACnB,SAAS,EAAE,MAAM,EAAE,CAAC;IACpB,MAAM,EAAE,MAAM,EAAE,CAAC;IACjB,WAAW,EAAE,MAAM,EAAE,CAAC;IACtB,GAAG,EAAE,MAAM,CAAC;IACZ,UAAU,CAAC,EAAE,MAAM,CAAC;CACrB;AAED,MAAM,WAAW,uBAAuB;IACtC,QAAQ,EAAE,MAAM,CAAC;IACjB,SAAS,EAAE,MAAM,CAAC;IAClB,UAAU,EAAE,MAAM,CAAC;IACnB,GAAG,EAAE,MAAM,CAAC;IACZ,UAAU,CAAC,EAAE,MAAM,CAAC;CACrB;AAKD,qBAAa,KAAK;IAChB,OAAO,CAAC,UAAU,CAAoC;IACtD,OAAO,CAAC,QAAQ,CAA0G;IAC1H,OAAO,CAAC,SAAS,CAAS;IAC1B,OAAO,CAAC,oBAAoB,CAAU;IACtC,OAAO,CAAC,YAAY,CAAC,CAAS;IAC9B,OAAO,CAAC,WAAW,CAAC,CAA0G;IAC9H,OAAO,CAAC,cAAc,CAAC,CAAS;IAChC,OAAO,CAAC,OAAO,CAAC,CAAS;IACzB,OAAO,CAAC,KAAK,CAAU;IACvB,OAAO,CAAC,OAAO,CAAsB;IACrC,OAAO,CAAC,eAAe,CAAS;IAChC,OAAO,CAAC,aAAa,CAAU;IAC/B,OAAO,CAAC,cAAc,CAA8B;IACpD,OAAO,CAAC,eAAe,CAA8B;IACrD,OAAO,CAAC,YAAY,CAAS;IAC7B,OAAO,CAAC,gBAAgB,CAAU;IAClC,OAAO,CAAC,eAAe,CAAC,CAAS;IACjC,OAAO,CAAC,YAAY,CAAS;IAC7B,OAAO,CAAC,cAAc,CAAC,CAAS;IAChC,OAAO,CAAC,aAAa,CAAC,CAA0G;IAChI,OAAO,CAAC,cAAc,CAAU;IAEhC,OAAO,CAAC,YAAY,CAAC,CAAS;IAC9B,OAAO,CAAC,eAAe,CAAC,CAAS;IACjC,OAAO,CAAC,aAAa,CAAC,CAAS;IAC/B,OAAO,CAAC,gBAAgB,CAAC,CAAS;IAClC,OAAO,CAAC,eAAe,CAAC,CAAS;IACjC,OAAO,CAAC,kBAAkB,CAAC,CAAS;IACpC,OAAO,CAAC,kBAAkB,CAAC,CAAS;IACpC,OAAO,CAAC,qBAAqB,CAAC,CAAS;IACvC,OAAO,CAAC,sBAAsB,CAAC,CAAS;IAGxC,OAAO,CAAC,cAAc,CAAC,CAAgF;IACvG,OAAO,CAAC,oBAAoB,CAAC,CAA0C;gBAE3D,MAAM,GAAE,WAAgB;IAsCpC,OAAO,CAAC,gBAAgB;IASxB,OAAO,CAAC,qBAAqB;IAK7B,OAAO,CAAC,iBAAiB;IAoBzB,oGAAoG;IAC9F,gBAAgB,CAAC,SAAS,CAAC,EAAE;QAAE,QAAQ,CAAC,EAAE,QAAQ,GAAG,WAAW,GAAG,QAAQ,CAAC;QAAC,KAAK,CAAC,EAAE,MAAM,CAAA;KAAE,GAAG,OAAO,CAAC,aAAa,CAAC;IAI5H,oEAAoE;YACtD,QAAQ;YAsJR,QAAQ;IA2GtB;;;;;;;;;OASG;IACH,OAAO,CAAC,wBAAwB;IAgBhC;;;;OAIG;IACH,OAAO,CAAC,iBAAiB;IAIzB;;;;;;;;;OASG;IACH,OAAO,CAAC,wBAAwB;IAuChC;;;OAGG;IACH,OAAO,CAAC,gBAAgB;IAiBxB;;;OAGG;IACH,iBAAiB,CACf,YAAY,CAAC,EAAE;QAAE,MAAM,CAAC,EAAE,MAAM,CAAC;QAAC,MAAM,CAAC,EAAE,MAAM,CAAC;QAAC,cAAc,CAAC,EAAE,MAAM,CAAC;QAAC,KAAK,CAAC,EAAE,MAAM,CAAA;KAAE,EAC5F,WAAW,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE;QAAE,UAAU,CAAC,EAAE,MAAM,CAAA;KAAE,CAAC,GACpD,IAAI;IAKP;;;;;;;;;;OAUG;IACH,OAAO,CAAC,oBAAoB;IA0B5B,0DAA0D;IAC1D,KAAK,IAAI,IAAI;IAIb;;;;;;;;;;;;OAYG;IACG,MAAM,IAAI,OAAO,CAAC,IAAI,CAAC;IAwB7B,uCAAuC;IACvC,UAAU,IAAI,YAAY,EAAE;IAI5B,0DAA0D;IAC1D,cAAc,CAAC,QAAQ,EAAE,MAAM,GAAG,IAAI;IAItC;;;OAGG;IACH,OAAO,CAAC,gBAAgB;IAmBxB;;;;;;;OAOG;IACH,OAAO,CAAC,cAAc;IA4EtB,OAAO,CAAC,eAAe;IAgBvB,OAAO,CAAC,oBAAoB;IAkB5B;;OAEG;IACH,OAAO,CAAC,4BAA4B;IAoBpC;;OAEG;IACH,OAAO,CAAC,iBAAiB;IAgBnB,MAAM,CACV,IAAI,EAAE,MAAM,EACZ,KAAK,EAAE,SAAS,EAChB,YAAY,CAAC,EAAE,MAAM,EACrB,QAAQ,CAAC,EAAE;QAAE,OAAO,EAAE,MAAM,CAAC;QAAC,GAAG,EAAE,MAAM,CAAA;KAAE,EAC3C,OAAO,CAAC,EAAE;QAAE,WAAW,CAAC,EAAE,OAAO,CAAA;KAAE,GAClC,OAAO,CAAC,aAAa,CAAC;IA4LzB;;;;;OAKG;YACW,YAAY;IA2I1B;;;;;;;;;;;;;;;;OAgBG;IACG,IAAI,CACR,IAAI,EAAE,MAAM,EACZ,KAAK,EAAE,SAAS,EAChB,OAAO,CAAC,EAAE;QAAE,QAAQ,CAAC,EAAE,MAAM,CAAC;QAAC,YAAY,CAAC,EAAE,MAAM,CAAA;KAAE,GACrD,OAAO,CAAC;QACT,IAAI,EAAE,IAAI,GAAG,IAAI,CAAA;QACjB,GAAG,EAAE,MAAM,CAAA;QACX,UAAU,EAAE,MAAM,CAAA;QAClB,UAAU,CAAC,EAAE,MAAM,CAAA;QACnB,WAAW,CAAC,EAAE,MAAM,CAAA;QACpB,YAAY,CAAC,EAAE,MAAM,CAAA;QACrB,oBAAoB,CAAC,EAAE,MAAM,CAAA;QAC7B,wBAAwB,CAAC,EAAE,MAAM,CAAA;QACjC,UAAU,CAAC,EAAE,MAAM,CAAA;KACpB,CAAC;IAiPF;;;;OAIG;IACG,QAAQ,CAAC,KAAK,EAAE,SAAS,EAAE,IAAI,EAAE,MAAM,GAAG,OAAO,CAAC,iBAAiB,CAAC;IAsDpE,sBAAsB,CAC1B,IAAI,EAAE,MAAM,EACZ,KAAK,EAAE,SAAS,EAChB,UAAU,EAAE,KAAK,CAAC;QAAE,GAAG,EAAE,MAAM,CAAC;QAAC,IAAI,EAAE,MAAM,CAAC;QAAC,KAAK,EAAE,MAAM,CAAA;KAAE,CAAC,EAC/D,YAAY,CAAC,EAAE,MAAM,GACpB,OAAO,CAAC,uBAAuB,CAAC;IAsEnC;;;;OAIG;IACG,oBAAoB,CACxB,KAAK,EAAE,SAAS,EAChB,IAAI,EAAE,MAAM,EACZ,aAAa,EAAE,MAAM,GACpB,OAAO,CAAC,gBAAgB,CAAC;IAkE5B;;;;OAIG;IACG,WAAW,CACf,KAAK,EAAE,SAAS,EAChB,IAAI,EAAE,MAAM,EACZ,WAAW,EAAE,MAAM,EAAE,EACrB,YAAY,CAAC,EAAE,MAAM,GACpB,OAAO,CAAC;QAAE,KAAK,EAAE,MAAM,CAAC;QAAC,QAAQ,EAAE,aAAa,EAAE,CAAC;QAAC,GAAG,EAAE,MAAM,CAAC;QAAC,UAAU,CAAC,EAAE,MAAM,CAAC;QAAC,iBAAiB,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,CAAA;KAAE,CAAC;IAiGvI;;;;OAIG;IACG,gBAAgB,CACpB,cAAc,EAAE,MAAM,EACtB,MAAM,EAAE,MAAM,GACb,OAAO,CAAC,KAAK,CAAC;QAAE,IAAI,EAAE,QAAQ,GAAG,UAAU,GAAG,SAAS,GAAG,OAAO,CAAC;QAAC,GAAG,EAAE,MAAM,CAAC;QAAC,KAAK,EAAE,MAAM,CAAA;KAAE,CAAC,CAAC;IAqDpG,OAAO,CAAC,KAAK;CAqDd;AAsHD;;;;;;;;;;;GAWG;AACH,wBAAgB,cAAc,CAAC,QAAQ,EAAE,MAAM,EAAE,QAAQ,SAAS,GAAG,MAAM,CAgE1E"}
|