testdriverai 7.2.3 → 7.2.10

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.
Files changed (142) hide show
  1. package/.github/workflows/publish.yaml +15 -7
  2. package/.github/workflows/testdriver.yml +163 -0
  3. package/.testdriver/last-sandbox +7 -0
  4. package/agent/events.js +1 -0
  5. package/agent/index.js +99 -163
  6. package/agent/lib/sandbox.js +11 -1
  7. package/agents.md +393 -0
  8. package/bin/testdriverai.js +8 -0
  9. package/debug/01-table-initial.png +0 -0
  10. package/debug/02-after-ai-explore.png +0 -0
  11. package/debug/02-after-scroll.png +0 -0
  12. package/debugger/index.html +37 -0
  13. package/docs/docs.json +93 -125
  14. package/docs/v7/_drafts/architecture.mdx +1 -26
  15. package/docs/v7/_drafts/caching.mdx +2 -2
  16. package/docs/v7/{getting-started → _drafts}/installation.mdx +0 -66
  17. package/docs/v7/{features/coverage.mdx → _drafts/powerful.mdx} +1 -90
  18. package/docs/v7/_drafts/quick-start-test-recording.mdx +0 -1
  19. package/docs/v7/{features → _drafts}/scalable.mdx +126 -4
  20. package/docs/v7/_drafts/screenshot.mdx +155 -0
  21. package/docs/v7/_drafts/test-recording.mdx +0 -6
  22. package/docs/v7/_drafts/writing-tests.mdx +25 -0
  23. package/docs/v7/{api/act.mdx → ai.mdx} +28 -27
  24. package/docs/v7/{api/assert.mdx → assert.mdx} +3 -3
  25. package/docs/v7/aws-setup.mdx +338 -0
  26. package/docs/v7/caching.mdx +128 -0
  27. package/docs/v7/ci-cd.mdx +605 -0
  28. package/docs/v7/{api/click.mdx → click.mdx} +4 -4
  29. package/docs/v7/cloud.mdx +120 -0
  30. package/docs/v7/customizing-devices.mdx +129 -0
  31. package/docs/v7/{api/doubleClick.mdx → double-click.mdx} +5 -5
  32. package/docs/v7/enterprise.mdx +135 -0
  33. package/docs/v7/examples.mdx +5 -0
  34. package/docs/v7/{api/exec.mdx → exec.mdx} +3 -3
  35. package/docs/v7/{api/find.mdx → find.mdx} +17 -21
  36. package/docs/v7/{api/focusApplication.mdx → focus-application.mdx} +3 -3
  37. package/docs/v7/generating-tests.mdx +32 -0
  38. package/docs/v7/{api/hover.mdx → hover.mdx} +3 -3
  39. package/docs/v7/locating-elements.mdx +71 -0
  40. package/docs/v7/making-assertions.mdx +32 -0
  41. package/docs/v7/{api/mouseDown.mdx → mouse-down.mdx} +7 -7
  42. package/docs/v7/{api/mouseUp.mdx → mouse-up.mdx} +8 -8
  43. package/docs/v7/performing-actions.mdx +51 -0
  44. package/docs/v7/{api/pressKeys.mdx → press-keys.mdx} +3 -3
  45. package/docs/v7/quickstart.mdx +162 -0
  46. package/docs/v7/reusable-code.mdx +240 -0
  47. package/docs/v7/{api/rightClick.mdx → right-click.mdx} +5 -5
  48. package/docs/v7/running-tests.mdx +181 -0
  49. package/docs/v7/{api/scroll.mdx → scroll.mdx} +3 -3
  50. package/docs/v7/secrets.mdx +115 -0
  51. package/docs/v7/self-hosted.mdx +66 -0
  52. package/docs/v7/{api/type.mdx → type.mdx} +3 -3
  53. package/docs/v7/variables.mdx +111 -0
  54. package/docs/v7/waiting-for-elements.mdx +66 -0
  55. package/docs/v7/what-is-testdriver.mdx +54 -0
  56. package/interfaces/cli/commands/init.js +33 -19
  57. package/interfaces/cli/lib/base.js +24 -0
  58. package/interfaces/cli.js +8 -1
  59. package/interfaces/logger.js +8 -3
  60. package/interfaces/vitest-plugin.mjs +16 -71
  61. package/lib/sentry.js +343 -0
  62. package/lib/vitest/hooks.mjs +81 -81
  63. package/package.json +4 -3
  64. package/sdk-log-formatter.js +41 -0
  65. package/sdk.d.ts +22 -9
  66. package/sdk.js +344 -100
  67. package/test/manual/reconnect-provision.test.mjs +49 -0
  68. package/test/manual/reconnect-signin.test.mjs +41 -0
  69. package/test/testdriver/act.test.mjs +30 -0
  70. package/test/testdriver/ai.test.mjs +30 -0
  71. package/test/testdriver/assert.test.mjs +1 -1
  72. package/test/testdriver/hover-text.test.mjs +1 -1
  73. package/test/testdriver/setup/testHelpers.mjs +8 -119
  74. package/test/testdriver/windows-installer.test.mjs +61 -0
  75. package/tests/example.test.js +33 -0
  76. package/tests/login.js +28 -0
  77. package/tests/table-sort-enrollments.test.mjs +72 -0
  78. package/tests/table-sort-experiment.test.mjs +42 -0
  79. package/tests/table-sort-setup.test.mjs +59 -0
  80. package/vitest.config.mjs +3 -1
  81. package/agent/lib/cache.js +0 -142
  82. package/docs/v7/api/assertions.mdx +0 -403
  83. package/docs/v7/features/ai-native.mdx +0 -413
  84. package/docs/v7/features/application-logs.mdx +0 -353
  85. package/docs/v7/features/browser-logs.mdx +0 -414
  86. package/docs/v7/features/cache-management.mdx +0 -402
  87. package/docs/v7/features/continuous-testing.mdx +0 -346
  88. package/docs/v7/features/data-driven-testing.mdx +0 -441
  89. package/docs/v7/features/easy-to-write.mdx +0 -280
  90. package/docs/v7/features/enterprise.mdx +0 -656
  91. package/docs/v7/features/fast.mdx +0 -406
  92. package/docs/v7/features/managed-sandboxes.mdx +0 -384
  93. package/docs/v7/features/network-monitoring.mdx +0 -568
  94. package/docs/v7/features/parallel-execution.mdx +0 -381
  95. package/docs/v7/features/powerful.mdx +0 -531
  96. package/docs/v7/features/sandbox-customization.mdx +0 -229
  97. package/docs/v7/features/stable.mdx +0 -473
  98. package/docs/v7/features/system-performance.mdx +0 -616
  99. package/docs/v7/features/test-analytics.mdx +0 -373
  100. package/docs/v7/features/test-cases.mdx +0 -393
  101. package/docs/v7/features/test-replays.mdx +0 -408
  102. package/docs/v7/features/test-reports.mdx +0 -308
  103. package/docs/v7/getting-started/debugging-tests.mdx +0 -382
  104. package/docs/v7/getting-started/quickstart.mdx +0 -90
  105. package/docs/v7/getting-started/running-tests.mdx +0 -173
  106. package/docs/v7/getting-started/setting-up-in-ci.mdx +0 -612
  107. package/docs/v7/getting-started/writing-tests.mdx +0 -534
  108. package/docs/v7/overview/what-is-testdriver.mdx +0 -386
  109. package/docs/v7/presets/chrome-extension.mdx +0 -248
  110. package/docs/v7/presets/chrome.mdx +0 -300
  111. package/docs/v7/presets/electron.mdx +0 -460
  112. package/docs/v7/presets/vscode.mdx +0 -417
  113. package/docs/v7/presets/webapp.mdx +0 -393
  114. /package/docs/v7/{commands → _drafts/commands}/assert.mdx +0 -0
  115. /package/docs/v7/{commands → _drafts/commands}/exec.mdx +0 -0
  116. /package/docs/v7/{commands → _drafts/commands}/focus-application.mdx +0 -0
  117. /package/docs/v7/{commands → _drafts/commands}/hover-image.mdx +0 -0
  118. /package/docs/v7/{commands → _drafts/commands}/hover-text.mdx +0 -0
  119. /package/docs/v7/{commands → _drafts/commands}/if.mdx +0 -0
  120. /package/docs/v7/{commands → _drafts/commands}/match-image.mdx +0 -0
  121. /package/docs/v7/{commands → _drafts/commands}/press-keys.mdx +0 -0
  122. /package/docs/v7/{commands → _drafts/commands}/remember.mdx +0 -0
  123. /package/docs/v7/{commands → _drafts/commands}/run.mdx +0 -0
  124. /package/docs/v7/{commands → _drafts/commands}/scroll-until-image.mdx +0 -0
  125. /package/docs/v7/{commands → _drafts/commands}/scroll-until-text.mdx +0 -0
  126. /package/docs/v7/{commands → _drafts/commands}/scroll.mdx +0 -0
  127. /package/docs/v7/{commands → _drafts/commands}/type.mdx +0 -0
  128. /package/docs/v7/{commands → _drafts/commands}/wait-for-image.mdx +0 -0
  129. /package/docs/v7/{commands → _drafts/commands}/wait-for-text.mdx +0 -0
  130. /package/docs/v7/{commands → _drafts/commands}/wait.mdx +0 -0
  131. /package/docs/v7/{getting-started → _drafts}/configuration.mdx +0 -0
  132. /package/docs/v7/{features → _drafts}/observable.mdx +0 -0
  133. /package/docs/v7/{platforms → _drafts/platforms}/linux.mdx +0 -0
  134. /package/docs/v7/{platforms → _drafts/platforms}/macos.mdx +0 -0
  135. /package/docs/v7/{platforms → _drafts/platforms}/windows.mdx +0 -0
  136. /package/docs/v7/{playwright.mdx → _drafts/playwright.mdx} +0 -0
  137. /package/docs/v7/{overview → _drafts}/readme.mdx +0 -0
  138. /package/docs/v7/{features → _drafts}/reports.mdx +0 -0
  139. /package/docs/v7/{api/client.mdx → client.mdx} +0 -0
  140. /package/docs/v7/{api/dashcam.mdx → dashcam.mdx} +0 -0
  141. /package/docs/v7/{api/elements.mdx → elements.mdx} +0 -0
  142. /package/docs/v7/{api/sandbox.mdx → sandbox.mdx} +0 -0
