@testdriverai/mcp 7.11.136-test → 7.11.138-test

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 (174) hide show
  1. package/ai/skills/testdriver-assert/SKILL.md +5 -5
  2. package/ai/skills/testdriver-caching/SKILL.md +2 -2
  3. package/ai/skills/testdriver-changelog/SKILL.md +186 -0
  4. package/ai/skills/testdriver-claude-mcp-plugin/SKILL.md +208 -0
  5. package/ai/skills/testdriver-click/SKILL.md +13 -13
  6. package/ai/skills/testdriver-client/SKILL.md +1 -1
  7. package/ai/skills/testdriver-debugging-with-screenshots/SKILL.md +5 -5
  8. package/ai/skills/testdriver-double-click/SKILL.md +7 -7
  9. package/ai/skills/testdriver-enterprise/SKILL.md +1 -1
  10. package/ai/skills/testdriver-events/SKILL.md +1 -1
  11. package/ai/skills/testdriver-exec/SKILL.md +10 -10
  12. package/ai/skills/testdriver-extract/SKILL.md +6 -6
  13. package/ai/skills/testdriver-find/SKILL.md +61 -61
  14. package/ai/skills/testdriver-focus-application/SKILL.md +6 -6
  15. package/ai/skills/testdriver-generating-tests/SKILL.md +3 -3
  16. package/ai/skills/testdriver-hosted/SKILL.md +3 -3
  17. package/ai/skills/testdriver-hover/SKILL.md +6 -6
  18. package/ai/skills/testdriver-making-assertions/SKILL.md +2 -2
  19. package/ai/skills/testdriver-mouse-down/SKILL.md +9 -9
  20. package/ai/skills/testdriver-mouse-up/SKILL.md +9 -9
  21. package/ai/skills/testdriver-parse/SKILL.md +4 -4
  22. package/ai/skills/testdriver-performing-actions/SKILL.md +4 -4
  23. package/ai/skills/testdriver-press-keys/SKILL.md +5 -5
  24. package/ai/skills/testdriver-quickstart/SKILL.md +51 -54
  25. package/ai/skills/testdriver-redraw/SKILL.md +1 -1
  26. package/ai/skills/testdriver-right-click/SKILL.md +7 -7
  27. package/ai/skills/testdriver-screenshot/SKILL.md +9 -9
  28. package/ai/skills/testdriver-scroll/SKILL.md +13 -13
  29. package/ai/skills/testdriver-self-hosted/SKILL.md +1 -1
  30. package/ai/skills/testdriver-type/SKILL.md +7 -7
  31. package/ai/skills/testdriver-wait/SKILL.md +5 -5
  32. package/ai/skills/testdriver-what-is-testdriver/SKILL.md +11 -11
  33. package/docs/{v7/_drafts → _drafts}/agents.mdx +1 -1
  34. package/docs/{v7/_drafts → _drafts}/best-practices.mdx +4 -4
  35. package/docs/{v7/_drafts → _drafts}/caching-selectors.mdx +3 -3
  36. package/docs/{v7/_drafts → _drafts}/configuration.mdx +4 -4
  37. package/docs/{v7/_drafts → _drafts}/debugging.mdx +4 -4
  38. package/docs/{v7/_drafts → _drafts}/error-handling.mdx +4 -4
  39. package/docs/{v7/_drafts → _drafts}/faq.mdx +7 -7
  40. package/docs/{v7/_drafts → _drafts}/installation.mdx +2 -2
  41. package/docs/{v7/_drafts → _drafts}/migration.mdx +4 -4
  42. package/docs/{v7/_drafts → _drafts}/observable.mdx +3 -3
  43. package/docs/{v7/_drafts → _drafts}/powerful.mdx +4 -4
  44. package/docs/{v7/_drafts → _drafts}/readme.mdx +11 -11
  45. package/docs/{v7/_drafts → _drafts}/reports.mdx +4 -4
  46. package/docs/{v7/_drafts → _drafts}/scalable.mdx +10 -10
  47. package/docs/{v7/_drafts → _drafts}/troubleshooting.mdx +4 -4
  48. package/docs/{v7/_drafts → _drafts}/vitest-plugin.mdx +2 -2
  49. package/docs/{v7/_drafts → _drafts}/vitest.mdx +9 -9
  50. package/docs/_scripts/generate-examples.js +9 -10
  51. package/docs/_scripts/generate-skills.js +4 -4
  52. package/docs/{v7/agent.mdx → agent.mdx} +17 -17
  53. package/docs/{v7/assert.mdx → assert.mdx} +5 -5
  54. package/docs/{v7/aws-setup.mdx → aws-setup.mdx} +6 -6
  55. package/docs/{v7/cache.mdx → cache.mdx} +9 -9
  56. package/docs/{v7/caching.mdx → caching.mdx} +13 -12
  57. package/docs/{v7/captcha.mdx → captcha.mdx} +7 -7
  58. package/docs/changelog.mdx +13 -13
  59. package/docs/{v7/ci-cd.mdx → ci-cd.mdx} +10 -10
  60. package/docs/{v7/click.mdx → click.mdx} +13 -13
  61. package/docs/client.mdx +323 -0
  62. package/docs/{v7/copilot → copilot}/auto-healing.mdx +2 -2
  63. package/docs/{v7/copilot → copilot}/running-tests.mdx +8 -8
  64. package/docs/{v7/customizing-devices.mdx → customizing-devices.mdx} +1 -1
  65. package/docs/{v7/dashcam.mdx → dashcam.mdx} +3 -3
  66. package/docs/{v7/debugging-with-screenshots.mdx → debugging-with-screenshots.mdx} +12 -12
  67. package/docs/docs.json +429 -288
  68. package/docs/{v7/double-click.mdx → double-click.mdx} +7 -7
  69. package/docs/{v7/elements.mdx → elements.mdx} +7 -7
  70. package/docs/{v7/enterprise.mdx → enterprise.mdx} +2 -2
  71. package/docs/{v7/errors.mdx → errors.mdx} +3 -3
  72. package/docs/{v7/events.mdx → events.mdx} +4 -4
  73. package/docs/{v7/exec.mdx → exec.mdx} +10 -10
  74. package/docs/{v7/extract.mdx → extract.mdx} +10 -10
  75. package/docs/{v7/find.mdx → find.mdx} +61 -61
  76. package/docs/{v7/focus-application.mdx → focus-application.mdx} +6 -6
  77. package/docs/{v7/generating-tests.mdx → generating-tests.mdx} +10 -10
  78. package/docs/guide/best-practices-polling.mdx +6 -1
  79. package/docs/{v7/hosted.mdx → hosted.mdx} +7 -7
  80. package/docs/{v7/hover.mdx → hover.mdx} +6 -6
  81. package/docs/interacting-with-your-app.mdx +198 -0
  82. package/docs/locating-elements.mdx +423 -0
  83. package/docs/{v7/making-assertions.mdx → making-assertions.mdx} +7 -7
  84. package/docs/{v7/mouse-down.mdx → mouse-down.mdx} +9 -9
  85. package/docs/{v7/mouse-up.mdx → mouse-up.mdx} +9 -9
  86. package/docs/options.mdx +320 -0
  87. package/docs/{v7/parse.mdx → parse.mdx} +12 -12
  88. package/docs/{v7/performing-actions.mdx → performing-actions.mdx} +11 -11
  89. package/docs/{v7/press-keys.mdx → press-keys.mdx} +5 -5
  90. package/docs/{v7/provision.mdx → provision.mdx} +9 -9
  91. package/docs/quickstart-cli.mdx +437 -0
  92. package/docs/quickstart-github.mdx +54 -0
  93. package/docs/quickstart-manual.mdx +135 -0
  94. package/docs/quickstart.mdx +22 -0
  95. package/docs/{v7/redraw.mdx → redraw.mdx} +7 -7
  96. package/docs/{v7/reusable-code.mdx → reusable-code.mdx} +3 -3
  97. package/docs/{v7/right-click.mdx → right-click.mdx} +7 -7
  98. package/docs/{v7/screenshot.mdx → screenshot.mdx} +9 -9
  99. package/docs/{v7/screenshots.mdx → screenshots.mdx} +3 -3
  100. package/docs/{v7/scroll.mdx → scroll.mdx} +13 -13
  101. package/docs/{v7/secrets.mdx → secrets.mdx} +4 -4
  102. package/docs/{v7/self-hosted.mdx → self-hosted.mdx} +7 -7
  103. package/docs/{v7/test-results-json.mdx → test-results-json.mdx} +4 -4
  104. package/docs/{v7/type.mdx → type.mdx} +7 -7
  105. package/docs/{v7/variables.mdx → variables.mdx} +2 -2
  106. package/docs/{v7/wait.mdx → wait.mdx} +5 -5
  107. package/docs/what-is-testdriver.mdx +54 -0
  108. package/lib/environments.json +1 -1
  109. package/lib/github-comment.mjs +2 -3
  110. package/package.json +1 -1
  111. package/scripts/generate-skills.js +1 -1
  112. package/docs/v7/client.mdx +0 -486
  113. package/docs/v7/quickstart.mdx +0 -451
  114. package/docs/v7/what-is-testdriver.mdx +0 -54
  115. /package/docs/{v7/_drafts → _drafts}/architecture.mdx +0 -0
  116. /package/docs/{v7/_drafts → _drafts}/auto-cache-key.mdx +0 -0
  117. /package/docs/{v7/_drafts → _drafts}/awesome-logs-quick-ref.mdx +0 -0
  118. /package/docs/{v7/_drafts → _drafts}/cli-to-sdk-migration.mdx +0 -0
  119. /package/docs/{v7/_drafts → _drafts}/commands/assert.mdx +0 -0
  120. /package/docs/{v7/_drafts → _drafts}/commands/exec.mdx +0 -0
  121. /package/docs/{v7/_drafts → _drafts}/commands/focus-application.mdx +0 -0
  122. /package/docs/{v7/_drafts → _drafts}/commands/hover-image.mdx +0 -0
  123. /package/docs/{v7/_drafts → _drafts}/commands/hover-text.mdx +0 -0
  124. /package/docs/{v7/_drafts → _drafts}/commands/if.mdx +0 -0
  125. /package/docs/{v7/_drafts → _drafts}/commands/match-image.mdx +0 -0
  126. /package/docs/{v7/_drafts → _drafts}/commands/press-keys.mdx +0 -0
  127. /package/docs/{v7/_drafts → _drafts}/commands/remember.mdx +0 -0
  128. /package/docs/{v7/_drafts → _drafts}/commands/run.mdx +0 -0
  129. /package/docs/{v7/_drafts → _drafts}/commands/scroll-until-image.mdx +0 -0
  130. /package/docs/{v7/_drafts → _drafts}/commands/scroll-until-text.mdx +0 -0
  131. /package/docs/{v7/_drafts → _drafts}/commands/scroll.mdx +0 -0
  132. /package/docs/{v7/_drafts → _drafts}/commands/type.mdx +0 -0
  133. /package/docs/{v7/_drafts → _drafts}/commands/wait-for-image.mdx +0 -0
  134. /package/docs/{v7/_drafts → _drafts}/commands/wait-for-text.mdx +0 -0
  135. /package/docs/{v7/_drafts → _drafts}/commands/wait.mdx +0 -0
  136. /package/docs/{v7/_drafts → _drafts}/contributing.mdx +0 -0
  137. /package/docs/{v7/_drafts → _drafts}/dashcam-title-feature.mdx +0 -0
  138. /package/docs/{v7/_drafts → _drafts}/hooks.mdx +0 -0
  139. /package/docs/{v7/_drafts → _drafts}/init-command.mdx +0 -0
  140. /package/docs/{v7/_drafts → _drafts}/playwright.mdx +0 -0
  141. /package/docs/{v7/_drafts → _drafts}/plugin-migration.mdx +0 -0
  142. /package/docs/{v7/_drafts → _drafts}/presets.mdx +0 -0
  143. /package/docs/{v7/_drafts → _drafts}/progressive-disclosure.mdx +0 -0
  144. /package/docs/{v7/_drafts → _drafts}/provision.mdx +0 -0
  145. /package/docs/{v7/_drafts → _drafts}/quick-start-test-recording.mdx +0 -0
  146. /package/docs/{v7/_drafts → _drafts}/screenshot.mdx +0 -0
  147. /package/docs/{v7/_drafts → _drafts}/sdk-awesome-logs.mdx +0 -0
  148. /package/docs/{v7/_drafts → _drafts}/sdk-browser-rendering.mdx +0 -0
  149. /package/docs/{v7/_drafts → _drafts}/sdk-migration.mdx +0 -0
  150. /package/docs/{v7/_drafts → _drafts}/sdk-v7-complete.mdx +0 -0
  151. /package/docs/{v7/_drafts → _drafts}/self-hosting.mdx +0 -0
  152. /package/docs/{v7/_drafts → _drafts}/test-recording.mdx +0 -0
  153. /package/docs/{v7/_drafts → _drafts}/writing-tests.mdx +0 -0
  154. /package/docs/{v7/examples → examples}/ai.mdx +0 -0
  155. /package/docs/{v7/examples → examples}/assert.mdx +0 -0
  156. /package/docs/{v7/examples → examples}/captcha-api.mdx +0 -0
  157. /package/docs/{v7/examples → examples}/chrome-extension.mdx +0 -0
  158. /package/docs/{v7/examples → examples}/drag-and-drop.mdx +0 -0
  159. /package/docs/{v7/examples → examples}/element-not-found.mdx +0 -0
  160. /package/docs/{v7/examples → examples}/findall-coffee-icons.mdx +0 -0
  161. /package/docs/{v7/examples → examples}/formatted-logging.mdx +0 -0
  162. /package/docs/{v7/examples → examples}/hover-image.mdx +0 -0
  163. /package/docs/{v7/examples → examples}/hover-text-with-description.mdx +0 -0
  164. /package/docs/{v7/examples → examples}/hover-text.mdx +0 -0
  165. /package/docs/{v7/examples → examples}/installer.mdx +0 -0
  166. /package/docs/{v7/examples → examples}/launch-vscode-linux.mdx +0 -0
  167. /package/docs/{v7/examples → examples}/match-image.mdx +0 -0
  168. /package/docs/{v7/examples → examples}/parse.mdx +0 -0
  169. /package/docs/{v7/examples → examples}/press-keys.mdx +0 -0
  170. /package/docs/{v7/examples → examples}/scroll-keyboard.mdx +0 -0
  171. /package/docs/{v7/examples → examples}/scroll-until-text.mdx +0 -0
  172. /package/docs/{v7/examples → examples}/scroll.mdx +0 -0
  173. /package/docs/{v7/examples → examples}/type.mdx +0 -0
  174. /package/docs/{v7/mcp.mdx → mcp.mdx} +0 -0
