testdriverai 7.8.0-test.7 → 7.8.0-test.71

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 (98) hide show
  1. package/agent/index.js +18 -5
  2. package/agent/lib/commands.js +3 -2
  3. package/agent/lib/http.js +162 -0
  4. package/agent/lib/logger.js +15 -0
  5. package/agent/lib/sandbox.js +554 -209
  6. package/agent/lib/sdk.js +5 -22
  7. package/agent/lib/system.js +25 -65
  8. package/ai/skills/testdriver-cache/SKILL.md +221 -0
  9. package/ai/skills/testdriver-errors/SKILL.md +246 -0
  10. package/ai/skills/testdriver-events/SKILL.md +356 -0
  11. package/ai/skills/testdriver-find/SKILL.md +14 -20
  12. package/ai/skills/testdriver-mcp/SKILL.md +7 -0
  13. package/ai/skills/testdriver-provision/SKILL.md +331 -0
  14. package/ai/skills/testdriver-redraw/SKILL.md +214 -0
  15. package/ai/skills/testdriver-running-tests/SKILL.md +1 -1
  16. package/ai/skills/testdriver-screenshots/SKILL.md +184 -0
  17. package/docs/_data/examples-manifest.json +46 -46
  18. package/docs/_scripts/extract-example-urls.js +67 -72
  19. package/docs/changelog.mdx +148 -8
  20. package/docs/docs.json +46 -38
  21. package/docs/images/content/vscode/v7-chat.png +0 -0
  22. package/docs/images/content/vscode/v7-choose-agent.png +0 -0
  23. package/docs/images/content/vscode/v7-full.png +0 -0
  24. package/docs/images/content/vscode/v7-onboarding.png +0 -0
  25. package/docs/v7/cache.mdx +223 -0
  26. package/docs/v7/copilot/auto-healing.mdx +265 -0
  27. package/docs/v7/copilot/creating-tests.mdx +156 -0
  28. package/docs/v7/copilot/github.mdx +143 -0
  29. package/docs/v7/copilot/running-tests.mdx +149 -0
  30. package/docs/v7/copilot/setup.mdx +143 -0
  31. package/docs/v7/enterprise.mdx +3 -110
  32. package/docs/v7/errors.mdx +248 -0
  33. package/docs/v7/events.mdx +358 -0
  34. package/docs/v7/examples/ai.mdx +1 -1
  35. package/docs/v7/examples/assert.mdx +1 -1
  36. package/docs/v7/examples/captcha-api.mdx +1 -1
  37. package/docs/v7/examples/chrome-extension.mdx +1 -1
  38. package/docs/v7/examples/drag-and-drop.mdx +1 -1
  39. package/docs/v7/examples/element-not-found.mdx +1 -1
  40. package/docs/v7/examples/exec-output.mdx +85 -0
  41. package/docs/v7/examples/exec-pwsh.mdx +83 -0
  42. package/docs/v7/examples/focus-window.mdx +62 -0
  43. package/docs/v7/examples/hover-image.mdx +1 -1
  44. package/docs/v7/examples/hover-text.mdx +1 -1
  45. package/docs/v7/examples/installer.mdx +1 -1
  46. package/docs/v7/examples/launch-vscode-linux.mdx +1 -1
  47. package/docs/v7/examples/match-image.mdx +1 -1
  48. package/docs/v7/examples/press-keys.mdx +1 -1
  49. package/docs/v7/examples/scroll-keyboard.mdx +1 -1
  50. package/docs/v7/examples/scroll-until-image.mdx +1 -1
  51. package/docs/v7/examples/scroll-until-text.mdx +1 -1
  52. package/docs/v7/examples/scroll.mdx +1 -1
  53. package/docs/v7/examples/type.mdx +1 -1
  54. package/docs/v7/examples/windows-installer.mdx +1 -1
  55. package/docs/v7/find.mdx +14 -20
  56. package/docs/v7/{cloud.mdx → hosted.mdx} +43 -5
  57. package/docs/v7/mcp.mdx +9 -0
  58. package/docs/v7/provision.mdx +333 -0
  59. package/docs/v7/quickstart.mdx +30 -2
  60. package/docs/v7/redraw.mdx +216 -0
  61. package/docs/v7/running-tests.mdx +1 -1
  62. package/docs/v7/screenshots.mdx +186 -0
  63. package/docs/v7/self-hosted.mdx +127 -44
  64. package/docs/v7/test-results-json.mdx +258 -0
  65. package/examples/scroll-keyboard.test.mjs +1 -1
  66. package/examples/scroll.test.mjs +1 -12
  67. package/interfaces/logger.js +0 -12
  68. package/interfaces/vitest-plugin.mjs +170 -51
  69. package/lib/core/Dashcam.js +30 -23
  70. package/lib/environments.json +22 -0
  71. package/lib/github-comment.mjs +58 -40
  72. package/lib/init-project.js +5 -67
  73. package/lib/resolve-channel.js +42 -12
  74. package/lib/sentry.js +47 -23
  75. package/lib/vitest/hooks.mjs +63 -3
  76. package/{examples → manual}/drag-and-drop.test.mjs +1 -1
  77. package/manual/exec-stream-logs.test.mjs +25 -0
  78. package/mcp-server/dist/server.mjs +28 -8
  79. package/mcp-server/src/server.ts +31 -8
  80. package/package.json +4 -3
  81. package/sdk.d.ts +4 -0
  82. package/sdk.js +45 -15
  83. package/setup/aws/install-dev-runner.sh +79 -0
  84. package/setup/aws/spawn-runner.sh +165 -0
  85. package/test-sentry-span.js +35 -0
  86. package/vitest.config.mjs +22 -34
  87. package/vitest.runner.config.mjs +33 -0
  88. /package/{examples → manual}/flake-diffthreshold-001.test.mjs +0 -0
  89. /package/{examples → manual}/flake-diffthreshold-01.test.mjs +0 -0
  90. /package/{examples → manual}/flake-diffthreshold-05.test.mjs +0 -0
  91. /package/{examples → manual}/flake-noredraw-cache.test.mjs +0 -0
  92. /package/{examples → manual}/flake-noredraw-nocache.test.mjs +0 -0
  93. /package/{examples → manual}/flake-redraw-cache.test.mjs +0 -0
  94. /package/{examples → manual}/flake-redraw-nocache.test.mjs +0 -0
  95. /package/{examples → manual}/flake-rocket-match.test.mjs +0 -0
  96. /package/{examples → manual}/flake-shared.mjs +0 -0
  97. /package/{examples → manual}/no-provision.test.mjs +0 -0
  98. /package/{examples → manual}/scroll-until-text.test.mjs +0 -0
