@testmuai/playwright-bindings 0.1.26 → 0.1.27

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 (154) hide show
  1. package/dist/actionEngine.d.ts +37 -0
  2. package/dist/actionEngine.d.ts.map +1 -0
  3. package/dist/actionEngine.js +194 -0
  4. package/dist/actionEngine.js.map +1 -0
  5. package/dist/actionSpecs.d.ts +35 -0
  6. package/dist/actionSpecs.d.ts.map +1 -0
  7. package/dist/actionSpecs.js +354 -0
  8. package/dist/actionSpecs.js.map +1 -0
  9. package/dist/capability.d.ts +3 -5
  10. package/dist/capability.d.ts.map +1 -1
  11. package/dist/capability.js +66 -6
  12. package/dist/capability.js.map +1 -1
  13. package/dist/configure.d.ts +16 -0
  14. package/dist/configure.d.ts.map +1 -1
  15. package/dist/configure.js +14 -0
  16. package/dist/configure.js.map +1 -1
  17. package/dist/errors.d.ts +19 -0
  18. package/dist/errors.d.ts.map +1 -1
  19. package/dist/errors.js +29 -0
  20. package/dist/errors.js.map +1 -1
  21. package/dist/healCache.d.ts +28 -0
  22. package/dist/healCache.d.ts.map +1 -0
  23. package/dist/healCache.js +17 -0
  24. package/dist/healCache.js.map +1 -0
  25. package/dist/healPatch.d.ts.map +1 -1
  26. package/dist/healPatch.js +45 -3
  27. package/dist/healPatch.js.map +1 -1
  28. package/dist/helpers/assertion.d.ts.map +1 -1
  29. package/dist/helpers/assertion.js +18 -0
  30. package/dist/helpers/assertion.js.map +1 -1
  31. package/dist/helpers/assertionV3.d.ts +67 -0
  32. package/dist/helpers/assertionV3.d.ts.map +1 -0
  33. package/dist/helpers/assertionV3.js +384 -0
  34. package/dist/helpers/assertionV3.js.map +1 -0
  35. package/dist/helpers/condition.d.ts +84 -0
  36. package/dist/helpers/condition.d.ts.map +1 -0
  37. package/dist/helpers/condition.js +292 -0
  38. package/dist/helpers/condition.js.map +1 -0
  39. package/dist/helpers/cookies.d.ts +12 -0
  40. package/dist/helpers/cookies.d.ts.map +1 -0
  41. package/dist/helpers/cookies.js +66 -0
  42. package/dist/helpers/cookies.js.map +1 -0
  43. package/dist/helpers/coordinateResolver.d.ts +29 -0
  44. package/dist/helpers/coordinateResolver.d.ts.map +1 -0
  45. package/dist/helpers/coordinateResolver.js +118 -0
  46. package/dist/helpers/coordinateResolver.js.map +1 -0
  47. package/dist/helpers/coordinateResolverRead.d.ts +36 -0
  48. package/dist/helpers/coordinateResolverRead.d.ts.map +1 -0
  49. package/dist/helpers/coordinateResolverRead.js +107 -0
  50. package/dist/helpers/coordinateResolverRead.js.map +1 -0
  51. package/dist/helpers/dialog.d.ts +29 -0
  52. package/dist/helpers/dialog.d.ts.map +1 -0
  53. package/dist/helpers/dialog.js +35 -0
  54. package/dist/helpers/dialog.js.map +1 -0
  55. package/dist/helpers/drag.d.ts +36 -1
  56. package/dist/helpers/drag.d.ts.map +1 -1
  57. package/dist/helpers/drag.js +267 -0
  58. package/dist/helpers/drag.js.map +1 -1
  59. package/dist/helpers/executeApi.d.ts +2 -0
  60. package/dist/helpers/executeApi.d.ts.map +1 -1
  61. package/dist/helpers/executeApi.js +30 -10
  62. package/dist/helpers/executeApi.js.map +1 -1
  63. package/dist/helpers/executeJs.d.ts.map +1 -1
  64. package/dist/helpers/executeJs.js +46 -3
  65. package/dist/helpers/executeJs.js.map +1 -1
  66. package/dist/helpers/gesture.d.ts +45 -0
  67. package/dist/helpers/gesture.d.ts.map +1 -0
  68. package/dist/helpers/gesture.js +131 -0
  69. package/dist/helpers/gesture.js.map +1 -0
  70. package/dist/helpers/healCascade.d.ts +57 -0
  71. package/dist/helpers/healCascade.d.ts.map +1 -0
  72. package/dist/helpers/healCascade.js +363 -0
  73. package/dist/helpers/healCascade.js.map +1 -0
  74. package/dist/helpers/png.d.ts +3 -0
  75. package/dist/helpers/png.d.ts.map +1 -0
  76. package/dist/helpers/png.js +18 -0
  77. package/dist/helpers/png.js.map +1 -0
  78. package/dist/helpers/screenshot.d.ts +27 -0
  79. package/dist/helpers/screenshot.d.ts.map +1 -1
  80. package/dist/helpers/screenshot.js +56 -0
  81. package/dist/helpers/screenshot.js.map +1 -1
  82. package/dist/helpers/scrollUntil.d.ts +13 -0
  83. package/dist/helpers/scrollUntil.d.ts.map +1 -0
  84. package/dist/helpers/scrollUntil.js +88 -0
  85. package/dist/helpers/scrollUntil.js.map +1 -0
  86. package/dist/helpers/tabs.d.ts +42 -1
  87. package/dist/helpers/tabs.d.ts.map +1 -1
  88. package/dist/helpers/tabs.js +259 -5
  89. package/dist/helpers/tabs.js.map +1 -1
  90. package/dist/helpers/text.d.ts +15 -0
  91. package/dist/helpers/text.d.ts.map +1 -0
  92. package/dist/helpers/text.js +24 -0
  93. package/dist/helpers/text.js.map +1 -0
  94. package/dist/helpers/textNormalize.d.ts +18 -0
  95. package/dist/helpers/textNormalize.d.ts.map +1 -0
  96. package/dist/helpers/textNormalize.js +39 -0
  97. package/dist/helpers/textNormalize.js.map +1 -0
  98. package/dist/helpers/textualRead.d.ts +37 -0
  99. package/dist/helpers/textualRead.d.ts.map +1 -0
  100. package/dist/helpers/textualRead.js +211 -0
  101. package/dist/helpers/textualRead.js.map +1 -0
  102. package/dist/helpers/vision.d.ts +2 -0
  103. package/dist/helpers/vision.d.ts.map +1 -1
  104. package/dist/helpers/vision.js +11 -0
  105. package/dist/helpers/vision.js.map +1 -1
  106. package/dist/helpers/visionV3.d.ts +38 -0
  107. package/dist/helpers/visionV3.d.ts.map +1 -0
  108. package/dist/helpers/visionV3.js +291 -0
  109. package/dist/helpers/visionV3.js.map +1 -0
  110. package/dist/helpers/wait.d.ts +14 -1
  111. package/dist/helpers/wait.d.ts.map +1 -1
  112. package/dist/helpers/wait.js +25 -0
  113. package/dist/helpers/wait.js.map +1 -1
  114. package/dist/index.d.ts +29 -3
  115. package/dist/index.d.ts.map +1 -1
  116. package/dist/index.js +23 -4
  117. package/dist/index.js.map +1 -1
  118. package/dist/log.d.ts +4 -1
  119. package/dist/log.d.ts.map +1 -1
  120. package/dist/log.js +8 -3
  121. package/dist/log.js.map +1 -1
  122. package/dist/rankedLocator.d.ts +27 -0
  123. package/dist/rankedLocator.d.ts.map +1 -0
  124. package/dist/rankedLocator.js +85 -0
  125. package/dist/rankedLocator.js.map +1 -0
  126. package/dist/reporters/index.d.ts +2 -0
  127. package/dist/reporters/index.d.ts.map +1 -1
  128. package/dist/reporters/index.js.map +1 -1
  129. package/dist/reporters/lt.d.ts.map +1 -1
  130. package/dist/reporters/lt.js +7 -1
  131. package/dist/reporters/lt.js.map +1 -1
  132. package/dist/routeFailure.d.ts +9 -0
  133. package/dist/routeFailure.d.ts.map +1 -0
  134. package/dist/routeFailure.js +34 -0
  135. package/dist/routeFailure.js.map +1 -0
  136. package/dist/session.d.ts.map +1 -1
  137. package/dist/session.js +21 -0
  138. package/dist/session.js.map +1 -1
  139. package/dist/step.d.ts +10 -0
  140. package/dist/step.d.ts.map +1 -1
  141. package/dist/step.js +14 -1
  142. package/dist/step.js.map +1 -1
  143. package/dist/testConfig.d.ts.map +1 -1
  144. package/dist/testConfig.js +8 -1
  145. package/dist/testConfig.js.map +1 -1
  146. package/dist/vars.d.ts +10 -0
  147. package/dist/vars.d.ts.map +1 -1
  148. package/dist/vars.js +30 -3
  149. package/dist/vars.js.map +1 -1
  150. package/dist/visionLocator.d.ts +53 -0
  151. package/dist/visionLocator.d.ts.map +1 -0
  152. package/dist/visionLocator.js +117 -0
  153. package/dist/visionLocator.js.map +1 -0
  154. package/package.json +2 -2