@@ -0,0 +1,423 @@
1
+ ---
2
+ title: "Locating Elements"
3
+ sidebarTitle: "Locating Elements"
4
+ description: "Locate UI elements using AI"
5
+ icon: "mouse-pointer"
6
+ ---
7
+
8
+ ## Overview
9
+
10
+ The TestDriver element finding system uses AI. It finds elements on the screen with natural language descriptions. The `find()` method returns an `Element` object. You can [interact with the object](/interacting-with-your-app).
11
+
12
+ ## Finding Elements
13
+
14
+ ### find()
15
+
16
+ Find an element on the screen with a natural language description.
17
+
18
+ ```javascript
19
+ const element = await testdriver.find(description)
20
+ ```
21
+
22
+ **Parameters:**
23
+ - `description` (string) - A natural language description of the element to find
24
+
25
+ **Returns:** `Promise<Element>` - The Element instance that TestDriver found
26
+
27
+ **Example:**
28
+ ```javascript
29
+ // Find a button
30
+ const submitButton = await testdriver.find('the submit button');
31
+
32
+ // Find an input field with context
33
+ const emailField = await testdriver.find('email input field in the login form');
34
+
35
+ // Find an element by visual characteristics
36
+ const redButton = await testdriver.find('red button in the top right corner');
37
+ ```
38
+
39
+ <Tip>
40
+ Be specific in your descriptions. Include visual details, location context, or nearby text to make the accuracy better.
41
+ </Tip>
42
+
43
+ ## Element Class
44
+
45
+ The `Element` class represents a located (or to-be-located) UI element. It provides methods for interaction and properties for element information. For interaction methods like `click()` and `hover()`, see [Interacting With Your App](/interacting-with-your-app).
46
+
47
+ ### Methods
48
+
49
+ #### found()
50
+
51
+ Check if the element was successfully located.
52
+
53
+ ```javascript
54
+ element.found()
55
+ ```
56
+
57
+ **Returns:** `boolean` - True if element coordinates were found
58
+
59
+ **Example:**
60
+ ```javascript
61
+ const element = await testdriver.find('login button');
62
+ if (element.found()) {
63
+ await element.click();
64
+ } else {
65
+ console.log('Element not found');
66
+ }
67
+ ```
68
+
69
+ #### find()
70
+
71
+ Re-locate the element, optionally with a new description.
72
+
73
+ ```javascript
74
+ await element.find(newDescription)
75
+ ```
76
+
77
+ **Parameters:**
78
+ - `newDescription` (string, optional) - New description to search for
79
+
80
+ **Returns:** `Promise<Element>` - This element instance
81
+
82
+ **Example:**
83
+ ```javascript
84
+ // Re-locate if the UI changed
85
+ const element = await testdriver.find('submit button');
86
+ // ... page updates ...
87
+ await element.find(); // Re-locate with same description
88
+
89
+ // Or update the description
90
+ await element.find('blue submit button'); // Now looking for blue button
91
+ ```
92
+
93
+ ### Properties
94
+
95
+ Element properties provide additional information about located elements. Properties are available after a successful `find()` call.
96
+
97
+ #### coordinates
98
+
99
+ Get the element's coordinates object containing all position information.
100
+
101
+ ```javascript
102
+ const coords = element.getCoordinates()
103
+ // or access directly
104
+ element.coordinates
105
+ ```
106
+
107
+ **Returns:** `Object | null` - Coordinate object with `{ x, y, centerX, centerY }`
108
+
109
+ **Example:**
110
+ ```javascript
111
+ const button = await testdriver.find('submit button');
112
+ const coords = button.coordinates;
113
+
114
+ if (coords) {
115
+ console.log(`Top-left: (${coords.x}, ${coords.y})`);
116
+ console.log(`Center: (${coords.centerX}, ${coords.centerY})`);
117
+ }
118
+ ```
119
+
120
+ #### x, y, centerX, centerY
121
+
122
+ Direct access to coordinate values. Always available after successful `find()`.
123
+
124
+ ```javascript
125
+ element.x // Top-left X coordinate (number)
126
+ element.y // Top-left Y coordinate (number)
127
+ element.centerX // Center X coordinate (number)
128
+ element.centerY // Center Y coordinate (number)
129
+ ```
130
+
131
+ **Example:**
132
+ ```javascript
133
+ const button = await testdriver.find('submit button');
134
+ console.log(`Button at: (${button.x}, ${button.y})`);
135
+ console.log(`Button center: (${button.centerX}, ${button.centerY})`);
136
+
137
+ // Use for custom mouse operations
138
+ await testdriver.click(button.centerX, button.centerY);
139
+ ```
140
+
141
+ #### width, height
142
+
143
+ Element dimensions in pixels. Available when AI detects element bounds.
144
+
145
+ ```javascript
146
+ element.width // Width in pixels (number | null)
147
+ element.height // Height in pixels (number | null)
148
+ ```
149
+
150
+ **Example:**
151
+ ```javascript
152
+ const button = await testdriver.find('submit button');
153
+
154
+ if (button.width && button.height) {
155
+ console.log(`Button size: ${button.width}x${button.height}px`);
156
+
157
+ // Check if button is large enough
158
+ if (button.width < 50) {
159
+ console.warn('Button might be too small');
160
+ }
161
+ }
162
+ ```
163
+
164
+ #### boundingBox
165
+
166
+ Complete bounding box information including position and dimensions.
167
+
168
+ ```javascript
169
+ element.boundingBox
170
+ ```
171
+
172
+ **Returns:** `Object | null` - Bounding box with all dimension data
173
+
174
+ ```typescript
175
+ {
176
+ x: number, // Top-left X
177
+ y: number, // Top-left Y
178
+ width: number, // Width in pixels
179
+ height: number // Height in pixels
180
+ }
181
+ ```
182
+
183
+ **Example:**
184
+ ```javascript
185
+ const element = await testdriver.find('dialog box');
186
+
187
+ if (element.boundingBox) {
188
+ const { x, y, width, height } = element.boundingBox;
189
+ console.log(`Dialog: ${width}x${height} at (${x}, ${y})`);
190
+
191
+ // Calculate if element is in viewport
192
+ const rightEdge = x + width;
193
+ const bottomEdge = y + height;
194
+ console.log(`Element extends to (${rightEdge}, ${bottomEdge})`);
195
+ }
196
+ ```
197
+
198
+ #### screenshot
199
+
200
+ Base64-encoded PNG screenshot of the screen when element was found. Only available in DEBUG mode or when an error occurs.
201
+
202
+ ```javascript
203
+ element.screenshot
204
+ ```
205
+
206
+ **Returns:** `string | null` - Base64-encoded PNG image
207
+
208
+ **Example:**
209
+ ```javascript
210
+ const element = await testdriver.find('error message');
211
+
212
+ if (element.screenshot) {
213
+ // Save screenshot to file
214
+ const fs = require('fs');
215
+ const base64Data = element.screenshot.replace(/^data:image\/\w+;base64,/, '');
216
+ fs.writeFileSync('element-screenshot.png', Buffer.from(base64Data, 'base64'));
217
+ console.log('Screenshot saved');
218
+ }
219
+ ```
220
+
221
+ <Warning>
222
+ Screenshots can be large. They're automatically excluded from error messages to prevent memory issues.
223
+ </Warning>
224
+
225
+ #### text
226
+
227
+ Text content extracted from the element by AI (if available).
228
+
229
+ ```javascript
230
+ element.text
231
+ ```
232
+
233
+ **Returns:** `string | null` - Element's text content
234
+
235
+ **Example:**
236
+ ```javascript
237
+ const message = await testdriver.find('notification message');
238
+
239
+ if (message.text) {
240
+ console.log('Message says:', message.text);
241
+
242
+ // Use text content in assertions
243
+ if (message.text.includes('success')) {
244
+ console.log('Success message detected');
245
+ }
246
+ }
247
+
248
+ // Another example - extracting button label
249
+ const button = await testdriver.find('blue button');
250
+ console.log('Button text:', button.text); // "Submit"
251
+ ```
252
+
253
+ #### label
254
+
255
+ Accessible label or name of the element (if available). Useful for verifying accessibility.
256
+
257
+ ```javascript
258
+ element.label
259
+ ```
260
+
261
+ **Returns:** `string | null` - Accessible label
262
+
263
+ **Example:**
264
+ ```javascript
265
+ const input = await testdriver.find('first input field');
266
+
267
+ if (input.label) {
268
+ console.log('Input label:', input.label); // "Email Address"
269
+ }
270
+ ```
271
+
272
+ #### confidence
273
+
274
+ AI confidence score for the element match (0-1, where 1 is perfect confidence).
275
+
276
+ ```javascript
277
+ element.confidence
278
+ ```
279
+
280
+ **Returns:** `number | null` - Confidence score between 0 and 1
281
+
282
+ **Example:**
283
+ ```javascript
284
+ const element = await testdriver.find('submit button');
285
+
286
+ if (element.confidence !== null) {
287
+ const percentage = (element.confidence * 100).toFixed(1);
288
+ console.log(`Match confidence: ${percentage}%`);
289
+
290
+ if (element.confidence < 0.8) {
291
+ console.warn('⚠️ Low confidence match - element might not be correct');
292
+ } else if (element.confidence > 0.95) {
293
+ console.log('✅ High confidence match');
294
+ }
295
+ }
296
+ ```
297
+
298
+ <Tip>
299
+ Confidence scores below 0.8 may indicate the element description was ambiguous or the wrong element was found.
300
+ </Tip>
301
+
302
+ ### Property Availability
303
+
304
+ | Property | When Available |
305
+ |----------|---------------|
306
+ | `x`, `y`, `centerX`, `centerY` | ✅ Always after successful `find()` |
307
+ | `coordinates` | ✅ Always after successful `find()` |
308
+ | `width`, `height` | ⚠️ When AI detects element bounds |
309
+ | `boundingBox` | ⚠️ When AI detects element bounds |
310
+ | `text` | ⚠️ When AI extracts text content |
311
+ | `label` | ⚠️ When element has accessible label |
312
+ | `confidence` | ✅ Always after AI element finding |
313
+ | `screenshot` | ⚠️ Only in DEBUG mode or on errors |
314
+
315
+ <Note>
316
+ Properties marked with ⚠️ may be `null` depending on what the AI could detect from the screenshot.
317
+ </Note>
318
+
319
+ ## JSON Serialization
320
+
321
+ Element objects can be safely serialized using `JSON.stringify()` for logging, debugging, and data storage. Circular references are automatically removed:
322
+
323
+ ```javascript
324
+ const element = await testdriver.find('login button');
325
+
326
+ // Safe to stringify - no circular reference errors!
327
+ console.log(JSON.stringify(element, null, 2));
328
+ ```
329
+
330
+ **Serialized output includes:**
331
+
332
+ ```json
333
+ {
334
+ "description": "login button",
335
+ "coordinates": { "x": 100, "y": 200, "centerX": 150, "centerY": 225 },
336
+ "found": true,
337
+ "threshold": 0.01,
338
+ "x": 100,
339
+ "y": 200,
340
+ "cache": {
341
+ "hit": true,
342
+ "strategy": "pixel-diff",
343
+ "createdAt": "2025-12-09T10:30:00.000Z",
344
+ "diffPercent": 0.0023,
345
+ "imageUrl": "https://cache.testdriver.ai/..."
346
+ },
347
+ "similarity": 0.98,
348
+ "confidence": 0.95,
349
+ "selector": "button#login",
350
+ "aiResponse": "Found the blue login button in the center of the form..."
351
+ }
352
+ ```
353
+
354
+ **Serialized properties:**
355
+
356
+ | Property | Type | Description |
357
+ |----------|------|-------------|
358
+ | `description` | string | Element search description |
359
+ | `coordinates` | object | Full coordinate object `{x, y, centerX, centerY}` |
360
+ | `found` | boolean | Whether element was located |
361
+ | `threshold` | number | Cache threshold used for this find |
362
+ | `x`, `y` | number | Top-left coordinates |
363
+ | `cache.hit` | boolean | Whether cache was used |
364
+ | `cache.strategy` | string | Cache strategy (e.g., "pixel-diff") |
365
+ | `cache.createdAt` | string | ISO timestamp when cache was created |
366
+ | `cache.diffPercent` | number | Pixel difference from cached image |
367
+ | `cache.imageUrl` | string | URL to cached screenshot |
368
+ | `similarity` | number | Similarity score (0-1) |
369
+ | `confidence` | number | AI confidence score (0-1) |
370
+ | `selector` | string | CSS/XPath selector if available |
371
+ | `aiResponse` | string | AI's explanation of what it found |
372
+
373
+ **Use cases:**
374
+
375
+ ```javascript
376
+ // Debugging element detection
377
+ const element = await testdriver.find('submit button');
378
+ if (!element.found()) {
379
+ console.error('Element not found:', JSON.stringify(element, null, 2));
380
+ }
381
+
382
+ // Logging cache performance
383
+ const data = JSON.parse(JSON.stringify(element));
384
+ if (data.cache.hit) {
385
+ console.log(`Cache hit! Diff: ${(data.cache.diffPercent * 100).toFixed(2)}%`);
386
+ }
387
+
388
+ // Sharing element data across processes
389
+ const elementData = JSON.stringify(element);
390
+ // Send to another process, log to file, etc.
391
+ ```
392
+
393
+ <Tip>
394
+ Use JSON serialization when you need to log element data or when debugging why an element wasn't found. The serialized output excludes large binary data (screenshots) and circular references.
395
+ </Tip>
396
+
397
+ ## Best Practices
398
+
399
+ <AccordionGroup>
400
+ <Accordion title="Be specific with descriptions">
401
+ Include visual details, position context, and nearby text:
402
+
403
+ ```javascript
404
+ // ❌ Too vague
405
+ await testdriver.find('button');
406
+
407
+ // ✅ Specific
408
+ await testdriver.find('blue submit button below the email field');
409
+ ```
410
+ </Accordion>
411
+
412
+ <Accordion title="Check if element was found">
413
+ Always verify elements were located before interacting:
414
+
415
+ ```javascript
416
+ const element = await testdriver.find('submit button');
417
+ if (!element.found()) {
418
+ throw new Error('Submit button not found');
419
+ }
420
+ await element.click();
421
+ ```
422
+ </Accordion>
423
+ </AccordionGroup>
@@ -1,17 +1,17 @@
1
1
  ---