@@ -2,20 +2,160 @@
2
2
  title: "Changelog"
3
3
  description: "Product updates and announcements"
4
4
  rss: true
5
+ icon: "code-compare"
5
6
  ---
6
7
 
7
- {/* New entries are prepended automatically by the release workflow. */}
8
- {/* Do not remove the CHANGELOG_MARKER comment below — the CI script inserts new <Update> blocks after it. */}
9
- {/* CHANGELOG_MARKER */}
10
- <Update label="v7.8.0-test.7" description="March 2026" tags={["test"]}>
11
- 🔧 Maintenance
8
+ <Update label="v7.8.0-test.22" description="March 2026" tags={["test"]}>
9
+
10
+ Releases test.11 through test.22 include version bumps and internal CI improvements across all packages. No new user-facing changes — see [v7.8.0-test.10](#v780-test10) for the latest updates in this release stream.
11
+
12
+ </Update>
13
+
14
+ <Update label="v7.8.0-test.10" description="March 2026" tags={["test"]}>
15
+
16
+ 🔧 Improvements
17
+
18
+ - **Parallel test concurrency** — Concurrency limits are now enforced with atomic slot tracking, eliminating a race condition where multiple tests launching at the same time could all bypass the limit. If you hit your concurrency cap, the SDK waits and retries automatically.
19
+ - **Dashboard access for all plans** — Test recordings and metrics on the [dashboard](https://console.testdriver.ai) are now visible to all users, including those on the Free plan.
20
+ - **Sandbox message throttling** — High-frequency interactions no longer risk hitting connection limits. The SDK automatically paces outgoing messages during fast command sequences.
21
+ - **Windows Dashcam stability** — Web log tracking on Windows sandboxes now handles errors gracefully instead of failing the test.
22
+
23
+ </Update>
24
+
25
+ <Update label="v7.8.0-test.9" description="March 2026" tags={["test"]}>
26
+
27
+ 🔧 Improvements
28
+
29
+ - **Stable release promotion** — Fixed an issue where promoting a test or canary release to stable could be incorrectly skipped. Stable releases now proceed reliably regardless of the prior pre-release channel.
30
+ - **Example docs sync** — Example documentation now updates more reliably, continuing even when individual example tests fail so that passing examples still get refreshed.
31
+
32
+ </Update>
33
+
34
+ <Update label="v7.8.0-test.8" description="March 2026" tags={["test"]}>
35
+
36
+ 🔧 Improvements
12
37
 
13
- - Fix version bump syntax in release workflow [f3ac61dc]
38
+ - **VS Code environment switching** The TestDriver VS Code extension now includes a status bar indicator and a new **TestDriver: Switch Environment** command. You can switch between stable, canary, and test environments directly from VS Code, and your MCP server configuration updates automatically.
39
+ - **Plan rename: Starter → Pro** — The "Starter" plan has been renamed to **Pro**. No changes to pricing or features — just a clearer name. The "Self-Hosted" tier is now labeled **Enterprise**.
40
+ - **SDK network resilience** — API requests now automatically retry on transient server errors (500, 502, 503, 504) with exponential backoff, reducing flaky test failures caused by brief infrastructure hiccups.
41
+ - **Pricing page refresh** — The [hosted plans page](/v7/hosted) now shows plan cards with included minutes, concurrency limits, and pricing at a glance.
42
+
43
+ 📚 Docs updates
44
+
45
+ - **Quickstart redesign** — The [quickstart](/v7/quickstart) now has tabbed setup paths for CLI, GitHub Copilot, and manual installation.
46
+ - **Deployment section** — "Cloud" is now [Hosted](/v7/hosted) and the previous Enterprise page has been consolidated into [Self-Hosted](/v7/self-hosted), which covers both standard and air-gapped deployments.
47
+
48
+ </Update>
49
+
50
+ <Update label="v7.8.0-test.7" description="March 2026" tags={["test"]}>
51
+ This release includes all changes from v7.8.0-test.6 with version bumps across all packages. No additional user-facing changes.
14
52
  </Update>
15
53
 
16
54
  <Update label="v7.8.0-test.6" description="March 2026" tags={["test"]}>
17
- 🔧 Maintenance
18
55
 
19
- - Fix changelog generation in release workflow (04a789ec)
56
+ 🔧 Improvements
57
+
58
+ - **Sandbox spawning reliability** — Sandbox creation now uses a 3-minute timeout to handle slow infrastructure, then immediately switches to a 60-second orphan timeout for fast cleanup. This reduces sandbox creation failures during high-traffic periods.
59
+ - **Command deadline timeouts** — Sandbox commands now enforce a hard deadline that terminates execution if the connection drops mid-command, preventing tests from hanging indefinitely.
60
+ - **Real-time channel cleanup** — Fixed a compatibility issue with the real-time messaging layer that could cause channel cleanup to fail during shutdown.
61
+ - **Dashboard timestamp tooltips** — Extended UTC date tooltips to the test history sidebar. Hovering over any relative timestamp (e.g., "5 minutes ago") across the [dashboard](https://console.testdriver.ai) now shows the full UTC date and time.
62
+
63
+ </Update>
64
+
65
+ <Update label="v7.8.0-test.4" description="March 2026" tags={["test"]}>
66
+
67
+ ✨ New features
68
+
69
+ - **[GitHub Copilot integration](/v7/copilot/setup)** — Use TestDriver directly from GitHub Copilot in VS Code. The new MCP server lets Copilot launch sandboxes, interact with elements, and run assertions through natural language. Includes guides for [creating tests](/v7/copilot/creating-tests), [running tests](/v7/copilot/running-tests), [GitHub Actions integration](/v7/copilot/github), and [auto-healing](/v7/copilot/auto-healing).
70
+
71
+ 🔧 Improvements
72
+
73
+ - **Sandbox reliability** — Linux sandboxes now use a longer creation timeout to handle slow infrastructure, then immediately switch to a short orphan timeout for fast cleanup of disconnected sessions.
74
+ - **Command execution timeouts** — Sandbox commands now have deadline timeouts that prevent hangs if the connection drops mid-execution.
75
+ - **Real-time connection stability** — Updated the real-time messaging layer for better compatibility and more reliable channel cleanup during shutdown.
76
+ - **Dashboard date display** — Hovering over relative timestamps (e.g., "5 minutes ago") now shows the full UTC date and time.
77
+
78
+ </Update>
79
+
80
+ <Update label="v7.8.0-canary.5" description="March 2026" tags={["canary"]}>
81
+ This release includes all changes from v7.8.0-canary.4 with version bumps.
82
+
83
+ ✨ New features
84
+
85
+ - **[Cache API](/v7/cache)** — Speed up repeated test runs with screenshot-based caching. The system compares screenshots to cached results and reuses element positions when the screen hasn't changed, reducing AI calls.
86
+ - **[Custom error classes](/v7/errors)** — New `ElementNotFoundError` and `AIError` classes with rich debugging info including screenshot paths, pixel diffs, and detailed messages.
87
+ - **[Events system](/v7/events)** — Listen to SDK lifecycle events with wildcard support via `testdriver.emitter`. Uses colon-delimited namespaces (e.g., `command:start`, `log:*`).
88
+ - **[Provision API](/v7/provision)** — Launch browsers, desktop apps, VS Code, and Chrome extensions in your sandbox before tests run. Access via `testdriver.provision.*`.
89
+ - **[Redraw detection](/v7/redraw)** — Wait for screens to stabilize after interactions using two-phase detection with pixel comparison and z-score analysis.
90
+ - **[Screenshots API](/v7/screenshots)** — Capture screenshots manually with `testdriver.screenshot()` or automatically before/after every command.
91
+
92
+ 📚 New examples
93
+
94
+ - [Exec output](/v7/examples/exec-output) — Capture and use output from PowerShell commands
95
+ - [Exec PowerShell](/v7/examples/exec-pwsh) — Generate dynamic data with PowerShell
96
+ - [Focus window](/v7/examples/focus-window) — Switch focus between application windows
97
+
98
+ 🔧 Improvements
99
+
100
+ - Improved console URL mapping for canary and test environments
101
+ - Enhanced Ably channel cleanup for better resource management
102
+ - Updated release workflow with improved changelog generation
103
+ </Update>
104
+
105
+ <Update label="v7.5.26" description="March 2026" tags={["stable"]}>
106
+ 🚀 Stable release
107
+
108
+ This release promotes v7.5.25 to stable with deployment channel improvements.
109
+
110
+ ✨ Features
111
+
112
+ - **Deployment channels** — SDK now supports stable and canary release channels. Stable releases use the `latest` npm tag, while canary releases use the `canary` tag. Install canary with `npm install testdriverai@canary`.
113
+
114
+ 🔧 Improvements
115
+
116
+ - Improved cache hit debugging and logging
117
+ - Enhanced element location reliability
118
+ - Better error handling during test execution
119
+
120
+ 🐛 Bug fixes
121
+
122
+ - Fixed restart behavior during auto-updates
123
+ - Fixed console URL routing for various environments
124
+
125
+ <Note>
126
+ This release includes changes from v7.5.17 through v7.5.25.
127
+ </Note>
128
+ </Update>
129
+
130
+ <Update label="v7.5.25" description="March 2026" tags={["stable"]}>
131
+ 🐛 Bug fixes
132
+
133
+ - Fixed restart update behavior
134
+ </Update>
135
+
136
+ <Update label="v7.5.24" description="March 2026" tags={["stable"]}>
137
+ 🔧 Improvements
138
+
139
+ - Disabled auto-update restart to improve CI stability
140
+ </Update>
141
+
142
+ <Update label="v7.5.22" description="March 2026" tags={["stable"]}>
143
+ 🔧 Improvements
144
+
145
+ - Added markdown-to-HTML rendering for marketing content
146
+ </Update>
147
+
148
+ <Update label="v7.5.19" description="March 2026" tags={["stable"]}>
149
+ 🔧 Improvements
150
+
151
+ - Enhanced debugging output for cache hits
152
+ - Improved element location reliability
153
+ </Update>
154
+
155
+ <Update label="v7.5.17" description="March 2026" tags={["stable"]}>
156
+ 🔧 Improvements
157
+
158
+ - Improved codespace scaling and development environment setup
159
+ - Updated VS Code extension version
20
160
  </Update>
21
161
 
package/docs/docs.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "$schema": "https://mintlify.com/docs.json",
3
- "theme": "palm",
3
+ "theme": "almond",
4
4
  "name": "TestDriver",
5
5
  "colors": {
6
6
  "primary": "#b3d334",
@@ -48,19 +48,31 @@
48
48
  "/v7/examples/windows-installer"
49
49
  ]
50
50
  },
51
+
51
52
  {
52
- "group": "Plans & Pricing",
53
+ "group": "Deployment",
53
54
  "icon": "server",
54
55
  "pages": [
55
- "/v7/cloud",
56
- "/v7/self-hosted",
57
- "/v7/enterprise"
56
+ "/v7/hosted",
57
+ "/v7/self-hosted"
58
58
  ]
59
- }
59
+ },
60
+ "/changelog"
61
+ ]
62
+ },
63
+
64
+ {
65
+ "group": "GitHub Copilot",
66
+ "pages": [
67
+ "/v7/copilot/setup",
68
+ "/v7/copilot/creating-tests",
69
+ "/v7/copilot/running-tests",
70
+ "/v7/copilot/github",
71
+ "/v7/copilot/auto-healing"
60
72
  ]
61
73
  },