@@ -0,0 +1 @@
1
+ {"version":3,"file":"scrollUntil.js","sourceRoot":"","sources":["../../src/helpers/scrollUntil.ts"],"names":[],"mappings":"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"}
@@ -1,3 +1,44 @@
1
+ /**
2
+ * Tab helpers — PY _helpers/tabs.py port. V3 adds tolerant tab-identifier
3
+ * resolution (exact → ci-exact title → host/prefix URL → ci-contains) with an
4
+ * automind /v1/heal/switch-tab rescue; the V4 index/exact-title paths stay
5
+ * byte-identical to the pre-V3 behavior.
6
+ */
1
7
  import type { BrowserContext, Page } from 'playwright';
2
- export declare function switchTab(context: BrowserContext, index: number): Promise<Page>;
8
+ /** Host/prefix-aware URL match: bare domain or full URL identifiers; matching
9
+ * is by host (github.com ≠ gist.github.com ≠ github.com.evil.com); an
10
+ * identifier path must prefix the URL path; www. ignored both sides. */
11
+ export declare function _urlMatches(identifier: string, url: string): boolean;
12
+ type SeenPage = [Page, string, string];
13
+ /** First non-empty tier wins: exact title/URL, ci-exact title, host/prefix
14
+ * URL, ci-contains title. */
15
+ export declare function _matchTabTiers(seen: SeenPage[], identifier: string): Page[];
16
+ /** Open a new tab; V3 blank tabs land on Google (V2 parity), V4 blank tabs
17
+ * do not navigate (legacy behavior preserved). */
18
+ export declare function newTab(context: BrowserContext, url?: string | null): Promise<Page>;
19
+ export interface SwitchTabOptions {
20
+ title?: string | null;
21
+ description?: string | null;
22
+ }
23
+ /** Switch by 0-based index, or by title (takes precedence). V3 resolves the
24
+ * identifier tolerantly with an automind rescue; V4 keeps exact-title only. */
25
+ export declare function switchTab(context: BrowserContext, tabIndex: number, opts?: SwitchTabOptions): Promise<Page>;
26
+ export interface CloseTabOptions {
27
+ index?: number | null;
28
+ title?: string | null;
29
+ description?: string | null;
30
+ }
31
+ /**
32
+ * Close a tab and activate the most-recent remaining one. V3: refuses to
33
+ * close the only tab; resolves title-first (V3 codegen's index defaults to a
34
+ * meaningless 0) with automind rescue, then intent, then index. V4 keeps the
35
+ * legacy index → exact-title → most-recent order.
36
+ */
37
+ export declare function closeTab(context: BrowserContext, opts?: CloseTabOptions): Promise<void>;
38
+ /**
39
+ * Return page if still open, else re-point to the last surviving tab (the
40
+ * per-action stale-window heal — V3 export calls this after tab ops).
41
+ */
42
+ export declare function ensureActivePage(page: Page): Promise<Page>;
43
+ export {};
3
44
  //# sourceMappingURL=tabs.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"tabs.d.ts","sourceRoot":"","sources":["../../src/helpers/tabs.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,cAAc,EAAE,IAAI,EAAE,MAAM,YAAY,CAAC;AAGvD,wBAAsB,SAAS,CAAC,OAAO,EAAE,cAAc,EAAE,KAAK,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC,CAWrF"}