2
- title: "Validate"
3
- sidebarTitle: "Validate"
2
+ title: "Verifying Results"
3
+ sidebarTitle: "Verifying Results"
4
4
  description: "Locate elements and verify app state with AI-powered assertions"
5
5
  icon: "circle-check"
6
6
  ---
7
7
 
8
- Once a test runs, validate that the app did what it should. Validation has two parts: locating the elements you want to check, and making assertions about the state of your app. TestDriver uses AI as a judge, returning a boolean plus reasoning about whether your app is in the expected state.
8
+ After a test runs, make sure that the app did the correct thing. Validation has two parts: to find the elements that you want to check, and to make assertions about the state of your app. TestDriver uses the AI as a judge. It returns a boolean and the reason. This shows if your app is in the correct state.
9
9
 
10
10
  ## Locating Elements
11
11
 
12
12
  ### Locating Single Elements
13
13
 
14
- Use natural language to describe elements. Descriptions should be specific enough to locate the element, but not too-specific that they break with minor UI changes. For example:
14
+ Use natural language to describe elements. A description must be specific enough to find the element. But it must not be so specific that it breaks with small UI changes. For example:
15
15
 
16
16
  ```javascript
17
17
  await testdriver.find('email input field');
@@ -19,11 +19,11 @@ await testdriver.find('first product card in the grid');
19
19
  await testdriver.find('dropdown menu labeled "Country"');
20
20
  ```
