@nuanu-ai/agentbrowse 0.2.12 → 0.2.14
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +5 -0
- package/dist/agentpay-stagehand-llm.d.ts +16 -0
- package/dist/agentpay-stagehand-llm.d.ts.map +1 -1
- package/dist/agentpay-stagehand-llm.js +35 -10
- package/dist/commands/act.d.ts.map +1 -1
- package/dist/commands/act.js +16 -15
- package/dist/commands/action-acceptance.d.ts +1 -0
- package/dist/commands/action-acceptance.d.ts.map +1 -1
- package/dist/commands/action-acceptance.js +77 -1
- package/dist/commands/extract-snapshot-sanitizer.d.ts +2 -0
- package/dist/commands/extract-snapshot-sanitizer.d.ts.map +1 -0
- package/dist/commands/extract-snapshot-sanitizer.js +65 -0
- package/dist/commands/extract-stagehand-executor.d.ts.map +1 -1
- package/dist/commands/extract-stagehand-executor.js +33 -3
- package/dist/commands/extract.d.ts.map +1 -1
- package/dist/commands/extract.js +29 -0
- package/dist/commands/launch.js +0 -7
- package/dist/commands/observe-inventory.d.ts.map +1 -1
- package/dist/commands/observe-inventory.js +43 -0
- package/dist/commands/observe-persistence.d.ts +1 -0
- package/dist/commands/observe-persistence.d.ts.map +1 -1
- package/dist/commands/observe-persistence.js +52 -1
- package/dist/commands/observe-projection.d.ts +28 -5
- package/dist/commands/observe-projection.d.ts.map +1 -1
- package/dist/commands/observe-projection.js +189 -9
- package/dist/commands/observe-semantics.d.ts.map +1 -1
- package/dist/commands/observe-semantics.js +13 -2
- package/dist/commands/observe-surfaces.d.ts +1 -0
- package/dist/commands/observe-surfaces.d.ts.map +1 -1
- package/dist/commands/observe-surfaces.js +65 -0
- package/dist/commands/observe.d.ts.map +1 -1
- package/dist/commands/observe.js +49 -19
- package/dist/commands/observe.test-harness.d.ts +1 -0
- package/dist/commands/observe.test-harness.d.ts.map +1 -1
- package/dist/commands/observe.test-harness.js +53 -16
- package/dist/commands/semantic-observe.d.ts +2 -0
- package/dist/commands/semantic-observe.d.ts.map +1 -1
- package/dist/commands/semantic-observe.js +4 -0
- package/dist/playwright-runtime.d.ts +3 -1
- package/dist/playwright-runtime.d.ts.map +1 -1
- package/dist/playwright-runtime.js +42 -2
- package/dist/runtime-state.d.ts +3 -0
- package/dist/runtime-state.d.ts.map +1 -1
- package/dist/runtime-state.js +2 -0
- package/dist/secrets/fill-ordering.d.ts +1 -2
- package/dist/secrets/fill-ordering.d.ts.map +1 -1
- package/dist/secrets/fill-ordering.js +0 -3
- package/dist/secrets/form-matcher.d.ts.map +1 -1
- package/dist/secrets/form-matcher.js +0 -9
- package/dist/secrets/types.d.ts +0 -9
- package/dist/secrets/types.d.ts.map +1 -1
- package/dist/solver/browser-launcher.d.ts.map +1 -1
- package/dist/solver/browser-launcher.js +492 -55
- package/dist/solver/captcha-detector.d.ts.map +1 -1
- package/dist/solver/captcha-detector.js +187 -12
- package/dist/solver/captcha-runtime.d.ts.map +1 -1
- package/dist/solver/captcha-runtime.js +8 -0
- package/dist/solver/captcha-solver.d.ts +11 -1
- package/dist/solver/captcha-solver.d.ts.map +1 -1
- package/dist/solver/captcha-solver.js +11 -4
- package/dist/solver/turnstile-challenge.d.ts +3 -0
- package/dist/solver/turnstile-challenge.d.ts.map +1 -0
- package/dist/solver/turnstile-challenge.js +173 -0
- package/dist/solver/types.d.ts +10 -8
- package/dist/solver/types.d.ts.map +1 -1
- package/package.json +1 -1
- package/dist/secrets/request-guidance.d.ts +0 -24
- package/dist/secrets/request-guidance.d.ts.map +0 -1
- package/dist/secrets/request-guidance.js +0 -142
|
@@ -4,29 +4,101 @@ export async function detectCaptchas(page) {
|
|
|
4
4
|
const pageUrl = page.url();
|
|
5
5
|
return page.evaluate((url) => {
|
|
6
6
|
const found = [];
|
|
7
|
+
const seen = new Set();
|
|
7
8
|
const recaptchaEl = document.querySelector('.g-recaptcha[data-sitekey], div[data-sitekey]:not([data-hcaptcha-widget-id])');
|
|
8
9
|
if (recaptchaEl) {
|
|
9
10
|
const key = recaptchaEl.getAttribute('data-sitekey');
|
|
10
|
-
if (key)
|
|
11
|
-
|
|
11
|
+
if (key) {
|
|
12
|
+
const seenKey = ['recaptcha-v2', '', key, ''].join(':');
|
|
13
|
+
if (!seen.has(seenKey)) {
|
|
14
|
+
seen.add(seenKey);
|
|
15
|
+
found.push({ type: 'recaptcha-v2', siteKey: key, pageUrl: url });
|
|
16
|
+
}
|
|
17
|
+
}
|
|
12
18
|
}
|
|
13
19
|
const recaptchaIframe = document.querySelector('iframe[src*="recaptcha/api2"], iframe[src*="recaptcha/enterprise"]');
|
|
14
20
|
if (recaptchaIframe && found.length === 0) {
|
|
15
21
|
const match = recaptchaIframe.src.match(/[?&]k=([^&]+)/);
|
|
16
|
-
if (match?.[1])
|
|
17
|
-
|
|
22
|
+
if (match?.[1]) {
|
|
23
|
+
const seenKey = ['recaptcha-v2', '', match[1], ''].join(':');
|
|
24
|
+
if (!seen.has(seenKey)) {
|
|
25
|
+
seen.add(seenKey);
|
|
26
|
+
found.push({ type: 'recaptcha-v2', siteKey: match[1], pageUrl: url });
|
|
27
|
+
}
|
|
28
|
+
}
|
|
18
29
|
}
|
|
19
30
|
const hcaptchaEl = document.querySelector('.h-captcha[data-sitekey], div[data-hcaptcha-widget-id][data-sitekey]');
|
|
20
31
|
if (hcaptchaEl) {
|
|
21
32
|
const key = hcaptchaEl.getAttribute('data-sitekey');
|
|
22
|
-
if (key)
|
|
23
|
-
|
|
33
|
+
if (key) {
|
|
34
|
+
const seenKey = ['hcaptcha', '', key, ''].join(':');
|
|
35
|
+
if (!seen.has(seenKey)) {
|
|
36
|
+
seen.add(seenKey);
|
|
37
|
+
found.push({ type: 'hcaptcha', siteKey: key, pageUrl: url });
|
|
38
|
+
}
|
|
39
|
+
}
|
|
24
40
|
}
|
|
25
41
|
const turnstileEl = document.querySelector('.cf-turnstile[data-sitekey]');
|
|
26
42
|
if (turnstileEl) {
|
|
27
43
|
const key = turnstileEl.getAttribute('data-sitekey');
|
|
28
|
-
if (key)
|
|
29
|
-
|
|
44
|
+
if (key) {
|
|
45
|
+
const seenKey = ['turnstile', '', key, ''].join(':');
|
|
46
|
+
if (!seen.has(seenKey)) {
|
|
47
|
+
seen.add(seenKey);
|
|
48
|
+
found.push({
|
|
49
|
+
type: 'turnstile',
|
|
50
|
+
siteKey: key,
|
|
51
|
+
pageUrl: url,
|
|
52
|
+
});
|
|
53
|
+
}
|
|
54
|
+
}
|
|
55
|
+
}
|
|
56
|
+
const challengeStore = window.__agentbrowseTurnstileChallenges;
|
|
57
|
+
if (Array.isArray(challengeStore)) {
|
|
58
|
+
for (const challenge of challengeStore) {
|
|
59
|
+
const callbackId = challenge.callbackId ?? '';
|
|
60
|
+
const siteKey = challenge.siteKey ?? '';
|
|
61
|
+
const seenKey = ['turnstile', 'cloudflare-challenge', siteKey, callbackId].join(':');
|
|
62
|
+
if (!seen.has(seenKey)) {
|
|
63
|
+
seen.add(seenKey);
|
|
64
|
+
found.push({
|
|
65
|
+
type: 'turnstile',
|
|
66
|
+
variant: 'cloudflare-challenge',
|
|
67
|
+
siteKey,
|
|
68
|
+
pageUrl: url,
|
|
69
|
+
captureSource: challenge.captureSource ?? 'render-hook',
|
|
70
|
+
challengeReady: Boolean(siteKey && challenge.cData && challenge.chlPageData),
|
|
71
|
+
action: challenge.action ?? '',
|
|
72
|
+
cData: challenge.cData ?? '',
|
|
73
|
+
chlPageData: challenge.chlPageData ?? '',
|
|
74
|
+
callbackId,
|
|
75
|
+
userAgent: challenge.userAgent ?? '',
|
|
76
|
+
});
|
|
77
|
+
}
|
|
78
|
+
}
|
|
79
|
+
}
|
|
80
|
+
if (found.length === 0) {
|
|
81
|
+
const hasChallengePlatformScript = document.querySelectorAll("script[src*='/cdn-cgi/challenge-platform/']").length > 0;
|
|
82
|
+
const hasChallengeField = Array.from(document.querySelectorAll("input[name='cf-turnstile-response'], textarea[name='cf-turnstile-response']")).some((node) => {
|
|
83
|
+
const id = node.getAttribute('id') ?? '';
|
|
84
|
+
return id.startsWith('cf-chl-widget');
|
|
85
|
+
});
|
|
86
|
+
const hasCfChlOpt = Boolean(window._cf_chl_opt &&
|
|
87
|
+
typeof window._cf_chl_opt === 'object');
|
|
88
|
+
if (hasChallengePlatformScript || hasChallengeField || hasCfChlOpt) {
|
|
89
|
+
const seenKey = ['turnstile', 'cloudflare-challenge', '', ''].join(':');
|
|
90
|
+
if (!seen.has(seenKey)) {
|
|
91
|
+
seen.add(seenKey);
|
|
92
|
+
found.push({
|
|
93
|
+
type: 'turnstile',
|
|
94
|
+
variant: 'cloudflare-challenge',
|
|
95
|
+
siteKey: '',
|
|
96
|
+
pageUrl: url,
|
|
97
|
+
captureSource: 'dom-fallback',
|
|
98
|
+
challengeReady: false,
|
|
99
|
+
});
|
|
100
|
+
}
|
|
101
|
+
}
|
|
30
102
|
}
|
|
31
103
|
return found;
|
|
32
104
|
}, pageUrl);
|
|
@@ -43,10 +115,39 @@ export async function solveVisibleCaptchasWithOptions(page, solver, opts) {
|
|
|
43
115
|
if (opts?.skipCaptcha?.(captcha)) {
|
|
44
116
|
continue;
|
|
45
117
|
}
|
|
118
|
+
if (captcha.variant === 'cloudflare-challenge' && captcha.challengeReady === false) {
|
|
119
|
+
const missingParamsOutcome = {
|
|
120
|
+
captcha,
|
|
121
|
+
injected: false,
|
|
122
|
+
clicked: false,
|
|
123
|
+
verified: false,
|
|
124
|
+
error: 'challenge-params-missing',
|
|
125
|
+
};
|
|
126
|
+
opts?.onProgress?.(`[captcha] detected ${captcha.type} on ${captcha.pageUrl}, but challenge params were not captured`);
|
|
127
|
+
outcomes.push(missingParamsOutcome);
|
|
128
|
+
opts?.onCaptchaResult?.(missingParamsOutcome);
|
|
129
|
+
continue;
|
|
130
|
+
}
|
|
131
|
+
if (captcha.variant === 'cloudflare-challenge') {
|
|
132
|
+
const transportRequiredOutcome = {
|
|
133
|
+
captcha,
|
|
134
|
+
injected: false,
|
|
135
|
+
clicked: false,
|
|
136
|
+
verified: false,
|
|
137
|
+
error: 'challenge-shared-transport-required',
|
|
138
|
+
};
|
|
139
|
+
opts?.onProgress?.(`[captcha] detected ${captcha.type} on ${captcha.pageUrl}, but Cloudflare challenge pages need shared browser/solver transport and that orchestration path is still deferred`);
|
|
140
|
+
outcomes.push(transportRequiredOutcome);
|
|
141
|
+
opts?.onCaptchaResult?.(transportRequiredOutcome);
|
|
142
|
+
continue;
|
|
143
|
+
}
|
|
46
144
|
opts?.onProgress?.(`[captcha] detected ${captcha.type} on ${captcha.pageUrl}, sending to solver (timeout ${Math.ceil(timeoutMs / 1000)}s)`);
|
|
47
145
|
try {
|
|
146
|
+
const solveRequest = toSolverRequest(captcha);
|
|
48
147
|
const maybeToken = await Promise.race([
|
|
49
|
-
|
|
148
|
+
solveRequest
|
|
149
|
+
? solver.solve(captcha.type, captcha.siteKey, captcha.pageUrl, solveRequest)
|
|
150
|
+
: solver.solve(captcha.type, captcha.siteKey, captcha.pageUrl),
|
|
50
151
|
sleep(timeoutMs).then(() => SOLVE_TIMEOUT),
|
|
51
152
|
]);
|
|
52
153
|
if (maybeToken === SOLVE_TIMEOUT) {
|
|
@@ -62,8 +163,9 @@ export async function solveVisibleCaptchasWithOptions(page, solver, opts) {
|
|
|
62
163
|
opts?.onCaptchaResult?.(timeoutOutcome);
|
|
63
164
|
continue;
|
|
64
165
|
}
|
|
65
|
-
const
|
|
66
|
-
await
|
|
166
|
+
const solution = maybeToken;
|
|
167
|
+
await applySolverUserAgent(page, solution.userAgent);
|
|
168
|
+
await injectCaptchaToken(page, captcha, solution.token);
|
|
67
169
|
let verified = await verifyCaptchaResolved(page, captcha);
|
|
68
170
|
let clicked = false;
|
|
69
171
|
// Click only as last resort — it triggers a new Google challenge flow,
|
|
@@ -191,6 +293,7 @@ async function injectCaptchaToken(page, captcha, token) {
|
|
|
191
293
|
}
|
|
192
294
|
}
|
|
193
295
|
else if (info.type === 'turnstile') {
|
|
296
|
+
const win = window;
|
|
194
297
|
const selectors = [
|
|
195
298
|
"input[name='cf-turnstile-response']",
|
|
196
299
|
"textarea[name='cf-turnstile-response']",
|
|
@@ -204,8 +307,23 @@ async function injectCaptchaToken(page, captcha, token) {
|
|
|
204
307
|
node.dispatchEvent(new Event('change', { bubbles: true }));
|
|
205
308
|
}
|
|
206
309
|
}
|
|
310
|
+
if (info.variant === 'cloudflare-challenge' && info.callbackId) {
|
|
311
|
+
const callback = win.__agentbrowseTurnstileCallbacks?.[info.callbackId];
|
|
312
|
+
if (typeof callback === 'function') {
|
|
313
|
+
callback(info.token);
|
|
314
|
+
win.__agentbrowseTurnstileSolved = {
|
|
315
|
+
...(win.__agentbrowseTurnstileSolved ?? {}),
|
|
316
|
+
[info.callbackId]: info.token,
|
|
317
|
+
};
|
|
318
|
+
}
|
|
319
|
+
}
|
|
207
320
|
}
|
|
208
|
-
}, {
|
|
321
|
+
}, {
|
|
322
|
+
type: captcha.type,
|
|
323
|
+
token,
|
|
324
|
+
variant: captcha.variant,
|
|
325
|
+
callbackId: captcha.callbackId,
|
|
326
|
+
});
|
|
209
327
|
}
|
|
210
328
|
function recaptchaAnchorFrames(page, siteKey) {
|
|
211
329
|
const all = page.frames().filter((frame) => frame.url().includes('/recaptcha/api2/anchor'));
|
|
@@ -400,6 +518,9 @@ async function verifyCaptchaResolved(page, captcha) {
|
|
|
400
518
|
"input[name*='hcaptcha-response']",
|
|
401
519
|
]);
|
|
402
520
|
case 'turnstile':
|
|
521
|
+
if (captcha.variant === 'cloudflare-challenge') {
|
|
522
|
+
return verifyCloudflareChallengeCleared(page);
|
|
523
|
+
}
|
|
403
524
|
return hasTokenInAnyFrame(page, [
|
|
404
525
|
"input[name='cf-turnstile-response']",
|
|
405
526
|
"textarea[name='cf-turnstile-response']",
|
|
@@ -407,6 +528,36 @@ async function verifyCaptchaResolved(page, captcha) {
|
|
|
407
528
|
]);
|
|
408
529
|
}
|
|
409
530
|
}
|
|
531
|
+
async function verifyCloudflareChallengeCleared(page) {
|
|
532
|
+
const deadline = Date.now() + 10_000;
|
|
533
|
+
while (Date.now() < deadline) {
|
|
534
|
+
try {
|
|
535
|
+
const stillChallenge = await page.evaluate(() => {
|
|
536
|
+
const hasChallengePlatformScript = document.querySelectorAll("script[src*='/cdn-cgi/challenge-platform/']").length > 0;
|
|
537
|
+
const hasChallengeField = Array.from(document.querySelectorAll("input[name='cf-turnstile-response'], textarea[name='cf-turnstile-response']")).some((node) => {
|
|
538
|
+
const id = node.getAttribute('id') ?? '';
|
|
539
|
+
return id.startsWith('cf-chl-widget');
|
|
540
|
+
});
|
|
541
|
+
const hasCfChlOpt = Boolean(window._cf_chl_opt &&
|
|
542
|
+
typeof window._cf_chl_opt === 'object');
|
|
543
|
+
const bodyText = document.body?.innerText ?? '';
|
|
544
|
+
return (hasChallengePlatformScript ||
|
|
545
|
+
hasChallengeField ||
|
|
546
|
+
hasCfChlOpt ||
|
|
547
|
+
document.title === 'Just a moment...' ||
|
|
548
|
+
bodyText.includes('Just a moment'));
|
|
549
|
+
});
|
|
550
|
+
if (!stillChallenge) {
|
|
551
|
+
return true;
|
|
552
|
+
}
|
|
553
|
+
}
|
|
554
|
+
catch {
|
|
555
|
+
// Page may be navigating between challenge and destination; retry briefly.
|
|
556
|
+
}
|
|
557
|
+
await sleep(500);
|
|
558
|
+
}
|
|
559
|
+
return false;
|
|
560
|
+
}
|
|
410
561
|
export function setupCaptchaMonitor(page, solver) {
|
|
411
562
|
let solving = false;
|
|
412
563
|
const checkAndSolve = async () => {
|
|
@@ -461,3 +612,27 @@ function formatSolveError(error) {
|
|
|
461
612
|
return String(error);
|
|
462
613
|
}
|
|
463
614
|
}
|
|
615
|
+
function toSolverRequest(captcha) {
|
|
616
|
+
if (captcha.type !== 'turnstile' || captcha.variant !== 'cloudflare-challenge') {
|
|
617
|
+
return undefined;
|
|
618
|
+
}
|
|
619
|
+
return {
|
|
620
|
+
action: captcha.action,
|
|
621
|
+
data: captcha.cData,
|
|
622
|
+
pagedata: captcha.chlPageData,
|
|
623
|
+
userAgent: captcha.userAgent,
|
|
624
|
+
};
|
|
625
|
+
}
|
|
626
|
+
async function applySolverUserAgent(page, userAgent) {
|
|
627
|
+
if (!userAgent || !userAgent.trim())
|
|
628
|
+
return;
|
|
629
|
+
const client = await page.createCDPSession();
|
|
630
|
+
try {
|
|
631
|
+
await client.send('Network.setUserAgentOverride', {
|
|
632
|
+
userAgent,
|
|
633
|
+
});
|
|
634
|
+
}
|
|
635
|
+
finally {
|
|
636
|
+
await client.detach().catch(() => { });
|
|
637
|
+
}
|
|
638
|
+
}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"captcha-runtime.d.ts","sourceRoot":"","sources":["../../src/solver/captcha-runtime.ts"],"names":[],"mappings":"AAKA,MAAM,MAAM,yBAAyB,GAAG;IACtC,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,cAAc,CAAC,EAAE,MAAM,CAAC;IACxB,cAAc,CAAC,EAAE,MAAM,CAAC;IACxB,gBAAgB,CAAC,EAAE,MAAM,CAAC;IAC1B,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,UAAU,CAAC,EAAE,CAAC,OAAO,EAAE,MAAM,KAAK,IAAI,CAAC;CACxC,CAAC;AAEF,MAAM,MAAM,wBAAwB,GAAG;IACrC,MAAM,EAAE,MAAM,CAAC;IACf,QAAQ,EAAE,MAAM,CAAC;IACjB,UAAU,EAAE,MAAM,CAAC;IACnB,kBAAkB,EAAE,MAAM,EAAE,CAAC;IAC7B,QAAQ,EAAE,MAAM,CAAC;IACjB,QAAQ,EAAE,OAAO,CAAC;CACnB,CAAC;AAMF,wBAAsB,kBAAkB,CACtC,MAAM,EAAE,MAAM,EACd,MAAM,EAAE,MAAM,EACd,IAAI,CAAC,EAAE,yBAAyB,GAC/B,OAAO,CAAC,wBAAwB,CAAC,
|
|
1
|
+
{"version":3,"file":"captcha-runtime.d.ts","sourceRoot":"","sources":["../../src/solver/captcha-runtime.ts"],"names":[],"mappings":"AAKA,MAAM,MAAM,yBAAyB,GAAG;IACtC,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,cAAc,CAAC,EAAE,MAAM,CAAC;IACxB,cAAc,CAAC,EAAE,MAAM,CAAC;IACxB,gBAAgB,CAAC,EAAE,MAAM,CAAC;IAC1B,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,UAAU,CAAC,EAAE,CAAC,OAAO,EAAE,MAAM,KAAK,IAAI,CAAC;CACxC,CAAC;AAEF,MAAM,MAAM,wBAAwB,GAAG;IACrC,MAAM,EAAE,MAAM,CAAC;IACf,QAAQ,EAAE,MAAM,CAAC;IACjB,UAAU,EAAE,MAAM,CAAC;IACnB,kBAAkB,EAAE,MAAM,EAAE,CAAC;IAC7B,QAAQ,EAAE,MAAM,CAAC;IACjB,QAAQ,EAAE,OAAO,CAAC;CACnB,CAAC;AAMF,wBAAsB,kBAAkB,CACtC,MAAM,EAAE,MAAM,EACd,MAAM,EAAE,MAAM,EACd,IAAI,CAAC,EAAE,yBAAyB,GAC/B,OAAO,CAAC,wBAAwB,CAAC,CA0HnC"}
|
|
@@ -58,6 +58,8 @@ export async function solveCaptchasByCdp(cdpUrl, apiKey, opts) {
|
|
|
58
58
|
onProgress,
|
|
59
59
|
skipCaptcha: (captcha) => solvedKeys.has(captchaKey(captcha)),
|
|
60
60
|
});
|
|
61
|
+
const hasMissingParamsChallenge = outcomes.some((outcome) => outcome.error === 'challenge-params-missing');
|
|
62
|
+
const hasSharedTransportRequiredChallenge = outcomes.some((outcome) => outcome.error === 'challenge-shared-transport-required');
|
|
61
63
|
for (const outcome of outcomes) {
|
|
62
64
|
const key = captchaKey(outcome.captcha);
|
|
63
65
|
if (outcome.injected || outcome.verified) {
|
|
@@ -69,6 +71,12 @@ export async function solveCaptchasByCdp(cdpUrl, apiKey, opts) {
|
|
|
69
71
|
}
|
|
70
72
|
}
|
|
71
73
|
const unsolvedAfter = unsolvedBefore.filter((captcha) => !solvedKeys.has(captchaKey(captcha)));
|
|
74
|
+
if (hasMissingParamsChallenge) {
|
|
75
|
+
return finalizeResult(solved, detectedKeys, verifiedKeys, false, onProgress);
|
|
76
|
+
}
|
|
77
|
+
if (hasSharedTransportRequiredChallenge) {
|
|
78
|
+
return finalizeResult(solved, detectedKeys, verifiedKeys, false, onProgress);
|
|
79
|
+
}
|
|
72
80
|
if (unsolvedAfter.length === 0) {
|
|
73
81
|
return finalizeResult(solved, detectedKeys, verifiedKeys, false, onProgress);
|
|
74
82
|
}
|
|
@@ -6,6 +6,16 @@ export type CaptchaSolverConfig = {
|
|
|
6
6
|
taskPollIntervalMs?: number;
|
|
7
7
|
taskTimeoutMs?: number;
|
|
8
8
|
};
|
|
9
|
+
export type CaptchaSolveRequest = {
|
|
10
|
+
action?: string;
|
|
11
|
+
data?: string;
|
|
12
|
+
pagedata?: string;
|
|
13
|
+
userAgent?: string;
|
|
14
|
+
};
|
|
15
|
+
export type CaptchaSolveResult = {
|
|
16
|
+
token: string;
|
|
17
|
+
userAgent?: string;
|
|
18
|
+
};
|
|
9
19
|
/**
|
|
10
20
|
* Backend CAPTCHA gateway client. No direct provider keys are used in CLI.
|
|
11
21
|
*/
|
|
@@ -16,7 +26,7 @@ export declare class CaptchaSolver {
|
|
|
16
26
|
private readonly taskPollIntervalMs;
|
|
17
27
|
private readonly taskTimeoutMs;
|
|
18
28
|
constructor(config: CaptchaSolverConfig);
|
|
19
|
-
solve(type: CaptchaType, siteKey: string, pageUrl: string): Promise<
|
|
29
|
+
solve(type: CaptchaType, siteKey: string, pageUrl: string, request?: CaptchaSolveRequest): Promise<CaptchaSolveResult>;
|
|
20
30
|
private createTask;
|
|
21
31
|
private getTaskStatus;
|
|
22
32
|
private request;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"captcha-solver.d.ts","sourceRoot":"","sources":["../../src/solver/captcha-solver.ts"],"names":[],"mappings":"AAAA,MAAM,MAAM,WAAW,GAAG,cAAc,GAAG,UAAU,GAAG,WAAW,CAAC;AAEpE,MAAM,MAAM,mBAAmB,GAAG;IAChC,MAAM,EAAE,MAAM,CAAC;IACf,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,gBAAgB,CAAC,EAAE,MAAM,CAAC;IAC1B,kBAAkB,CAAC,EAAE,MAAM,CAAC;IAC5B,aAAa,CAAC,EAAE,MAAM,CAAC;CACxB,CAAC;
|
|
1
|
+
{"version":3,"file":"captcha-solver.d.ts","sourceRoot":"","sources":["../../src/solver/captcha-solver.ts"],"names":[],"mappings":"AAAA,MAAM,MAAM,WAAW,GAAG,cAAc,GAAG,UAAU,GAAG,WAAW,CAAC;AAEpE,MAAM,MAAM,mBAAmB,GAAG;IAChC,MAAM,EAAE,MAAM,CAAC;IACf,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,gBAAgB,CAAC,EAAE,MAAM,CAAC;IAC1B,kBAAkB,CAAC,EAAE,MAAM,CAAC;IAC5B,aAAa,CAAC,EAAE,MAAM,CAAC;CACxB,CAAC;AAiBF,MAAM,MAAM,mBAAmB,GAAG;IAChC,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,SAAS,CAAC,EAAE,MAAM,CAAC;CACpB,CAAC;AAEF,MAAM,MAAM,kBAAkB,GAAG;IAC/B,KAAK,EAAE,MAAM,CAAC;IACd,SAAS,CAAC,EAAE,MAAM,CAAC;CACpB,CAAC;AAMF;;GAEG;AACH,qBAAa,aAAa;IACxB,OAAO,CAAC,QAAQ,CAAC,MAAM,CAAS;IAChC,OAAO,CAAC,QAAQ,CAAC,MAAM,CAAS;IAChC,OAAO,CAAC,QAAQ,CAAC,gBAAgB,CAAS;IAC1C,OAAO,CAAC,QAAQ,CAAC,kBAAkB,CAAS;IAC5C,OAAO,CAAC,QAAQ,CAAC,aAAa,CAAS;gBAE3B,MAAM,EAAE,mBAAmB;IAejC,KAAK,CACT,IAAI,EAAE,WAAW,EACjB,OAAO,EAAE,MAAM,EACf,OAAO,EAAE,MAAM,EACf,OAAO,CAAC,EAAE,mBAAmB,GAC5B,OAAO,CAAC,kBAAkB,CAAC;YAqBhB,UAAU;YAiBV,aAAa;YAOb,OAAO;CAsCtB"}
|
|
@@ -23,14 +23,17 @@ export class CaptchaSolver {
|
|
|
23
23
|
throw new Error('CaptchaSolver: apiUrl is required (set AGENTPAY_API_URL)');
|
|
24
24
|
}
|
|
25
25
|
}
|
|
26
|
-
async solve(type, siteKey, pageUrl) {
|
|
27
|
-
const task = await this.createTask(type, siteKey, pageUrl);
|
|
26
|
+
async solve(type, siteKey, pageUrl, request) {
|
|
27
|
+
const task = await this.createTask(type, siteKey, pageUrl, request);
|
|
28
28
|
const deadline = Date.now() + this.taskTimeoutMs;
|
|
29
29
|
while (Date.now() < deadline) {
|
|
30
30
|
await sleep(this.taskPollIntervalMs);
|
|
31
31
|
const status = await this.getTaskStatus(task.task_id);
|
|
32
32
|
if (status.status === 'ready' && status.token) {
|
|
33
|
-
return
|
|
33
|
+
return {
|
|
34
|
+
token: status.token,
|
|
35
|
+
userAgent: status.user_agent,
|
|
36
|
+
};
|
|
34
37
|
}
|
|
35
38
|
if (status.status === 'failed') {
|
|
36
39
|
throw new Error(`CAPTCHA solving failed: ${status.error || 'provider error'}`);
|
|
@@ -38,11 +41,15 @@ export class CaptchaSolver {
|
|
|
38
41
|
}
|
|
39
42
|
throw new Error(`CAPTCHA solving timed out after ${Math.ceil(this.taskTimeoutMs / 1000)}s`);
|
|
40
43
|
}
|
|
41
|
-
async createTask(type, siteKey, pageUrl) {
|
|
44
|
+
async createTask(type, siteKey, pageUrl, request) {
|
|
42
45
|
return this.request('POST', '/tools/captcha/tasks', {
|
|
43
46
|
type,
|
|
44
47
|
site_key: siteKey,
|
|
45
48
|
page_url: pageUrl,
|
|
49
|
+
action: request?.action,
|
|
50
|
+
data: request?.data,
|
|
51
|
+
pagedata: request?.pagedata,
|
|
52
|
+
user_agent: request?.userAgent,
|
|
46
53
|
});
|
|
47
54
|
}
|
|
48
55
|
async getTaskStatus(taskId) {
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"turnstile-challenge.d.ts","sourceRoot":"","sources":["../../src/solver/turnstile-challenge.ts"],"names":[],"mappings":"AAKA,wBAAgB,qBAAqB,CAAC,GAAG,EAAE,MAAM,GAAG,OAAO,CAY1D;AAED,wBAAgB,2BAA2B,CAAC,WAAW,EAAE,MAAM,GAAG,MAAM,CA6JvE"}
|
|
@@ -0,0 +1,173 @@
|
|
|
1
|
+
const TURNSTILE_HOST = 'challenges.cloudflare.com';
|
|
2
|
+
const TURNSTILE_PATH_FRAGMENT = '/turnstile/';
|
|
3
|
+
const TURNSTILE_API_SUFFIX = '/api.js';
|
|
4
|
+
const AGENTBROWSE_PASSTHROUGH_PARAM = '__agentbrowse_passthrough';
|
|
5
|
+
export function isTurnstileApiRequest(url) {
|
|
6
|
+
try {
|
|
7
|
+
const parsed = new URL(url);
|
|
8
|
+
return (parsed.hostname === TURNSTILE_HOST &&
|
|
9
|
+
parsed.pathname.includes(TURNSTILE_PATH_FRAGMENT) &&
|
|
10
|
+
parsed.pathname.endsWith(TURNSTILE_API_SUFFIX) &&
|
|
11
|
+
!parsed.searchParams.has(AGENTBROWSE_PASSTHROUGH_PARAM));
|
|
12
|
+
}
|
|
13
|
+
catch {
|
|
14
|
+
return false;
|
|
15
|
+
}
|
|
16
|
+
}
|
|
17
|
+
export function buildTurnstileApiShimSource(originalUrl) {
|
|
18
|
+
const serializedUrl = JSON.stringify(originalUrl);
|
|
19
|
+
return `
|
|
20
|
+
(function () {
|
|
21
|
+
const originalUrl = ${serializedUrl};
|
|
22
|
+
const passthroughParam = ${JSON.stringify(AGENTBROWSE_PASSTHROUGH_PARAM)};
|
|
23
|
+
const callbacksKey = '__agentbrowseTurnstileCallbacks';
|
|
24
|
+
const challengesKey = '__agentbrowseTurnstileChallenges';
|
|
25
|
+
const pendingRendersKey = '__agentbrowseTurnstilePendingRenders';
|
|
26
|
+
const scriptLoadKey = '__agentbrowseTurnstileRealScriptLoading';
|
|
27
|
+
const stateKey = '__agentbrowseTurnstileState';
|
|
28
|
+
|
|
29
|
+
function ensureStores(win) {
|
|
30
|
+
if (!Array.isArray(win[challengesKey])) {
|
|
31
|
+
win[challengesKey] = [];
|
|
32
|
+
}
|
|
33
|
+
if (!win[callbacksKey] || typeof win[callbacksKey] !== 'object') {
|
|
34
|
+
win[callbacksKey] = {};
|
|
35
|
+
}
|
|
36
|
+
if (!win[stateKey] || typeof win[stateKey] !== 'object') {
|
|
37
|
+
win[stateKey] = { nextCallbackId: 1 };
|
|
38
|
+
}
|
|
39
|
+
if (!Array.isArray(win[pendingRendersKey])) {
|
|
40
|
+
win[pendingRendersKey] = [];
|
|
41
|
+
}
|
|
42
|
+
}
|
|
43
|
+
|
|
44
|
+
function addPassthroughParam(url) {
|
|
45
|
+
const parsed = new URL(url);
|
|
46
|
+
parsed.searchParams.set(passthroughParam, '1');
|
|
47
|
+
parsed.searchParams.delete('onload');
|
|
48
|
+
return parsed.toString();
|
|
49
|
+
}
|
|
50
|
+
|
|
51
|
+
function appendRealScript(doc, win, src, stubRender) {
|
|
52
|
+
if (win[scriptLoadKey]) {
|
|
53
|
+
return;
|
|
54
|
+
}
|
|
55
|
+
win[scriptLoadKey] = true;
|
|
56
|
+
const script = doc.createElement('script');
|
|
57
|
+
script.src = addPassthroughParam(src);
|
|
58
|
+
script.async = true;
|
|
59
|
+
script.onload = function () {
|
|
60
|
+
win[scriptLoadKey] = false;
|
|
61
|
+
const pendingRenders = Array.isArray(win[pendingRendersKey]) ? win[pendingRendersKey].slice() : [];
|
|
62
|
+
win[pendingRendersKey] = [];
|
|
63
|
+
const realTurnstile = win.turnstile;
|
|
64
|
+
if (!realTurnstile || typeof realTurnstile.render !== 'function' || realTurnstile.render === stubRender) {
|
|
65
|
+
return;
|
|
66
|
+
}
|
|
67
|
+
for (const entry of pendingRenders) {
|
|
68
|
+
try {
|
|
69
|
+
realTurnstile.render(entry.container, entry.options);
|
|
70
|
+
} catch {
|
|
71
|
+
// Preserve page execution if passthrough replay fails.
|
|
72
|
+
}
|
|
73
|
+
}
|
|
74
|
+
};
|
|
75
|
+
(doc.head || doc.documentElement).appendChild(script);
|
|
76
|
+
}
|
|
77
|
+
|
|
78
|
+
function notifyOnload(win, onloadName) {
|
|
79
|
+
if (!onloadName) return;
|
|
80
|
+
const current = win[onloadName];
|
|
81
|
+
if (typeof current === 'function') {
|
|
82
|
+
current();
|
|
83
|
+
return;
|
|
84
|
+
}
|
|
85
|
+
|
|
86
|
+
try {
|
|
87
|
+
let assignedValue;
|
|
88
|
+
Object.defineProperty(win, onloadName, {
|
|
89
|
+
configurable: true,
|
|
90
|
+
enumerable: true,
|
|
91
|
+
get: function () {
|
|
92
|
+
return assignedValue;
|
|
93
|
+
},
|
|
94
|
+
set: function (value) {
|
|
95
|
+
assignedValue = value;
|
|
96
|
+
if (typeof value === 'function') {
|
|
97
|
+
value();
|
|
98
|
+
}
|
|
99
|
+
},
|
|
100
|
+
});
|
|
101
|
+
} catch {
|
|
102
|
+
// Ignore non-configurable global callback names.
|
|
103
|
+
}
|
|
104
|
+
}
|
|
105
|
+
|
|
106
|
+
const win = window;
|
|
107
|
+
const doc = document;
|
|
108
|
+
const parsedUrl = new URL(originalUrl);
|
|
109
|
+
const onloadName = parsedUrl.searchParams.get('onload') || '';
|
|
110
|
+
ensureStores(win);
|
|
111
|
+
const callbacks = win[callbacksKey];
|
|
112
|
+
const challenges = win[challengesKey];
|
|
113
|
+
const pendingRenders = win[pendingRendersKey];
|
|
114
|
+
const state = win[stateKey];
|
|
115
|
+
win.__agentbrowseTurnstileShimInstalled = true;
|
|
116
|
+
const userAgent = (win.navigator && typeof win.navigator.userAgent === 'string')
|
|
117
|
+
? win.navigator.userAgent
|
|
118
|
+
: '';
|
|
119
|
+
|
|
120
|
+
const stubRender = function (container, options) {
|
|
121
|
+
const isChallenge = Boolean(
|
|
122
|
+
options && (
|
|
123
|
+
(typeof options.cData === 'string' && options.cData) ||
|
|
124
|
+
(typeof options.chlPageData === 'string' && options.chlPageData)
|
|
125
|
+
)
|
|
126
|
+
);
|
|
127
|
+
|
|
128
|
+
if (!isChallenge) {
|
|
129
|
+
state.lastShimMode = 'passthrough';
|
|
130
|
+
pendingRenders.push({ container: container, options: options });
|
|
131
|
+
appendRealScript(doc, win, originalUrl, stubRender);
|
|
132
|
+
return 'agentbrowse-turnstile-passthrough';
|
|
133
|
+
}
|
|
134
|
+
|
|
135
|
+
const callbackId = typeof options.callback === 'function'
|
|
136
|
+
? 'cf-turnstile-callback-' + String(state.nextCallbackId || 1)
|
|
137
|
+
: '';
|
|
138
|
+
if (callbackId) {
|
|
139
|
+
callbacks[callbackId] = options.callback;
|
|
140
|
+
state.nextCallbackId = (state.nextCallbackId || 1) + 1;
|
|
141
|
+
}
|
|
142
|
+
|
|
143
|
+
challenges.push({
|
|
144
|
+
siteKey: typeof options.sitekey === 'string'
|
|
145
|
+
? options.sitekey
|
|
146
|
+
: typeof options.siteKey === 'string'
|
|
147
|
+
? options.siteKey
|
|
148
|
+
: '',
|
|
149
|
+
action: typeof options.action === 'string' ? options.action : '',
|
|
150
|
+
cData: typeof options.cData === 'string' ? options.cData : '',
|
|
151
|
+
chlPageData: typeof options.chlPageData === 'string' ? options.chlPageData : '',
|
|
152
|
+
callbackId: callbackId,
|
|
153
|
+
userAgent: userAgent,
|
|
154
|
+
captureSource: 'api-shim',
|
|
155
|
+
});
|
|
156
|
+
state.lastShimMode = 'challenge-captured';
|
|
157
|
+
|
|
158
|
+
return 'agentbrowse-turnstile-challenge';
|
|
159
|
+
};
|
|
160
|
+
|
|
161
|
+
win.turnstile = {
|
|
162
|
+
render: stubRender,
|
|
163
|
+
execute: function () {
|
|
164
|
+
return 'agentbrowse-turnstile-challenge';
|
|
165
|
+
},
|
|
166
|
+
reset: function () {},
|
|
167
|
+
remove: function () {},
|
|
168
|
+
};
|
|
169
|
+
|
|
170
|
+
notifyOnload(win, onloadName);
|
|
171
|
+
})();
|
|
172
|
+
`;
|
|
173
|
+
}
|
package/dist/solver/types.d.ts
CHANGED
|
@@ -37,19 +37,23 @@ export type SolverConfig = {
|
|
|
37
37
|
};
|
|
38
38
|
defaults?: {
|
|
39
39
|
headless?: boolean;
|
|
40
|
-
captchaAutoSolve?: boolean;
|
|
41
40
|
};
|
|
42
41
|
};
|
|
43
42
|
export type CaptchaType = 'recaptcha-v2' | 'hcaptcha' | 'turnstile';
|
|
43
|
+
export type TurnstileVariant = 'standalone' | 'cloudflare-challenge';
|
|
44
|
+
export type TurnstileCaptureSource = 'render-hook' | 'api-shim' | 'dom-fallback';
|
|
44
45
|
export type DetectedCaptcha = {
|
|
45
46
|
type: CaptchaType;
|
|
46
47
|
siteKey: string;
|
|
47
48
|
pageUrl: string;
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
49
|
+
variant?: TurnstileVariant;
|
|
50
|
+
captureSource?: TurnstileCaptureSource;
|
|
51
|
+
challengeReady?: boolean;
|
|
52
|
+
action?: string;
|
|
53
|
+
cData?: string;
|
|
54
|
+
chlPageData?: string;
|
|
55
|
+
callbackId?: string;
|
|
56
|
+
userAgent?: string;
|
|
53
57
|
};
|
|
54
58
|
export type LaunchOptions = {
|
|
55
59
|
headless?: boolean;
|
|
@@ -60,7 +64,5 @@ export type LaunchOptions = {
|
|
|
60
64
|
width: number;
|
|
61
65
|
height: number;
|
|
62
66
|
};
|
|
63
|
-
captchaInitialSolveTimeoutMs?: number;
|
|
64
|
-
captchaSolver?: CaptchaSolverOptions;
|
|
65
67
|
};
|
|
66
68
|
//# sourceMappingURL=types.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../../src/solver/types.ts"],"names":[],"mappings":"AAAA,MAAM,MAAM,kBAAkB,GAAG;IAC/B,SAAS,EAAE,MAAM,CAAC;IAClB,QAAQ,EAAE;QAAE,KAAK,EAAE,MAAM,CAAC;QAAC,MAAM,EAAE,MAAM,CAAA;KAAE,CAAC;IAC5C,MAAM,EAAE;QAAE,KAAK,EAAE,MAAM,CAAC;QAAC,MAAM,EAAE,MAAM,CAAC;QAAC,UAAU,EAAE,MAAM,CAAA;KAAE,CAAC;IAC9D,QAAQ,EAAE,MAAM,CAAC;IACjB,MAAM,EAAE,MAAM,CAAC;IACf,QAAQ,EAAE,MAAM,CAAC;IACjB,WAAW,EAAE,MAAM,CAAC;IACpB,aAAa,EAAE,MAAM,CAAC;IACtB,mBAAmB,EAAE,MAAM,CAAC;IAC5B,YAAY,EAAE,MAAM,CAAC;IACrB,KAAK,CAAC,EAAE,WAAW,CAAC;IACpB,SAAS,EAAE,MAAM,CAAC;CACnB,CAAC;AAEF,MAAM,MAAM,WAAW,GAAG;IACxB,MAAM,EAAE,MAAM,CAAC;IACf,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,QAAQ,CAAC,EAAE,MAAM,CAAC;CACnB,CAAC;AAEF,MAAM,MAAM,WAAW,GAAG;IACxB,IAAI,EAAE,MAAM,CAAC;IACb,WAAW,EAAE,kBAAkB,CAAC;IAChC,WAAW,EAAE,MAAM,CAAC;IACpB,eAAe,EAAE,MAAM,CAAC;CACzB,CAAC;AAEF,MAAM,MAAM,YAAY,GAAG;IACzB,QAAQ,CAAC,EAAE;QACT,MAAM,CAAC,EAAE,MAAM,CAAC;QAChB,MAAM,CAAC,EAAE,MAAM,CAAC;KACjB,CAAC;IACF,QAAQ,CAAC,EAAE;QACT,QAAQ,CAAC,EAAE,OAAO,CAAC;
|
|
1
|
+
{"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../../src/solver/types.ts"],"names":[],"mappings":"AAAA,MAAM,MAAM,kBAAkB,GAAG;IAC/B,SAAS,EAAE,MAAM,CAAC;IAClB,QAAQ,EAAE;QAAE,KAAK,EAAE,MAAM,CAAC;QAAC,MAAM,EAAE,MAAM,CAAA;KAAE,CAAC;IAC5C,MAAM,EAAE;QAAE,KAAK,EAAE,MAAM,CAAC;QAAC,MAAM,EAAE,MAAM,CAAC;QAAC,UAAU,EAAE,MAAM,CAAA;KAAE,CAAC;IAC9D,QAAQ,EAAE,MAAM,CAAC;IACjB,MAAM,EAAE,MAAM,CAAC;IACf,QAAQ,EAAE,MAAM,CAAC;IACjB,WAAW,EAAE,MAAM,CAAC;IACpB,aAAa,EAAE,MAAM,CAAC;IACtB,mBAAmB,EAAE,MAAM,CAAC;IAC5B,YAAY,EAAE,MAAM,CAAC;IACrB,KAAK,CAAC,EAAE,WAAW,CAAC;IACpB,SAAS,EAAE,MAAM,CAAC;CACnB,CAAC;AAEF,MAAM,MAAM,WAAW,GAAG;IACxB,MAAM,EAAE,MAAM,CAAC;IACf,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,QAAQ,CAAC,EAAE,MAAM,CAAC;CACnB,CAAC;AAEF,MAAM,MAAM,WAAW,GAAG;IACxB,IAAI,EAAE,MAAM,CAAC;IACb,WAAW,EAAE,kBAAkB,CAAC;IAChC,WAAW,EAAE,MAAM,CAAC;IACpB,eAAe,EAAE,MAAM,CAAC;CACzB,CAAC;AAEF,MAAM,MAAM,YAAY,GAAG;IACzB,QAAQ,CAAC,EAAE;QACT,MAAM,CAAC,EAAE,MAAM,CAAC;QAChB,MAAM,CAAC,EAAE,MAAM,CAAC;KACjB,CAAC;IACF,QAAQ,CAAC,EAAE;QACT,QAAQ,CAAC,EAAE,OAAO,CAAC;KACpB,CAAC;CACH,CAAC;AAEF,MAAM,MAAM,WAAW,GAAG,cAAc,GAAG,UAAU,GAAG,WAAW,CAAC;AAEpE,MAAM,MAAM,gBAAgB,GAAG,YAAY,GAAG,sBAAsB,CAAC;AACrE,MAAM,MAAM,sBAAsB,GAAG,aAAa,GAAG,UAAU,GAAG,cAAc,CAAC;AAEjF,MAAM,MAAM,eAAe,GAAG;IAC5B,IAAI,EAAE,WAAW,CAAC;IAClB,OAAO,EAAE,MAAM,CAAC;IAChB,OAAO,EAAE,MAAM,CAAC;IAChB,OAAO,CAAC,EAAE,gBAAgB,CAAC;IAC3B,aAAa,CAAC,EAAE,sBAAsB,CAAC;IACvC,cAAc,CAAC,EAAE,OAAO,CAAC;IACzB,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,KAAK,CAAC,EAAE,MAAM,CAAC;IACf,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,UAAU,CAAC,EAAE,MAAM,CAAC;IACpB,SAAS,CAAC,EAAE,MAAM,CAAC;CACpB,CAAC;AAEF,MAAM,MAAM,aAAa,GAAG;IAC1B,QAAQ,CAAC,EAAE,OAAO,CAAC;IACnB,GAAG,CAAC,EAAE,MAAM,CAAC;IACb,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB,cAAc,CAAC,EAAE,MAAM,CAAC;IACxB,UAAU,CAAC,EAAE;QACX,KAAK,EAAE,MAAM,CAAC;QACd,MAAM,EAAE,MAAM,CAAC;KAChB,CAAC;CACH,CAAC"}
|
package/package.json
CHANGED
|
@@ -1,24 +0,0 @@
|
|
|
1
|
-
import type { TargetDescriptor } from '../runtime-state.js';
|
|
2
|
-
import type { FillableFormFieldBinding, FillableFormGuidanceHint, FillableFormRecommendedTiming, StoredSecretFieldKey } from './types.js';
|
|
3
|
-
declare function collectVisibleFieldEvidence(fields: ReadonlyArray<FillableFormFieldBinding>, targetByRef: ReadonlyMap<string, TargetDescriptor>): string;
|
|
4
|
-
declare function collectBlockingValidationEvidence(fields: ReadonlyArray<FillableFormFieldBinding>, targetByRef: ReadonlyMap<string, TargetDescriptor>): string[];
|
|
5
|
-
declare function collectPassiveRequiredEvidence(fields: ReadonlyArray<FillableFormFieldBinding>, targetByRef: ReadonlyMap<string, TargetDescriptor>): string[];
|
|
6
|
-
declare function hasCorePaymentCardFields(fieldKeys: ReadonlySet<StoredSecretFieldKey>): boolean;
|
|
7
|
-
declare function looksLikePrimaryLoginForm(fieldKeys: ReadonlySet<StoredSecretFieldKey>): boolean;
|
|
8
|
-
declare function looksLikeStrongIdentityForm(fieldKeys: ReadonlySet<StoredSecretFieldKey>): boolean;
|
|
9
|
-
export declare function buildFillableFormGuidance(params: {
|
|
10
|
-
purpose: string;
|
|
11
|
-
recommendedTiming?: FillableFormRecommendedTiming;
|
|
12
|
-
fields: ReadonlyArray<FillableFormFieldBinding>;
|
|
13
|
-
targetByRef: ReadonlyMap<string, TargetDescriptor>;
|
|
14
|
-
}): FillableFormGuidanceHint;
|
|
15
|
-
export declare const __testRequestGuidance: {
|
|
16
|
-
collectVisibleFieldEvidence: typeof collectVisibleFieldEvidence;
|
|
17
|
-
collectBlockingValidationEvidence: typeof collectBlockingValidationEvidence;
|
|
18
|
-
collectPassiveRequiredEvidence: typeof collectPassiveRequiredEvidence;
|
|
19
|
-
hasCorePaymentCardFields: typeof hasCorePaymentCardFields;
|
|
20
|
-
looksLikePrimaryLoginForm: typeof looksLikePrimaryLoginForm;
|
|
21
|
-
looksLikeStrongIdentityForm: typeof looksLikeStrongIdentityForm;
|
|
22
|
-
};
|
|
23
|
-
export {};
|
|
24
|
-
//# sourceMappingURL=request-guidance.d.ts.map
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"request-guidance.d.ts","sourceRoot":"","sources":["../../src/secrets/request-guidance.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,gBAAgB,EAAE,MAAM,qBAAqB,CAAC;AAC5D,OAAO,KAAK,EACV,wBAAwB,EACxB,wBAAwB,EACxB,6BAA6B,EAC7B,oBAAoB,EAErB,MAAM,YAAY,CAAC;AAoCpB,iBAAS,2BAA2B,CAClC,MAAM,EAAE,aAAa,CAAC,wBAAwB,CAAC,EAC/C,WAAW,EAAE,WAAW,CAAC,MAAM,EAAE,gBAAgB,CAAC,GACjD,MAAM,CAYR;AAED,iBAAS,iCAAiC,CACxC,MAAM,EAAE,aAAa,CAAC,wBAAwB,CAAC,EAC/C,WAAW,EAAE,WAAW,CAAC,MAAM,EAAE,gBAAgB,CAAC,GACjD,MAAM,EAAE,CA+BV;AAED,iBAAS,8BAA8B,CACrC,MAAM,EAAE,aAAa,CAAC,wBAAwB,CAAC,EAC/C,WAAW,EAAE,WAAW,CAAC,MAAM,EAAE,gBAAgB,CAAC,GACjD,MAAM,EAAE,CAsBV;AAED,iBAAS,wBAAwB,CAAC,SAAS,EAAE,WAAW,CAAC,oBAAoB,CAAC,GAAG,OAAO,CAEvF;AAED,iBAAS,yBAAyB,CAAC,SAAS,EAAE,WAAW,CAAC,oBAAoB,CAAC,GAAG,OAAO,CAExF;AAED,iBAAS,2BAA2B,CAAC,SAAS,EAAE,WAAW,CAAC,oBAAoB,CAAC,GAAG,OAAO,CAK1F;AAmBD,wBAAgB,yBAAyB,CAAC,MAAM,EAAE;IAChD,OAAO,EAAE,MAAM,CAAC;IAChB,iBAAiB,CAAC,EAAE,6BAA6B,CAAC;IAClD,MAAM,EAAE,aAAa,CAAC,wBAAwB,CAAC,CAAC;IAChD,WAAW,EAAE,WAAW,CAAC,MAAM,EAAE,gBAAgB,CAAC,CAAC;CACpD,GAAG,wBAAwB,CA4C3B;AAED,eAAO,MAAM,qBAAqB;;;;;;;CAOjC,CAAC"}
|