62
74
  {
63
- "group": "Creating Tests",
75
+ "group": "Guide",
64
76
  "pages": [
65
77
  "/v7/generating-tests",
66
78
  "/v7/device-config",
@@ -75,7 +87,8 @@
75
87
  "pages": [
76
88
  "/v7/running-tests",
77
89
  "/v7/caching",
78
- "/v7/ci-cd"
90
+ "/v7/ci-cd",
91
+ "/v7/test-results-json"
79
92
  ]
80
93
  },
81
94
  {
@@ -94,40 +107,35 @@
94
107
  ]
95
108
  },
96
109
  {
97
- "group": "Actions",
98
- "pages": [
99
- "/v7/ai",
100
- "/v7/assert",
101
- "/v7/captcha",
102
- "/v7/click",
103
- "/v7/double-click",
104
- "/v7/exec",
105
- "/v7/find",
106
- "/v7/focus-application",
107
- "/v7/hover",
108
- "/v7/mouse-down",
109
- "/v7/mouse-up",
110
- "/v7/parse",
111
- "/v7/press-keys",
112
- "/v7/right-click",
113
- "/v7/screenshot",
114
- "/v7/type",
115
- "/v7/scroll"
116
- ]
117
- },
118
- {
119
- "group": "SDK",
110
+ "group": "SDK Reference",
120
111
  "pages": [
121
- "/v7/elements",
122
112
  "/v7/client",
113
+ "/v7/elements",
114
+ {
115
+ "group": "Actions",
116
+ "icon": "bolt",
117
+ "pages": [
118
+ "/v7/ai",
119
+ "/v7/assert",
120
+ "/v7/captcha",
121
+ "/v7/click",
122
+ "/v7/double-click",
123
+ "/v7/exec",
124
+ "/v7/find",
125
+ "/v7/focus-application",
126
+ "/v7/hover",
127
+ "/v7/mouse-down",
128
+ "/v7/mouse-up",
129
+ "/v7/parse",
130
+ "/v7/press-keys",
131
+ "/v7/right-click",
132
+ "/v7/screenshot",
133
+ "/v7/scroll",
134
+ "/v7/type"
135
+ ]
136
+ },
123
137
  "/v7/dashcam"
124
138
  ]
125
- },
126
- {
127
- "group": "",
128
- "pages": [
129
- "/changelog"
130
- ]
131
139
  }