21
21
 
22
- <Info>TestDriver will cache found elements for improved performance on subsequent calls. Learn more about [element caching here](/v7/caching).</Info>
22
+ <Info>TestDriver caches the found elements for better performance on later calls. Read more about [element caching here](/caching).</Info>
23
23
 
24
24
  ### Debugging Found Elements
25
25
 
26
- After finding an element, you can inspect its properties for debugging:
26
+ After TestDriver finds an element, you can look at its properties for debug:
27
27
 
28
28
  ```javascript
29
29
  const button = await testdriver.find('submit button');
@@ -104,6 +104,6 @@ await testdriver.assert('form has red border');
104
104
 
105
105
  ## Next
106
106
 
107
- <Card title="Adapt" icon="arrows-rotate" href="/v7/performing-actions">
107
+ <Card title="Adapt" icon="arrows-rotate" href="/performing-actions">
108
108
  Drive your app forward by performing actions on the elements you've located and validated.
109
109
  </Card>
@@ -6,7 +6,7 @@ icon: "arrow-pointer"
6
6
 
7
7
  ## Overview
8
8
 
9
- The `mouseDown()` method presses the mouse button at an element's location without releasing it. This is useful for drag operations, custom gestures, or when you need precise control over mouse events. You can either call it on an [`Element`](/v7/core-concepts/elements) instance or use it directly with a selector.
9
+ The `mouseDown()` method pushes the mouse button at the location of an element. It does not release the button. Use this for drag operations, custom gestures, or when you need precise control of the mouse events. You can call it on an [`Element`](/core-concepts/elements) instance. Or you can use it with a selector.
10
10
 
11
11
  ## Syntax
12
12
 
@@ -30,7 +30,7 @@ When called directly on the AI client:
30
30
 
31
31
  ## Returns
32
32
 
33
- Returns a `Promise<void>` that resolves when the mouse button is pressed.
33
+ It returns a `Promise<void>`. The promise resolves when TestDriver pushes the mouse button.
34
34
 
35
35
  ## Examples
36
36
 
@@ -147,15 +147,15 @@ test('resizes panel', async () => {
147
147
 
148
148
  ## Important Notes
149
149
 
150
- - Always pair `mouseDown()` with [`mouseUp()`](/v7/mouse-up) to complete the gesture
150
+ - Always pair `mouseDown()` with [`mouseUp()`](/mouse-up) to complete the gesture
151
151
  - The mouse button remains pressed until `mouseUp()` is called
152
- - Use [`hover()`](/v7/hover) to move the mouse while the button is pressed
152
+ - Use [`hover()`](/hover) to move the mouse while the button is pressed
153
153
  - For simple drag operations, consider using `ai()` with a natural language description like `"drag file to folder"`
154
154
 
155
155
  ## Related Methods
156
156
 
157
- - [`mouseUp()`](/v7/mouse-up) - Release the mouse button
158
- - [`hover()`](/v7/hover) - Move mouse to element
159
- - [`click()`](/v7/click) - Full click (mouseDown + mouseUp)
160
- - [`doubleClick()`](/v7/double-click) - Double-click on element
161
- - [`rightClick()`](/v7/right-click) - Right-click for context menu
157
+ - [`mouseUp()`](/mouse-up) - Release the mouse button
158
+ - [`hover()`](/hover) - Move mouse to element
159
+ - [`click()`](/click) - Full click (mouseDown + mouseUp)
160
+ - [`doubleClick()`](/double-click) - Double-click on element
161
+ - [`rightClick()`](/right-click) - Right-click for context menu
@@ -6,7 +6,7 @@ icon: "arrow-pointer"
6
6
 
7
7
  ## Overview
8
8
 
9
- The `mouseUp()` method releases the mouse button, completing a drag operation or custom mouse gesture that was started with [`mouseDown()`](/v7/mouse-down). You can call it without parameters to release at the current mouse position.
9
+ The `mouseUp()` method releases the mouse button. It completes a drag operation or a custom mouse gesture that you started with [`mouseDown()`](/mouse-down). Call it without parameters to release the button at the present mouse position.
10
10
 
11
11
  ## Syntax
12
12
 
@@ -21,7 +21,7 @@ None. The mouse button is released at the current cursor position.
21
21
 
22
22
  ## Returns
23
23
 
24
- Returns a `Promise<void>` that resolves when the mouse button is released.
24
+ It returns a `Promise<void>`. The promise resolves when TestDriver releases the mouse button.
25
25
 
26
26
  ## Examples
27
27
 
@@ -150,15 +150,15 @@ test('selects text with mouse drag', async () => {
150
150
 
151
151
  ## Important Notes
152
152
 
153
- - `mouseUp()` must be preceded by [`mouseDown()`](/v7/mouse-down) to have an effect
153
+ - `mouseUp()` must be preceded by [`mouseDown()`](/mouse-down) to have an effect
154
154
  - Releases the button at the current cursor position
155
155
  - Completes any drag or selection operation that was in progress
156
- - For simple clicks, use [`click()`](/v7/click) instead of mouseDown/mouseUp pair
156
+ - For simple clicks, use [`click()`](/click) instead of mouseDown/mouseUp pair
157
157
 
158
158
  ## Related Methods
159
159
 
160
- - [`mouseDown()`](/v7/mouse-down) - Press mouse button without releasing
161
- - [`hover()`](/v7/hover) - Move mouse to element
162
- - [`click()`](/v7/click) - Complete click (mouseDown + mouseUp)
163
- - [`doubleClick()`](/v7/double-click) - Double-click on element
164
- - [`rightClick()`](/v7/right-click) - Right-click for context menu
160
+ - [`mouseDown()`](/mouse-down) - Press mouse button without releasing
161
+ - [`hover()`](/hover) - Move mouse to element
162
+ - [`click()`](/click) - Complete click (mouseDown + mouseUp)
163
+ - [`doubleClick()`](/double-click) - Double-click on element
164
+ - [`rightClick()`](/right-click) - Right-click for context menu