@@ -1,386 +0,0 @@
1
- ---
2
- title: "What is TestDriver?"
3
- description: "AI-powered end-to-end testing for web, desktop, and mobile applications"
4
- icon: "circle-info"
5
- mode: "wide"
6
- ---
7
-
8
- TestDriver is an AI-native testing platform that lets you write tests in natural language. It uses computer vision and AI to understand your application like a human would, eliminating brittle selectors and making tests easy to write and maintain.
9
-
10
- ## The Problem with Traditional Testing
11
-
12
- Traditional E2E testing tools require:
13
-
14
- <CardGroup cols={1}>
15
- <Card title="Brittle Selectors" icon="triangle-exclamation">
16
- ```javascript
17
- // ❌ Breaks when DOM changes
18
- await page.click('#root > div > form > div:nth-child(2) > button')
19
- ```
20
- </Card>
21
-
22
- <Card title="Flaky Tests" icon="shuffle">
23
- ```javascript
24
- // ❌ Arbitrary waits
25
- await page.click('button')
26
- await page.waitForTimeout(1000)
27
- await page.click('.dropdown-item')
28
- ```
29
- </Card>
30
-
31
- <Card title="Limited Scope" icon="ban">
32
- Most tools only work for web browsers. Testing desktop apps, extensions, or IDEs requires completely different frameworks.
33
- </Card>
34
- </CardGroup>
35
-
36
- ## The TestDriver Solution
37
-
38
- TestDriver solves these problems with AI-powered testing:
39
-
40
- <CodeGroup>
41
- ```javascript TestDriver - Natural & Simple
42
- import { test } from 'vitest';
43
- import { chrome } from 'testdriverai/presets';
44
-
45
- test('user can login', async (context) => {
46
- const { testdriver } = await chrome(context, {
47
- url: 'https://myapp.com/login'
48
- });
49
-
50
- await testdriver.find('email input').type('user@example.com');
51
- await testdriver.find('password input').type('secret', { secret: true });
52
- await testdriver.find('Login button').click();
53
-
54
- await testdriver.assert('Dashboard is visible');
55
- });
56
- ```
57
-
58
- ```javascript Traditional - Complex & Brittle
59
- import puppeteer from 'puppeteer';
60
-
61
- test('user can login', async () => {
62
- const browser = await puppeteer.launch();
63
- const page = await browser.newPage();
64
-
65
- try {
66
- await page.goto('https://myapp.com/login');
67
-
68
- const email = await page.waitForSelector(
69
- 'input[type="email"][name="email"]',
70
- { state: 'visible', timeout: 30000 }
71
- );
72
- await email.type('user@example.com');
73
-
74
- const password = await page.waitForSelector(
75
- 'input[type="password"][name="password"]',
76
- { state: 'visible', timeout: 30000 }
77
- );
78
- await password.type('secret');
79
-
80
- const button = await page.waitForSelector(
81
- 'button[type="submit"]',
82
- { state: 'visible', timeout: 30000 }
83
- );
84
- await button.click();
85
-
86
- await page.waitForSelector('.dashboard', {
87
- state: 'visible',
88
- timeout: 30000
89
- });
90
- } finally {
91
- await browser.close();
92
- }
93
- });
94
- ```
95
- </CodeGroup>
96
-
97
- ## How It Works
98
-
99
- TestDriver uses Claude AI's computer vision to understand your application:
100
-
101
- <Steps>
102
- <Step title="Natural Language">
103
- Describe what you want to interact with in plain English:
104
-
105
- ```javascript
106
- await testdriver.find('submit button in the login form')
107
- ```
108
- </Step>
109
-
110
- <Step title="AI Vision Analysis">
111
- TestDriver captures a screenshot and asks Claude AI to locate the element using computer vision - just like a human would.
112
- </Step>
113
-
114
- <Step title="Smart Caching">
115
- Element locations are cached for 1.7x faster subsequent runs. The cache automatically invalidates when your UI changes.
116
- </Step>
117
-
118
- <Step title="Automatic Stability">
119
- TestDriver waits for animations, network requests, and DOM changes to complete before acting - no manual waits needed.
120
- </Step>
121
- </Steps>
122
-
123
- ## Key Features
124
-
125
- <CardGroup cols={2}>
126
- <Card title="Easy to Write" icon="feather" href="/v7/features/easy-to-write">
127
- Natural language selectors, chainable API, full TypeScript support
128
- </Card>
129
-
130
- <Card title="Fast Performance" icon="bolt" href="/v7/features/fast">
131
- 1.7x faster with intelligent caching
132
- </Card>
133
-
134
- <Card title="Stable & Reliable" icon="shield-check" href="/v7/features/stable">
135
- Anti-flake technology eliminates timing issues
136
- </Card>
137
-
138
- <Card title="Scalable" icon="arrow-up-right-dots" href="/v7/features/scalable">
139
- From 1 test to 10,000+ with Vitest integration
140
- </Card>
141
-
142
- <Card title="AI-Native" icon="robot" href="/v7/features/ai-native">
143
- Built for AI agents and autonomous testing
144
- </Card>
145
-
146
- <Card title="Powerful" icon="wand-magic-sparkles" href="/v7/features/powerful">
147
- Test web, desktop, mobile, extensions, and more
148
- </Card>
149
-
150
- <Card title="Observable" icon="microscope" href="/v7/features/observable">
151
- Video replays, logs, and complete debugging tools
152
- </Card>
153
-
154
- <Card title="Enterprise Ready" icon="building" href="/v7/features/enterprise">
155
- Security, compliance, and on-premise deployment
156
- </Card>
157
- </CardGroup>
158
-
159
- ## What Can You Test?
160
-
161
- TestDriver is the only platform that lets you test everything with one SDK:
162
-
163
- <Tabs>
164
- <Tab title="Web Applications">
165
- ```javascript
166
- import { chrome } from 'testdriverai/presets';
167
-
168
- test('web app', async (context) => {
169
- const { testdriver } = await chrome(context, {
170
- url: 'https://myapp.com'
171
- });
172
- // Test any website
173
- });
174
- ```
175
- </Tab>
176
-
177
- <Tab title="Desktop Apps">
178
- ```javascript
179
- import { desktop } from 'testdriverai/presets';
180
-
181
- test('desktop app', async (context) => {
182
- const { testdriver } = await desktop(context, {
183
- appPath: '/Applications/MyApp.app'
184
- });
185
- // Test Windows, macOS, Linux apps
186
- });
187
- ```
188
- </Tab>
189
-
190
- <Tab title="Chrome Extensions">
191
- ```javascript
192
- import { chromeExtension } from 'testdriverai/presets';
193
-
194
- test('extension', async (context) => {
195
- const { testdriver } = await chromeExtension(context, {
196
- extensionPath: './my-extension'
197
- });
198
- // Test browser extensions
199
- });
200
- ```
201
- </Tab>
202
-
203
- <Tab title="VS Code Extensions">
204
- ```javascript
205
- import { vscode } from 'testdriverai/presets';
206
-
207
- test('vscode', async (context) => {
208
- const { testdriver } = await vscode(context, {
209
- workspace: '/tmp/project'
210
- });
211
- // Test IDE extensions
212
- });
213
- ```
214
- </Tab>
215
-
216
- <Tab title="Electron Apps">
217
- ```javascript
218
- import { electron } from 'testdriverai/presets';
219
-
220
- test('electron', async (context) => {
221
- const { app } = await electron(context, {
222
- appPath: './dist/my-app'
223
- });
224
- // Test Electron applications
225
- });
226
- ```
227
- </Tab>
228
- </Tabs>
229
-
230
- ## How TestDriver Compares
231
-
232
- <AccordionGroup>
233
- <Accordion title="vs. Playwright / Selenium">
234
- **TestDriver Advantages:**
235
- - 🎯 Natural language selectors (no CSS/XPath)
236
- - 🤖 AI-powered assertions
237
- - 🛡️ Built-in anti-flake technology
238
- - 💻 Desktop app support
239
- - ☁️ Hosted infrastructure included
240
- - 📹 Automatic video recording
241
-
242
- **When to use Playwright/Selenium:**
243
- - You need low-level browser control
244
- - You're testing extremely complex DOM structures
245
- - You require specific browser APIs
246
- </Accordion>
247
-
248
- <Accordion title="vs. Cypress">
249
- **TestDriver Advantages:**
250
- - 🖥️ Cross-platform (Windows, macOS, Linux)
251
- - 📱 Desktop application support
252
- - 🤖 AI-powered element location
253
- - ☁️ Hosted sandboxes included
254
- - ⚡ No flake from timing issues
255
- - 🌐 Multi-application testing
256
-
257
- **When to use Cypress:**
258
- - You only test web applications
259
- - You need real-time debugging in browser
260
- - You want to run tests in-browser only
261
- </Accordion>
262
-
263
- <Accordion title="vs. Manual QA">
264
- **TestDriver Advantages:**
265
- - ⚡ 100x faster execution
266
- - 🎯 Perfect consistency
267
- - 🔄 Run thousands of tests in parallel
268
- - 🚫 Zero human error
269
- - 🌙 24/7 execution capability
270
- - 🐛 Instant regression detection
271
-
272
- **When to use Manual QA:**
273
- - Exploratory testing
274
- - UX/design feedback
275
- - Edge cases not worth automating
276
- </Accordion>
277
- </AccordionGroup>
278
-
279
- ## Architecture
280
-
281
- TestDriver consists of three main components:
282
-
283
- ```mermaid
284
- graph LR
285
- A[Your Test Code] --> B[TestDriver SDK]
286
- B --> C[TestDriver API]
287
- C --> D[Claude AI Vision]
288
- C --> E[Sandbox VM]
289
- E --> F[Your Application]
290
-
291
- style A fill:#b3d334
292
- style B fill:#152a65,color:#fff
293
- style C fill:#152a65,color:#fff
294
- style D fill:#b3d334
295
- style E fill:#152a65,color:#fff
296
- ```
297
-
298
- 1. **TestDriver SDK** - The JavaScript/TypeScript library you use in your tests
299
- 2. **TestDriver API** - Cloud service that orchestrates sandboxes and AI
300
- 3. **Sandbox VMs** - Isolated virtual machines where your application runs
301
-
302
- [Learn more about architecture](/v7/api/sandbox)
303
-
304
- ## Pricing Model
305
-
306
- TestDriver uses usage-based pricing:
307
-
308
- <Card title="Pay-per-use" icon="dollar-sign">
309
- **What you pay for:**
310
- - AI vision analysis calls
311
- - Sandbox VM time (per minute)
312
- - Dashcam video storage
313
-
314
- **What's included:**
315
- - Intelligent caching (reduces costs by 90%+)
316
- - Shared team cache
317
- - Unlimited team members
318
- - Unlimited test executions
319
-
320
- **Typical costs:**
321
- - Single test: $0.04 - $0.12
322
- - 100-test suite: $4 - $12 (first run)
323
- - Cached suite: $0.50 - $2 (subsequent runs)
324
- </Card>
325
-
326
- Enterprise plans available with unlimited usage, on-premise deployment, and custom SLA.
327
-
328
- [View pricing details](https://testdriver.ai/pricing)
329
-
330
- ## Getting Started
331
-
332
- Ready to write your first test?
333
-
334
- <CardGroup cols={3}>
335
- <Card
336
- title="Quick Start"
337
- icon="rocket"
338
- href="/v7/getting-started/installation"
339
- >
340
- Install and run your first test in 2 minutes
341
- </Card>
342
-
343
- <Card
344
- title="View Examples"
345
- icon="code"
346
- href="/v7/presets/chrome"
347
- >
348
- See TestDriver in action
349
- </Card>
350
-
351
- <Card
352
- title="Watch Demo"
353
- icon="play"
354
- href="https://testdriver.ai/demo"
355
- >
356
- Schedule a live demo
357
- </Card>
358
- </CardGroup>
359
-
360
- ## Community & Support
361
-
362
- <CardGroup cols={3}>
363
- <Card
364
- title="Discord Community"
365
- icon="discord"
366
- href="https://discord.com/invite/cWDFW8DzPm"
367
- >
368
- Join 1,000+ developers
369
- </Card>
370
-
371
- <Card
372
- title="GitHub"
373
- icon="github"
374
- href="https://github.com/testdriverai"
375
- >
376
- View examples and contribute
377
- </Card>
378
-
379
- <Card
380
- title="Documentation"
381
- icon="book"
382
- href="/v7/getting-started/installation"
383
- >
384
- Complete guides and API reference
385
- </Card>
386
- </CardGroup>
@@ -1,248 +0,0 @@
1
- ---
2
- title: "Chrome Extension Testing"
3
- sidebarTitle: "Chrome Extensions"
4
- description: "Test Chrome extensions with Chrome for Testing"
5
- icon: "puzzle-piece"
6
- ---
7
-
8
- ## Overview
9
-
10
- Test Chrome extensions by loading them into Chrome for Testing. Use `testdriver.provision.chromeExtension()` to launch Chrome with either:
11
- - A **local unpacked extension** via `extensionPath`
12
- - A **Chrome Web Store extension** via `extensionId`
13
-
14
- The dashcam-chrome extension is automatically included on Linux for web log capture.
15
-
16
- ## Quick Start
17
-
18
- ### Using a Local Extension Path
19
-
20
- ```javascript
21
- import { describe, it, expect } from 'vitest';
22
- import { TestDriver } from 'testdriverai/vitest/hooks';
23
-
24
- describe('Chrome Extension Test', () => {
25
- it('should load and test a Chrome extension', async (context) => {
26
- const testdriver = TestDriver(context, { headless: true });
27
-
28
- // Wait for connection
29
- await testdriver.ready();
30
-
31
- // Clone an extension repo
32
- await testdriver.exec(
33
- 'sh',
34
- 'git clone --depth 1 https://github.com/GoogleChrome/chrome-extensions-samples.git /tmp/chrome-extensions-samples',
35
- 60000,
36
- true
37
- );
38
-
39
- // Launch Chrome with the extension loaded
40
- await testdriver.provision.chromeExtension({
41
- extensionPath: '/tmp/chrome-extensions-samples/functional-samples/tutorial.hello-world',
42
- url: 'https://example.com'
43
- });
44
-
45
- // Your test code here
46
- const result = await testdriver.assert("the page is visible");
47
- expect(result).toBeTruthy();
48
- });
49
- });
50
- ```
51
-
52
- ### Using a Chrome Web Store Extension ID
53
-
54
- ```javascript
55
- import { describe, it, expect } from 'vitest';
56
- import { TestDriver } from 'testdriverai/vitest/hooks';
57
-
58
- describe('Chrome Extension Test', () => {
59
- it('should load uBlock Origin and verify it works', async (context) => {
60
- const testdriver = TestDriver(context, { headless: true });
61
-
62
- // Launch Chrome with uBlock Origin loaded by its Chrome Web Store ID
63
- await testdriver.provision.chromeExtension({
64
- extensionId: 'cjpalhdlnbpafiamejdnhcphjbkeiagm', // uBlock Origin
65
- url: 'https://example.com'
66
- });
67
-
68
- // Your test code here
69
- const result = await testdriver.assert("the page is visible");
70
- expect(result).toBeTruthy();
71
- });
72
- });
73
- ```
74
-
75
- ## API Reference
76
-
77
- ### `testdriver.provision.chromeExtension(options)`
78
-
79
- Launches Chrome for Testing with a custom extension loaded.
80
-
81
- | Option | Type | Default | Description |
82
- |--------|------|---------|-------------|
83
- | `extensionPath` | `string` | - | Local filesystem path to the unpacked extension directory |
84
- | `extensionId` | `string` | - | Chrome Web Store extension ID (e.g., `cjpalhdlnbpafiamejdnhcphjbkeiagm`) |
85
- | `url` | `string` | `'http://testdriver-sandbox.vercel.app/'` | URL to navigate to after launch |
86
- | `maximized` | `boolean` | `true` | Start Chrome maximized |
87
-
88
- **Note:** Either `extensionPath` or `extensionId` is required. On Linux, the dashcam-chrome extension is automatically loaded alongside your extension for web log capture.
89
-
90
- ## Finding Extension IDs
91
-
92
- Extension IDs can be found in the Chrome Web Store URL:
93
-
94
- ```
95
- https://chrome.google.com/webstore/detail/ublock-origin/cjpalhdlnbpafiamejdnhcphjbkeiagm
96
- ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
97
- This is the extension ID
98
- ```
99
-
100
- ### Popular Extensions
101
-
102
- | Extension | ID |
103
- |-----------|---|
104
- | uBlock Origin | `cjpalhdlnbpafiamejdnhcphjbkeiagm` |
105
- | React Developer Tools | `fmkadmapgofadopljbjfkapdkoienihi` |
106
- | Redux DevTools | `lmhkpmbekcpmknklioeibfkpmmfibljd` |
107
- | Bitwarden | `nngceckbapebfimnlniiiahkandclblb` |
108
-
109
- ## Using Your Own Extension
110
-
111
- To test your own extension, you can either:
112
-
113
- 1. **Clone from a repository:**
114
- ```javascript
115
- await testdriver.ready();
116
- await testdriver.exec('sh', 'git clone https://github.com/your/extension.git /tmp/my-extension', 60000, true);
117
- await testdriver.provision.chromeExtension({
118
- extensionPath: '/tmp/my-extension',
119
- url: 'https://example.com'
120
- });
121
- ```
122
-
123
- 2. **Upload your extension files** (if supported by your test setup)
124
-
125
- 3. **Use a pre-built extension** in a known location
126
-
127
- ## Complete Example
128
-
129
- ```javascript
130
- import { describe, it, expect } from 'vitest';
131
- import { TestDriver } from 'testdriverai/vitest/hooks';
132
-
133
- describe('Chrome Extension - Hello World', () => {
134
- it('should load extension and verify popup', async (context) => {
135
- const testdriver = TestDriver(context, {
136
- headless: true,
137
- newSandbox: true,
138
- cacheKey: 'chrome-extension-test'
139
- });
140
-
141
- // Clone the Chrome extensions samples repo
142
- await testdriver.exec(
143
- 'sh',
144
- 'git clone --depth 1 https://github.com/GoogleChrome/chrome-extensions-samples.git /tmp/chrome-extensions-samples',
145
- 60000,
146
- true
147
- );
148
-
149
- // Launch Chrome with the hello-world extension loaded
150
- await testdriver.provision.chromeExtension({
151
- extensionPath: '/tmp/chrome-extensions-samples/functional-samples/tutorial.hello-world',
152
- url: 'https://testdriver.ai'
153
- });
154
-
155
- // Verify the page loaded
156
- const pageResult = await testdriver.assert("the testdriver.ai website is visible");
157
- expect(pageResult).toBeTruthy();
158
-
159
- // Click on the extensions button in Chrome toolbar
160
- const extensionsButton = await testdriver.find("Extensions button, puzzle piece icon in Chrome toolbar");
161
- await extensionsButton.click();
162
-
163
- // Find and click the hello world extension
164
- const helloExtension = await testdriver.find("Hello World extension in the extensions dropdown");
165
- await helloExtension.click();
166
-
167
- // Verify the extension popup shows
168
- const popupResult = await testdriver.assert("a popup shows with the text 'Hello Extensions'");
169
- expect(popupResult).toBeTruthy();
170
- });
171
- });
172
- ```
173
-
174
- ## Environment Setup
175
-
176
- Chrome for Testing is pre-installed in the E2B sandbox environment at:
177
-
178
- ```
179
- /opt/chrome-for-testing/chrome
180
- /usr/local/bin/chrome-for-testing (symlink)
181
- ```
182
-
183
- The dashcam-chrome extension is pre-installed at:
184
- ```
185
- /usr/lib/node_modules/dashcam-chrome/build
186
- ```
187
-
188
- ## Testing Extension Features
189
-
190
- ### Test Extension Popup
191
-
192
- ```javascript
193
- it('opens extension popup', async (context) => {
194
- const testdriver = TestDriver(context, { headless: true });
195
-
196
- // Setup extension...
197
- await testdriver.provision.chromeExtension({
198
- extensionPath: '/path/to/extension',
199
- url: 'https://example.com'
200
- });
201
-
202
- // Click extension icon in toolbar
203
- const extensionIcon = await testdriver.find('extension icon in toolbar');
204
- await extensionIcon.click();
205
-
206
- // Interact with popup
207
- const result = await testdriver.assert('extension popup is visible');
208
- expect(result).toBeTruthy();
209
- });
210
- ```
211
-
212
- ### Test Content Scripts
213
-
214
- ```javascript
215
- it('verifies content script injection', async (context) => {
216
- const testdriver = TestDriver(context, { headless: true });
217
-
218
- await testdriver.provision.chromeExtension({
219
- extensionPath: '/path/to/extension',
220
- url: 'https://example.com'
221
- });
222
-
223
- // Check for extension-injected elements
224
- const result = await testdriver.assert('element added by extension is visible');
225
- expect(result).toBeTruthy();
226
- });
227
- ```
228
-
229
- ## Troubleshooting
230
-
231
- ### Extension Not Loading
232
-
233
- 1. Verify the extension path exists and contains a valid `manifest.json`
234
- 2. Check Chrome for Testing is installed in the sandbox
235
- 3. Ensure extension is compatible with Chrome for Testing version (Manifest V3 recommended)
236
-
237
- ### Extension Permissions
238
-
239
- Some extensions may require additional permissions or setup. You may need to:
240
-
241
- 1. Navigate to `chrome://extensions/`
242
- 2. Enable developer mode
243
- 3. Grant required permissions
244
-
245
- ## See Also
246
-
247
- - [Web Apps (Chrome)](/v7/presets/chrome) - Regular Chrome browser testing
248
- - [Desktop Apps (Electron)](/v7/presets/electron) - Electron app testing- [Lifecycle Helpers](/v7/guides/lifecycle) - Prerun/postrun functions