132
140
  ]
133
141
  },
@@ -0,0 +1,223 @@
1
+ ---
2
+ title: "Cache"
3
+ sidebarTitle: "Cache"
4
+ description: "Speed up tests with screenshot-based caching"
5
+ icon: "bolt-lightning"
6
+ mode: "wide"
7
+ ---
8
+
9
+ ## Overview
10
+
11
+ The cache system speeds up repeated test runs by comparing screenshots to cached results. When the screen hasn't changed significantly, cached element positions are reused instead of making an AI call.
12
+
13
+ Cache works at two levels:
14
+ - **Screen cache** — pixel diff comparison between the current screenshot and the cached screenshot
15
+ - **Element cache** — OpenCV template matching to verify the cached element position is still correct
16
+
17
+ ## How It Works
18
+
19
+ 1. On `find()`, the SDK sends the current screenshot and cache metadata to the API
20
+ 2. The API compares the screenshot against previously cached results for the same `cacheKey`
21
+ 3. If the screen pixel diff is within the `screen` threshold AND the element template match exceeds the `element` threshold, the cached position is returned
22
+ 4. Otherwise, a new AI call is made and the result is cached
23
+
24
+ ```mermaid
25
+ flowchart LR
26
+ A[Screenshot + cacheKey] --> B{Screen Diff\n< threshold?}
27
+ B -- Yes --> C{Template\nMatch OK?}
28
+ C -- Yes --> D[Return cached position]
29
+ B -- No --> E[AI Call - fresh]
30
+ C -- No --> F[AI Call - fresh]
31
+ ```
32
+
33
+ ## Configuration
34
+
35
+ ### Constructor Options
36
+
37
+ ```javascript
38
+ const testdriver = new TestDriver({
39
+ cache: {
40
+ enabled: true,
41
+ thresholds: {
42
+ find: {
43
+ screen: 0.05, // 5% pixel diff allowed (default)
44
+ element: 0.8, // 80% OpenCV correlation required (default)
45
+ },
46
+ assert: 0.05, // 5% pixel diff for assertions (default)
47
+ },
48
+ },
49
+ cacheKey: 'my-custom-key', // overrides auto-generated key
50
+ });
51
+ ```
52
+
53
+ <ParamField path="cache" type="CacheConfig | false">
54
+ Cache configuration object, or `false` to disable entirely.
55
+
56
+ <Expandable title="properties">
57
+ <ParamField path="enabled" type="boolean" default={true}>
58
+ Enable or disable the cache system. Requires a valid `cacheKey` to actually activate.
59
+ </ParamField>
60
+
61
+ <ParamField path="thresholds" type="CacheThresholds">
62
+ Threshold configuration for different command types.
63
+
64
+ <Expandable title="properties">
65
+ <ParamField path="find" type="FindCacheThresholds">
66
+ Thresholds for `find()` and `findAll()`.
67
+
68
+ <Expandable title="properties">
69
+ <ParamField path="screen" type="number" default={0.05}>
70
+ Maximum pixel diff percentage allowed between the current screenshot and the cached screenshot. Lower values require a closer match. Range: `0` to `1`.
71
+ </ParamField>
72
+
73
+ <ParamField path="element" type="number" default={0.8}>
74
+ Minimum OpenCV template matching correlation required for the cached element crop. Higher values require a closer match. Range: `0` to `1`. Only used for `find()`, not `findAll()`.
75
+ </ParamField>
76
+ </Expandable>
77
+ </ParamField>
78
+
79
+ <ParamField path="assert" type="number" default={0.05}>
80
+ Maximum pixel diff allowed for assertion cache hits.
81
+ </ParamField>
82
+ </Expandable>
83
+ </ParamField>
84
+ </Expandable>
85
+ </ParamField>
86
+
87
+ <ParamField path="cacheKey" type="string">
88
+ Unique key for cache lookups. If not provided, an auto-generated key is created from a SHA-256 hash of the calling test file (first 16 hex characters). The cache key changes automatically when your test file changes, providing automatic cache invalidation.
89
+ </ParamField>
90
+
91
+ ### Disabling Cache
92
+
93
+ ```javascript
94
+ // Via constructor
95
+ const testdriver = new TestDriver({ cache: false });
96
+
97
+ // Via environment variable
98
+ // TD_NO_CACHE=true npx vitest run
99
+ ```
100
+
101
+ When cache is disabled, all thresholds are set to `-1` internally, causing the API to skip cache lookups.
102
+
103
+ ### Per-Command Overrides
104
+
105
+ Override cache thresholds for individual commands:
106
+
107
+ ```javascript
108
+ // Stricter screen matching for this specific find
109
+ const el = await testdriver.find('submit button', {
110
+ cache: {
111
+ thresholds: { screen: 0.01, element: 0.95 },
112
+ },
113
+ });
114
+
115
+ // Custom cache key for a specific assertion
116
+ await testdriver.assert('dashboard loaded', {
117
+ cache: { threshold: 0.01 },
118
+ cacheKey: 'dashboard-check',
119
+ });
120
+ ```
121
+
122
+ ## Threshold Priority
123
+
124
+ Thresholds are resolved in priority order (highest wins):
125
+
126
+ | Priority | Source | Example |
127
+ |----------|--------|---------|
128
+ | 1 (highest) | Per-command option | `find(desc, { cache: { thresholds: { screen: 0.1 } } })` |
129
+ | 2 | Legacy number argument | `find(desc, 0.1)` |
130
+ | 3 | Global constructor config | `new TestDriver({ cache: { thresholds: { find: { screen: 0.1 } } } })` |
131
+ | 4 (lowest) | Hard-coded defaults | `screen: 0.05`, `element: 0.8`, `assert: 0.05` |
132
+
133
+ ## Auto-Generated Cache Key
134
+
135
+ When you don't specify a `cacheKey`, the SDK automatically generates one:
136
+
137
+ 1. Walks the call stack to find your test file
138
+ 2. Reads the file content
139
+ 3. Computes a **SHA-256 hash** of the content
140
+ 4. Uses the **first 16 hex characters** as the cache key
141
+
142
+ This means:
143
+ - **Same test file** → same cache key → cache hits
144
+ - **Modified test file** → different hash → automatic cache invalidation
145
+ - **Different test files** → different keys → isolated caches
146
+
147
+ ```javascript
148
+ // Auto-generated cache key from test file hash
149
+ const testdriver = new TestDriver();
150
+ // cacheKey = "a3f2b1c4d5e6f7a8" (auto)
151
+
152
+ // Manual override
153
+ const testdriver = new TestDriver({ cacheKey: 'login-test-v2' });
154
+ ```
155
+
156
+ ## Template Matching (OpenCV)
157
+
158
+ Element cache validation uses OpenCV's normalized cross-correlation coefficient (`TM_CCOEFF_NORMED`) to verify that the cached element is still visible at the expected position.
159
+
160
+ **Algorithm:**
161
+ 1. Load the cached element crop (needle) and current screenshot (haystack)
162
+ 2. Run `cv.matchTemplate()` with `TM_CCOEFF_NORMED`
163
+ 3. Binary threshold at the configured element threshold
164
+ 4. Find contours to extract match positions
165
+ 5. Return matches with `{ x, y, width, height, centerX, centerY }`
166
+
167
+ **Scale factors tried:** `[1, 0.5, 2, 0.75, 1.25, 1.5]`
168
+ **Thresholds tried:** `[0.9, 0.8, 0.7]` (picks highest matching threshold)
169
+
170
+ This accounts for minor scaling differences between screenshots taken at different times or resolutions.
171
+
172
+ ## Cache Partitioning
173
+
174
+ Cache entries are partitioned by:
175
+ - **`cacheKey`** — identifies the test file
176
+ - **`os`** — operating system (linux, windows, darwin)
177
+ - **`resolution`** — screen resolution
178
+
179
+ This means cache from a Linux run won't be used for a Windows run, even with the same cache key.
180
+
181
+ ## Debugging Cache
182
+
183
+ API responses include cache metadata:
184
+
185
+ | Field | Description |
186
+ |---|---|
187
+ | `cacheHit` | `true` if cache was used |
188
+ | `similarity` | Pixel diff percentage between screenshots |
189
+ | `cacheSimilarity` | OpenCV template match score |
190
+
191
+ Use `getDebugInfo()` on an element to inspect cache results:
192
+
193
+ ```javascript
194
+ const el = await testdriver.find('submit button');
195
+ const debug = el.getDebugInfo();
196
+ console.log(debug);
197
+ // { cacheHit: true, similarity: 0.02, cacheSimilarity: 0.92, ... }
198
+ ```
199
+
200
+ ## Types
201
+
202
+ ```typescript
203
+ interface CacheConfig {
204
+ enabled?: boolean; // Default: true
205
+ thresholds?: CacheThresholds;
206
+ }
207
+
208
+ interface CacheThresholds {
209
+ find?: FindCacheThresholds;
210
+ assert?: number; // Default: 0.05
211
+ }
212
+
213
+ interface FindCacheThresholds {
214
+ screen?: number; // Default: 0.05
215
+ element?: number; // Default: 0.8
216
+ }
217
+
218
+ interface CacheDebugInfo {
219
+ cacheHit: boolean;
220
+ similarity: number;
221
+ cacheSimilarity: number;
222
+ }
223
+ ```