1
+ {"version":3,"file":"tabs.d.ts","sourceRoot":"","sources":["../../src/helpers/tabs.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AACH,OAAO,KAAK,EAAE,cAAc,EAAE,IAAI,EAAE,MAAM,YAAY,CAAC;AAYvD;;wEAEwE;AACxE,wBAAgB,WAAW,CAAC,UAAU,EAAE,MAAM,EAAE,GAAG,EAAE,MAAM,GAAG,OAAO,CAoBpE;AAED,KAAK,QAAQ,GAAG,CAAC,IAAI,EAAE,MAAM,EAAE,MAAM,CAAC,CAAC;AAiBvC;6BAC6B;AAC7B,wBAAgB,cAAc,CAAC,IAAI,EAAE,QAAQ,EAAE,EAAE,UAAU,EAAE,MAAM,GAAG,IAAI,EAAE,CAS3E;AAoFD;kDACkD;AAClD,wBAAsB,MAAM,CAAC,OAAO,EAAE,cAAc,EAAE,GAAG,CAAC,EAAE,MAAM,GAAG,IAAI,GAAG,OAAO,CAAC,IAAI,CAAC,CAQxF;AAED,MAAM,WAAW,gBAAgB;IAC/B,KAAK,CAAC,EAAE,MAAM,GAAG,IAAI,CAAC;IACtB,WAAW,CAAC,EAAE,MAAM,GAAG,IAAI,CAAC;CAC7B;AAED;+EAC+E;AAC/E,wBAAsB,SAAS,CAC7B,OAAO,EAAE,cAAc,EACvB,QAAQ,EAAE,MAAM,EAChB,IAAI,GAAE,gBAAqB,GAC1B,OAAO,CAAC,IAAI,CAAC,CA0Cf;AAED,MAAM,WAAW,eAAe;IAC9B,KAAK,CAAC,EAAE,MAAM,GAAG,IAAI,CAAC;IACtB,KAAK,CAAC,EAAE,MAAM,GAAG,IAAI,CAAC;IACtB,WAAW,CAAC,EAAE,MAAM,GAAG,IAAI,CAAC;CAC7B;AAED;;;;;GAKG;AACH,wBAAsB,QAAQ,CAAC,OAAO,EAAE,cAAc,EAAE,IAAI,GAAE,eAAoB,GAAG,OAAO,CAAC,IAAI,CAAC,CAmCjG;AAED;;;GAGG;AACH,wBAAsB,gBAAgB,CAAC,IAAI,EAAE,IAAI,GAAG,OAAO,CAAC,IAAI,CAAC,CAWhE"}
@@ -1,15 +1,269 @@
1
+ import { get as configGet, isV3 } from '../configure.js';
1
2
  import { log } from '../log.js';
2
- export async function switchTab(context, index) {
3
- log.helper(`[switch_tab] index=${index}`);
3
+ const TAB_HEAL_PATH = '/v1/heal/switch-tab';
4
+ // ── tolerant tab-identifier resolution ───────────────────────────────────────
5
+ function stripWww(host) {
6
+ return host.startsWith('www.') ? host.slice(4) : host;
7
+ }
8
+ /** Host/prefix-aware URL match: bare domain or full URL identifiers; matching
9
+ * is by host (github.com ≠ gist.github.com ≠ github.com.evil.com); an
10
+ * identifier path must prefix the URL path; www. ignored both sides. */
11
+ export function _urlMatches(identifier, url) {
12
+ if (typeof url !== 'string' || !url)
13
+ return false;
14
+ let parsedId;
15
+ try {
16
+ parsedId = new URL(identifier.includes('://') ? identifier : `http://${identifier}`);
17
+ }
18
+ catch {
19
+ return false;
20
+ }
21
+ const idHost = stripWww(parsedId.hostname.toLowerCase());
22
+ if (!idHost)
23
+ return false;
24
+ let parsedUrl;
25
+ try {
26
+ parsedUrl = new URL(url);
27
+ }
28
+ catch {
29
+ return false;
30
+ }
31
+ if (stripWww(parsedUrl.hostname.toLowerCase()) !== idHost)
32
+ return false;
33
+ const idPath = parsedId.pathname.replace(/\/+$/, '');
34
+ if (idPath && idPath !== '')
35
+ return parsedUrl.pathname.startsWith(idPath);
36
+ return true;
37
+ }
38
+ /** Snapshot (page, title, url) per open tab; a tab that errors mid-read
39
+ * contributes empty strings (fails to match) rather than aborting. */
40
+ async function seenPages(context) {
41
+ const seen = [];
42
+ for (const page of context.pages()) {
43
+ let title = '', url = '';
44
+ try {
45
+ title = await page.title();
46
+ url = page.url();
47
+ }
48
+ catch { /* closed mid-iteration */ }
49
+ seen.push([page, title || '', url || '']);
50
+ }
51
+ return seen;
52
+ }
53
+ /** First non-empty tier wins: exact title/URL, ci-exact title, host/prefix
54
+ * URL, ci-contains title. */
55
+ export function _matchTabTiers(seen, identifier) {
56
+ const identLower = identifier.toLowerCase();
57
+ const exact = seen.filter(([, t, u]) => t === identifier || u === identifier).map(([p]) => p);
58
+ if (exact.length)
59
+ return exact;
60
+ const ciExact = seen.filter(([, t]) => t.toLowerCase() === identLower).map(([p]) => p);
61
+ if (ciExact.length)
62
+ return ciExact;
63
+ const byUrl = seen.filter(([, , u]) => _urlMatches(identifier, u)).map(([p]) => p);
64
+ if (byUrl.length)
65
+ return byUrl;
66
+ return seen.filter(([, t]) => identLower !== '' && t.toLowerCase().includes(identLower)).map(([p]) => p);
67
+ }
68
+ async function resolveTabPage(context, identifier) {
69
+ const matches = _matchTabTiers(await seenPages(context), identifier);
70
+ if (!matches.length)
71
+ return null;
72
+ if (matches.length > 1) {
73
+ log.helper(`[tabs] ${matches.length} open tabs matched identifier ${JSON.stringify(identifier)}; using the first.`);
74
+ }
75
+ return matches[0];
76
+ }
77
+ // ── automind rescue (V2 kaneai_switch_tab_heal parity) ───────────────────────
78
+ function orgIdInt(raw) {
79
+ const parsed = parseInt(String(raw), 10);
80
+ return Number.isNaN(parsed) ? 0 : parsed;
81
+ }
82
+ function requestId() {
83
+ return [...Array(16)].map(() => Math.floor(Math.random() * 16).toString(16)).join('');
84
+ }
85
+ /** Resolve the target tab via automind: op intent + live titles → tab index.
86
+ * Returns null on ANY failure so callers fall back to static behavior. */
87
+ async function automindResolveTab(context, intent, operationType) {
88
+ try {
89
+ const baseUrl = String(configGet('automindUrl') ?? '');
90
+ const username = String(configGet('username') ?? '') || (process.env['LT_USERNAME'] ?? '');
91
+ const accesskey = String(configGet('accesskey') ?? '') || (process.env['LT_ACCESS_KEY'] ?? '');
92
+ if (!username || !accesskey || !baseUrl) {
93
+ log.helper('[tabs] automind tab resolution unavailable (missing creds/URL)');
94
+ return null;
95
+ }
96
+ const seen = await seenPages(context);
97
+ const titles = seen.map(([, t]) => t);
98
+ const payload = {
99
+ code_request_id: requestId(),
100
+ intent,
101
+ open_tabs: titles,
102
+ // No definitive "current tab" from the context alone; last = best-effort.
103
+ current_tab: titles.length ? titles[titles.length - 1] : '',
104
+ operation_type: operationType,
105
+ test_id: configGet('testId') ?? '',
106
+ session_id: configGet('sessionId') ?? '',
107
+ commit_id: configGet('commitId') ?? '',
108
+ org_id: orgIdInt(configGet('orgId')),
109
+ current_action: { operation_type: operationType, operation_intent: intent },
110
+ is_mobile: false,
111
+ device_os: '',
112
+ };
113
+ const resp = await fetch(`${baseUrl}${TAB_HEAL_PATH}`, {
114
+ method: 'POST',
115
+ headers: {
116
+ 'Content-Type': 'application/json',
117
+ Authorization: `Basic ${Buffer.from(`${username}:${accesskey}`).toString('base64')}`,
118
+ },
119
+ body: JSON.stringify(payload),
120
+ signal: AbortSignal.timeout(30_000),
121
+ });
122
+ if (resp.status !== 200) {
123
+ log.helper(`[tabs] automind ${TAB_HEAL_PATH} status=${resp.status}`);
124
+ return null;
125
+ }
126
+ const result = (await resp.json());
127
+ const idx = result.tab_index;
128
+ const i = Number(idx);
129
+ if (idx === null || idx === undefined || !Number.isInteger(i) || i < 0 || i >= seen.length) {
130
+ log.helper(`[tabs] automind tab resolution unusable: ${JSON.stringify(result)}`);
131
+ return null;
132
+ }
133
+ log.helper(`[tabs] automind resolved intent ${JSON.stringify(intent)} -> tab ${i}`);
134
+ return seen[i][0];
135
+ }
136
+ catch (e) {
137
+ log.helper(`[tabs] automind tab resolution failed: ${String(e)}`);
138
+ return null;
139
+ }
140
+ }
141
+ // ── public surface ───────────────────────────────────────────────────────────
142
+ /** Open a new tab; V3 blank tabs land on Google (V2 parity), V4 blank tabs
143
+ * do not navigate (legacy behavior preserved). */
144
+ export async function newTab(context, url) {
145
+ const page = await context.newPage();
146
+ let target = url ?? null;
147
+ if (target === null && isV3())
148
+ target = 'https://www.google.com';
149
+ if (target !== null)
150
+ await page.goto(target);
151
+ await page.bringToFront();
152
+ log.helper(`[new_tab] opened tab (url=${target ?? '<none>'})`);
153
+ return page;
154
+ }
155
+ /** Switch by 0-based index, or by title (takes precedence). V3 resolves the
156
+ * identifier tolerantly with an automind rescue; V4 keeps exact-title only. */
157
+ export async function switchTab(context, tabIndex, opts = {}) {
158
+ const { title = null, description = null } = opts;
159
+ if (title === null && description !== null && isV3()) {
160
+ const page = await automindResolveTab(context, description, 'SWITCH_TAB');
161
+ if (page === null)
162
+ throw new Error(`No tab matching description ${JSON.stringify(description)}`);
163
+ await page.bringToFront();
164
+ log.helper(`[switch_tab] switched via automind description=${JSON.stringify(description)}`);
165
+ return page;
166
+ }
167
+ if (title !== null) {
168
+ if (isV3()) {
169
+ let page = await resolveTabPage(context, title);
170
+ if (page === null)
171
+ page = await automindResolveTab(context, title, 'SWITCH_TAB');
172
+ if (page === null)
173
+ throw new Error(`No tab with title ${JSON.stringify(title)}`);
174
+ await page.bringToFront();
175
+ log.helper(`[switch_tab] switched to tab identifier=${JSON.stringify(title)} (url=${page.url()})`);
176
+ return page;
177
+ }
178
+ for (const page of context.pages()) {
179
+ if ((await page.title()) === title) {
180
+ await page.bringToFront();
181
+ log.helper(`[switch_tab] switched to tab title=${JSON.stringify(title)} (url=${page.url()})`);
182
+ return page;
183
+ }
184
+ }
185
+ throw new Error(`No tab with title ${JSON.stringify(title)}`);
186
+ }
4
187
  let pages = context.pages();
5
- if (index >= pages.length) {
188
+ log.helper(`[switch_tab] target_index=${tabIndex} current_tabs=${pages.length}`);
189
+ if (tabIndex >= pages.length) {
190
+ // Tab not in the list yet — a click may have opened target=_blank.
6
191
  await context.waitForEvent('page', { timeout: 5000 }).catch(() => null);
7
192
  pages = context.pages();
8
193
  }
9
- const target = pages[index];
194
+ const target = pages[tabIndex];
10
195
  if (!target)
11
- throw new Error(`Tab index ${index} does not exist (have ${pages.length})`);
196
+ throw new Error(`Tab ${tabIndex} does not exist (${pages.length} tabs open)`);
12
197
  await target.bringToFront();
198
+ log.helper(`[switch_tab] switched to tab ${tabIndex}`);
13
199
  return target;
14
200
  }
201
+ /**
202
+ * Close a tab and activate the most-recent remaining one. V3: refuses to
203
+ * close the only tab; resolves title-first (V3 codegen's index defaults to a
204
+ * meaningless 0) with automind rescue, then intent, then index. V4 keeps the
205
+ * legacy index → exact-title → most-recent order.
206
+ */
207
+ export async function closeTab(context, opts = {}) {
208
+ const { index = null, title = null, description = null } = opts;
209
+ const v3 = isV3();
210
+ if (v3 && context.pages().length <= 1) {
211
+ throw new Error('Cannot close the only open tab');
212
+ }
213
+ let target = null;
214
+ if (v3 && title !== null) {
215
+ target = await resolveTabPage(context, title);
216
+ if (target === null)
217
+ target = await automindResolveTab(context, description ?? title, 'CLOSE_TAB');
218
+ if (target === null)
219
+ throw new Error(`No tab with title ${JSON.stringify(title)}`);
220
+ }
221
+ else if (v3 && description !== null) {
222
+ target = await automindResolveTab(context, description, 'CLOSE_TAB');
223
+ if (target === null && index !== null)
224
+ target = context.pages()[index] ?? null;
225
+ if (target === null)
226
+ target = context.pages()[context.pages().length - 1] ?? null;
227
+ }
228
+ else if (index !== null) {
229
+ target = context.pages()[index] ?? null;
230
+ if (!target)
231
+ throw new Error(`Tab ${index} does not exist`);
232
+ }
233
+ else if (title !== null) {
234
+ for (const page of context.pages()) {
235
+ if ((await page.title()) === title) {
236
+ target = page;
237
+ break;
238
+ }
239
+ }
240
+ if (!target)
241
+ throw new Error(`No tab with title ${JSON.stringify(title)}`);
242
+ }
243
+ else {
244
+ target = context.pages()[context.pages().length - 1] ?? null;
245
+ }
246
+ if (!target)
247
+ throw new Error('close_tab: no tab to close');
248
+ log.helper(`[close_tab] closing tab (url=${target.url()})`);
249
+ await target.close();
250
+ const remaining = context.pages();
251
+ if (remaining.length)
252
+ await remaining[remaining.length - 1].bringToFront();
253
+ }
254
+ /**
255
+ * Return page if still open, else re-point to the last surviving tab (the
256
+ * per-action stale-window heal — V3 export calls this after tab ops).
257
+ */
258
+ export async function ensureActivePage(page) {
259
+ if (!page.isClosed())
260
+ return page;
261
+ const survivors = page.context().pages().filter((p) => !p.isClosed());
262
+ if (!survivors.length) {
263
+ throw new Error('ensure_active_page: the active tab was closed and no surviving tab remains in the browser context');
264
+ }
265
+ const next = survivors[survivors.length - 1];
266
+ await next.bringToFront();
267
+ return next;
268
+ }
15
269
  //# sourceMappingURL=tabs.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"tabs.js","sourceRoot":"","sources":["../../src/helpers/tabs.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,GAAG,EAAE,MAAM,WAAW,CAAC;AAEhC,MAAM,CAAC,KAAK,UAAU,SAAS,CAAC,OAAuB,EAAE,KAAa;IACpE,GAAG,CAAC,MAAM,CAAC,sBAAsB,KAAK,EAAE,CAAC,CAAC;IAC1C,IAAI,KAAK,GAAG,OAAO,CAAC,KAAK,EAAE,CAAC;IAC5B,IAAI,KAAK,IAAI,KAAK,CAAC,MAAM,EAAE,CAAC;QAC1B,MAAM,OAAO,CAAC,YAAY,CAAC,MAAM,EAAE,EAAE,OAAO,EAAE,IAAI,EAAE,CAAC,CAAC,KAAK,CAAC,GAAG,EAAE,CAAC,IAAI,CAAC,CAAC;QACxE,KAAK,GAAG,OAAO,CAAC,KAAK,EAAE,CAAC;IAC1B,CAAC;IACD,MAAM,MAAM,GAAG,KAAK,CAAC,KAAK,CAAC,CAAC;IAC5B,IAAI,CAAC,MAAM;QAAE,MAAM,IAAI,KAAK,CAAC,aAAa,KAAK,yBAAyB,KAAK,CAAC,MAAM,GAAG,CAAC,CAAC;IACzF,MAAM,MAAM,CAAC,YAAY,EAAE,CAAC;IAC5B,OAAO,MAAM,CAAC;AAChB,CAAC"}
1
+ {"version":3,"file":"tabs.js","sourceRoot":"","sources":["../../src/helpers/tabs.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,15 @@
1
+ /**
2
+ * Coerce a scalar fill/type value to the string Playwright requires.
3
+ *
4
+ * Variables are type-preserving — resolveVar returns the stored value
5
+ * untouched — so a number/boolean produced by executeJs (or stored via
6
+ * setVar) can reach a text-input verb as a non-string. Playwright's
7
+ * Locator.fill/type reject those ("expected string, got number").
8
+ *
9
+ * Only scalars are coerced (String() is locale-invariant by spec; toFixed /
10
+ * toLocaleString stay banned per the V3 contract). Objects and arrays are
11
+ * left untouched so they surface loudly as a clear Playwright error rather
12
+ * than silently filling "[object Object]". Mirrors PY _action_specs._coerce_text.
13
+ */
14
+ export declare function asText(value: unknown): unknown;
15
+ //# sourceMappingURL=text.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"text.d.ts","sourceRoot":"","sources":["../../src/helpers/text.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;GAYG;AACH,wBAAgB,MAAM,CAAC,KAAK,EAAE,OAAO,GAAG,OAAO,CAU9C"}
@@ -0,0 +1,24 @@
1
+ /**
2
+ * Coerce a scalar fill/type value to the string Playwright requires.
3
+ *
4
+ * Variables are type-preserving — resolveVar returns the stored value
5
+ * untouched — so a number/boolean produced by executeJs (or stored via
6
+ * setVar) can reach a text-input verb as a non-string. Playwright's
7
+ * Locator.fill/type reject those ("expected string, got number").
8
+ *
9
+ * Only scalars are coerced (String() is locale-invariant by spec; toFixed /
10
+ * toLocaleString stay banned per the V3 contract). Objects and arrays are
11
+ * left untouched so they surface loudly as a clear Playwright error rather
12
+ * than silently filling "[object Object]". Mirrors PY _action_specs._coerce_text.
13
+ */
14
+ export function asText(value) {
15
+ if (typeof value === 'string')
16
+ return value;
17
+ if (typeof value === 'number' ||
18
+ typeof value === 'boolean' ||
19
+ typeof value === 'bigint') {
20
+ return String(value);
21
+ }
22
+ return value;
23
+ }
24
+ //# sourceMappingURL=text.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"text.js","sourceRoot":"","sources":["../../src/helpers/text.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;GAYG;AACH,MAAM,UAAU,MAAM,CAAC,KAAc;IACnC,IAAI,OAAO,KAAK,KAAK,QAAQ;QAAE,OAAO,KAAK,CAAC;IAC5C,IACE,OAAO,KAAK,KAAK,QAAQ;QACzB,OAAO,KAAK,KAAK,SAAS;QAC1B,OAAO,KAAK,KAAK,QAAQ,EACzB,CAAC;QACD,OAAO,MAAM,CAAC,KAAK,CAAC,CAAC;IACvB,CAAC;IACD,OAAO,KAAK,CAAC;AACf,CAAC"}
@@ -0,0 +1,18 @@
1
+ /**
2
+ * Canonicalize text for substring/prefix/suffix matching, matching the
3
+ * Selenium runtime (PY oracle: _assertion_v3_eval._normalize_text).
4
+ *
5
+ * Folds accents/ligatures (NFKD + drop combining marks), maps smart
6
+ * punctuation and invisible characters, collapses whitespace, and optionally
7
+ * case-folds — so `contains`/`starts_with`/`ends_with` match the way the
8
+ * Selenium runtime evaluated them (e.g. "Café Menu" contains "cafe").
9
+ *
10
+ * Normalization is explicit per the V3 contract's runtime-conventions block:
11
+ * JS has no implicit equivalent of Python's unicodedata.normalize, and
12
+ * skipping it silently fails composed-vs-decomposed accent comparisons.
13
+ */
14
+ export declare function normalizeText(value: unknown, opts?: {
15
+ caseInsensitive?: boolean;
16
+ asciiFold?: boolean;
17
+ }): string;
18
+ //# sourceMappingURL=textNormalize.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"textNormalize.d.ts","sourceRoot":"","sources":["../../src/helpers/textNormalize.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;GAYG;AAWH,wBAAgB,aAAa,CAC3B,KAAK,EAAE,OAAO,EACd,IAAI,GAAE;IAAE,eAAe,CAAC,EAAE,OAAO,CAAC;IAAC,SAAS,CAAC,EAAE,OAAO,CAAA;CAAO,GAC5D,MAAM,CAcR"}
@@ -0,0 +1,39 @@
1
+ /**
2
+ * Canonicalize text for substring/prefix/suffix matching, matching the
3
+ * Selenium runtime (PY oracle: _assertion_v3_eval._normalize_text).
4
+ *
5
+ * Folds accents/ligatures (NFKD + drop combining marks), maps smart
6
+ * punctuation and invisible characters, collapses whitespace, and optionally
7
+ * case-folds — so `contains`/`starts_with`/`ends_with` match the way the
8
+ * Selenium runtime evaluated them (e.g. "Café Menu" contains "cafe").
9
+ *
10
+ * Normalization is explicit per the V3 contract's runtime-conventions block:
11
+ * JS has no implicit equivalent of Python's unicodedata.normalize, and
12
+ * skipping it silently fails composed-vs-decomposed accent comparisons.
13
+ */
14
+ const SMART_PUNCT = {
15
+ '‘': "'", '’': "'", // curly single quotes
16
+ '“': '"', '”': '"', // curly double quotes
17
+ ' ': ' ', // non-breaking space
18
+ '​': '', '‌': '', '‍': '', '': '', // zero-width / BOM
19
+ };
20
+ const SMART_PUNCT_RE = /[‘’“” ​‌‍]/g;
21
+ export function normalizeText(value, opts = {}) {
22
+ const { caseInsensitive = false, asciiFold = true } = opts;
23
+ let s = String(value);
24
+ if (!s)
25
+ return s;
26
+ if (asciiFold) {
27
+ // NFKD + strip combining marks — the accent fold.
28
+ s = s.normalize('NFKD').replace(/\p{M}/gu, '');
29
+ }
30
+ else {
31
+ s = s.normalize('NFKC');
32
+ }
33
+ s = s.replace(SMART_PUNCT_RE, (ch) => SMART_PUNCT[ch] ?? ch);
34
+ s = s.replace(/\s+/g, ' ').trim();
35
+ if (caseInsensitive)
36
+ s = s.toLowerCase();
37
+ return s;
38
+ }
39
+ //# sourceMappingURL=textNormalize.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"textNormalize.js","sourceRoot":"","sources":["../../src/helpers/textNormalize.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;GAYG;AAEH,MAAM,WAAW,GAA2B;IAC1C,GAAG,EAAE,GAAG,EAAE,GAAG,EAAE,GAAG,EAAE,sBAAsB;IAC1C,GAAG,EAAE,GAAG,EAAE,GAAG,EAAE,GAAG,EAAE,sBAAsB;IAC1C,GAAG,EAAE,GAAG,EAAiB,qBAAqB;IAC9C,GAAG,EAAE,EAAE,EAAE,GAAG,EAAE,EAAE,EAAE,GAAG,EAAE,EAAE,EAAE,GAAG,EAAE,EAAE,EAAE,mBAAmB;CACxD,CAAC;AAEF,MAAM,cAAc,GAAG,cAAc,CAAC;AAEtC,MAAM,UAAU,aAAa,CAC3B,KAAc,EACd,OAA2D,EAAE;IAE7D,MAAM,EAAE,eAAe,GAAG,KAAK,EAAE,SAAS,GAAG,IAAI,EAAE,GAAG,IAAI,CAAC;IAC3D,IAAI,CAAC,GAAG,MAAM,CAAC,KAAK,CAAC,CAAC;IACtB,IAAI,CAAC,CAAC;QAAE,OAAO,CAAC,CAAC;IACjB,IAAI,SAAS,EAAE,CAAC;QACd,kDAAkD;QAClD,CAAC,GAAG,CAAC,CAAC,SAAS,CAAC,MAAM,CAAC,CAAC,OAAO,CAAC,SAAS,EAAE,EAAE,CAAC,CAAC;IACjD,CAAC;SAAM,CAAC;QACN,CAAC,GAAG,CAAC,CAAC,SAAS,CAAC,MAAM,CAAC,CAAC;IAC1B,CAAC;IACD,CAAC,GAAG,CAAC,CAAC,OAAO,CAAC,cAAc,EAAE,CAAC,EAAE,EAAE,EAAE,CAAC,WAAW,CAAC,EAAE,CAAC,IAAI,EAAE,CAAC,CAAC;IAC7D,CAAC,GAAG,CAAC,CAAC,OAAO,CAAC,MAAM,EAAE,GAAG,CAAC,CAAC,IAAI,EAAE,CAAC;IAClC,IAAI,eAAe;QAAE,CAAC,GAAG,CAAC,CAAC,WAAW,EAAE,CAAC;IACzC,OAAO,CAAC,CAAC;AACX,CAAC"}
@@ -0,0 +1,37 @@
1
+ /**
2
+ * Async local attribute extraction for V3 textual_query — port of PY
3
+ * _helpers/_textual_read.py (itself a port of selenium's textual_query).
4
+ * Consumed only by the V3 locate-then-read path in visionV3.textualQueryV3;
5
+ * no V4 code imports this module.
6
+ *
7
+ * Every page function here is a REAL function, never a string — the grid CDP
8
+ * relay returns undefined for string page-functions (corner-case catalog).
9
+ *
10
+ * Intentional parity gaps carried over from PY (documented there; not bugs):
11
+ * role is explicit-attr only; size returns {width,height} floats ({} when not
12
+ * visible); rgbaToName HSV buckets are the selenium thresholds.
13
+ */
14
+ import type { Locator } from 'playwright';
15
+ export declare const LOCAL_READ_ATTRS: ReadonlySet<string>;
16
+ /** rgb()/rgba() CSS string → basic colour name; '' on parse failure. HSV
17
+ * buckets verbatim from selenium (colorsys.rgb_to_hsv math inlined). */
18
+ export declare function rgbaToName(cssValue: string | null | undefined): string;
19
+ /** Meaningful text/value for any element: input/textarea → inputValue;
20
+ * select → option values/text; contenteditable → innerText; else innerText()
21
+ * (rendered visible text — Selenium .text parity, NOT textContent). */
22
+ export declare function safeValue(el: Locator): Promise<string>;
23
+ /**
24
+ * Dispatch over attribute name and return the raw value for `el`. Throws for
25
+ * `location`/`custom_attributes_dict`/unknown names (loud-not-silent parity
26
+ * with selenium — the caller degrades to the server fallback).
27
+ */
28
+ export declare function populateAttribute(el: Locator, requestedAttribute: string): Promise<unknown>;
29
+ /**
30
+ * Post-locate extraction — shared entry for the V3 locate-then-read path.
31
+ * img/canvas short-circuit, regex-over-outerHTML for text/value, then
32
+ * coerceTextualValue. Does NOT locate; callers own that. regexPattern is
33
+ * accepted for parity but the current caller always passes null (same
34
+ * deferred-dispatcher note as PY _extract_value).
35
+ */
36
+ export declare function extractValue(el: Locator, selectedAttributeName: string, regexPattern: string | null, returnType: string): Promise<unknown>;
37
+ //# sourceMappingURL=textualRead.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"textualRead.d.ts","sourceRoot":"","sources":["../../src/helpers/textualRead.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;GAYG;AACH,OAAO,KAAK,EAAE,OAAO,EAAE,MAAM,YAAY,CAAC;AAM1C,eAAO,MAAM,gBAAgB,EAAE,WAAW,CAAC,MAAM,CAgB/C,CAAC;AAIH;wEACwE;AACxE,wBAAgB,UAAU,CAAC,QAAQ,EAAE,MAAM,GAAG,IAAI,GAAG,SAAS,GAAG,MAAM,CAgCtE;AAED;;uEAEuE;AACvE,wBAAsB,SAAS,CAAC,EAAE,EAAE,OAAO,GAAG,OAAO,CAAC,MAAM,CAAC,CAuC5D;AA0BD;;;;GAIG;AACH,wBAAsB,iBAAiB,CAAC,EAAE,EAAE,OAAO,EAAE,kBAAkB,EAAE,MAAM,GAAG,OAAO,CAAC,OAAO,CAAC,CAmDjG;AAED;;;;;;GAMG;AACH,wBAAsB,YAAY,CAChC,EAAE,EAAE,OAAO,EACX,qBAAqB,EAAE,MAAM,EAC7B,YAAY,EAAE,MAAM,GAAG,IAAI,EAC3B,UAAU,EAAE,MAAM,GACjB,OAAO,CAAC,OAAO,CAAC,CAclB"}