@apifuse/provider-sdk 2.1.0-beta.8 → 2.2.0-beta.1
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/AUTHORING.md +134 -0
- package/CHANGELOG.md +61 -0
- package/README.md +21 -9
- package/SUBMISSION.md +10 -11
- package/bin/apifuse-pack-check.ts +22 -0
- package/bin/apifuse-perf.ts +18 -9
- package/bin/apifuse-submit-check.ts +1747 -388
- package/dist/auth-turn/auth-turn.v1.schema.json +89 -0
- package/dist/auth-turn/fixtures/invalid/empty-kind.json +4 -0
- package/dist/auth-turn/fixtures/invalid/expires-at-not-string.json +5 -0
- package/dist/auth-turn/fixtures/invalid/missing-kind.json +3 -0
- package/dist/auth-turn/fixtures/invalid/missing-turn-id.json +3 -0
- package/dist/auth-turn/fixtures/invalid/timing-unknown-field.json +7 -0
- package/dist/auth-turn/fixtures/invalid/turn-id-snake-case.json +4 -0
- package/dist/auth-turn/fixtures/invalid/unknown-top-level-field.json +5 -0
- package/dist/auth-turn/fixtures/valid/abort.json +8 -0
- package/dist/auth-turn/fixtures/valid/challenge.json +17 -0
- package/dist/auth-turn/fixtures/valid/complete.json +13 -0
- package/dist/auth-turn/fixtures/valid/form.json +14 -0
- package/dist/auth-turn/fixtures/valid/message.json +13 -0
- package/dist/auth-turn/fixtures/valid/multi_choice.json +15 -0
- package/dist/auth-turn/fixtures/valid/pending.json +5 -0
- package/dist/auth-turn/fixtures/valid/poll.json +9 -0
- package/dist/auth-turn/fixtures/valid/redirect.json +16 -0
- package/dist/auth-turn/fixtures/valid/retry.json +8 -0
- package/dist/auth-turn/fixtures/valid/unknown-kind.json +7 -0
- package/dist/auth-turn/index.d.ts +195 -0
- package/dist/auth-turn/index.js +133 -0
- package/dist/auth.d.ts +76 -0
- package/dist/auth.js +436 -0
- package/dist/ceremonies/index.js +7 -31
- package/dist/cli/create.js +45 -30
- package/dist/cli/templates/provider/.dockerignore.tpl +22 -0
- package/dist/cli/templates/provider/.gitignore.tpl +22 -0
- package/dist/cli/templates/provider/AGENTS.md.tpl +87 -0
- package/dist/cli/templates/provider/CLAUDE.md.tpl +1 -0
- package/dist/cli/templates/provider/Dockerfile.tpl +7 -0
- package/dist/cli/templates/provider/README.md.tpl +163 -0
- package/dist/cli/templates/provider/dev.ts.tpl +5 -0
- package/dist/cli/templates/provider/domain/README.md.tpl +3 -0
- package/dist/cli/templates/provider/index.test.ts.tpl +13 -0
- package/dist/cli/templates/provider/index.ts.tpl +15 -0
- package/dist/cli/templates/provider/mappers/README.md.tpl +3 -0
- package/dist/cli/templates/provider/meta.ts.tpl +7 -0
- package/dist/cli/templates/provider/operations/index.ts.tpl +5 -0
- package/dist/cli/templates/provider/operations/ping.ts.tpl +24 -0
- package/dist/cli/templates/provider/schemas/ping.ts.tpl +24 -0
- package/dist/cli/templates/provider/skills/fixtures-and-recording/SKILL.md.tpl +58 -0
- package/dist/cli/templates/provider/skills/health-checks-and-fail-closed/SKILL.md.tpl +65 -0
- package/dist/cli/templates/provider/skills/normalization-standards/SKILL.md.tpl +57 -0
- package/dist/cli/templates/provider/skills/pagination-and-counts/SKILL.md.tpl +52 -0
- package/dist/cli/templates/provider/skills/upstream-contract-verification/SKILL.md.tpl +45 -0
- package/dist/cli/templates/provider/skills/upstream-notes/README.md.tpl +13 -0
- package/dist/cli/templates/provider/start.ts.tpl +5 -0
- package/dist/cli/templates/provider/upstream/README.md.tpl +3 -0
- package/dist/contract.js +1 -0
- package/dist/define.d.ts +6 -1
- package/dist/define.js +140 -70
- package/dist/index.d.ts +3 -2
- package/dist/index.js +2 -1
- package/dist/lint.d.ts +1 -0
- package/dist/lint.js +27 -0
- package/dist/provider.d.ts +4 -2
- package/dist/provider.js +2 -1
- package/dist/runtime/auth-flow.js +2 -0
- package/dist/runtime/browser.js +203 -0
- package/dist/runtime/http.js +28 -8
- package/dist/runtime/stealth.d.ts +5 -2
- package/dist/runtime/stealth.js +157 -4
- package/dist/server/index.d.ts +4 -0
- package/dist/server/index.js +4 -0
- package/dist/server/self-test-input-tokens.d.ts +1 -0
- package/dist/server/self-test-input-tokens.js +37 -0
- package/dist/server/self-test-redaction.d.ts +20 -0
- package/dist/server/self-test-redaction.js +70 -0
- package/dist/server/self-test-token.d.ts +30 -0
- package/dist/server/self-test-token.js +50 -0
- package/dist/server/self-test.d.ts +98 -0
- package/dist/server/self-test.js +555 -0
- package/dist/server/serve.d.ts +6 -0
- package/dist/server/serve.js +33 -8
- package/dist/testing/run.js +5 -1
- package/dist/types.d.ts +152 -0
- package/package.json +10 -3
- package/src/auth-turn/auth-turn.v1.schema.json +89 -0
- package/src/auth-turn/fixtures/invalid/empty-kind.json +4 -0
- package/src/auth-turn/fixtures/invalid/expires-at-not-string.json +5 -0
- package/src/auth-turn/fixtures/invalid/missing-kind.json +3 -0
- package/src/auth-turn/fixtures/invalid/missing-turn-id.json +3 -0
- package/src/auth-turn/fixtures/invalid/timing-unknown-field.json +7 -0
- package/src/auth-turn/fixtures/invalid/turn-id-snake-case.json +4 -0
- package/src/auth-turn/fixtures/invalid/unknown-top-level-field.json +5 -0
- package/src/auth-turn/fixtures/valid/abort.json +8 -0
- package/src/auth-turn/fixtures/valid/challenge.json +17 -0
- package/src/auth-turn/fixtures/valid/complete.json +13 -0
- package/src/auth-turn/fixtures/valid/form.json +14 -0
- package/src/auth-turn/fixtures/valid/message.json +13 -0
- package/src/auth-turn/fixtures/valid/multi_choice.json +15 -0
- package/src/auth-turn/fixtures/valid/pending.json +5 -0
- package/src/auth-turn/fixtures/valid/poll.json +9 -0
- package/src/auth-turn/fixtures/valid/redirect.json +16 -0
- package/src/auth-turn/fixtures/valid/retry.json +8 -0
- package/src/auth-turn/fixtures/valid/unknown-kind.json +7 -0
- package/src/auth-turn/index.ts +177 -0
- package/src/auth.ts +786 -0
- package/src/ceremonies/index.ts +9 -43
- package/src/cli/create.ts +60 -97
- package/src/cli/templates/provider/AGENTS.md.tpl +87 -0
- package/src/cli/templates/provider/CLAUDE.md.tpl +1 -0
- package/src/cli/templates/provider/README.md.tpl +7 -4
- package/src/cli/templates/provider/skills/fixtures-and-recording/SKILL.md.tpl +58 -0
- package/src/cli/templates/provider/skills/health-checks-and-fail-closed/SKILL.md.tpl +65 -0
- package/src/cli/templates/provider/skills/normalization-standards/SKILL.md.tpl +57 -0
- package/src/cli/templates/provider/skills/pagination-and-counts/SKILL.md.tpl +52 -0
- package/src/cli/templates/provider/skills/upstream-contract-verification/SKILL.md.tpl +45 -0
- package/src/cli/templates/provider/skills/upstream-notes/README.md.tpl +13 -0
- package/src/contract.ts +1 -0
- package/src/define.ts +198 -71
- package/src/index.ts +16 -0
- package/src/lint.ts +33 -0
- package/src/provider.ts +27 -0
- package/src/runtime/auth-flow.ts +2 -0
- package/src/runtime/browser.ts +293 -1
- package/src/runtime/http.ts +48 -7
- package/src/runtime/stealth.ts +190 -6
- package/src/server/index.ts +36 -0
- package/src/server/self-test-input-tokens.ts +46 -0
- package/src/server/self-test-redaction.ts +97 -0
- package/src/server/self-test-token.ts +70 -0
- package/src/server/self-test.ts +725 -0
- package/src/server/serve.ts +67 -4
- package/src/testing/run.ts +9 -1
- package/src/types.ts +188 -0
package/src/server/serve.ts
CHANGED
|
@@ -3,6 +3,7 @@ import { join } from "node:path";
|
|
|
3
3
|
|
|
4
4
|
import { Hono } from "hono";
|
|
5
5
|
import { z } from "zod";
|
|
6
|
+
import { AuthAbortError, createAuthFlowHelpers } from "../auth";
|
|
6
7
|
import {
|
|
7
8
|
AuthError,
|
|
8
9
|
ProviderError,
|
|
@@ -75,6 +76,12 @@ import type {
|
|
|
75
76
|
StealthClient,
|
|
76
77
|
SttContext,
|
|
77
78
|
} from "../types";
|
|
79
|
+
import {
|
|
80
|
+
createSelfTestApp,
|
|
81
|
+
createSelfTestInvoke,
|
|
82
|
+
resolveSelfTestPort,
|
|
83
|
+
} from "./self-test";
|
|
84
|
+
import { resolveSelfTestMasterSecrets } from "./self-test-token";
|
|
78
85
|
import {
|
|
79
86
|
type AuthFlowRequest,
|
|
80
87
|
AuthFlowRequestSchema,
|
|
@@ -329,6 +336,7 @@ function createAuthFlowContext(
|
|
|
329
336
|
provider: ProviderDefinition,
|
|
330
337
|
request: AuthFlowRequest,
|
|
331
338
|
options: ProviderServerOptions = {},
|
|
339
|
+
signal?: AbortSignal,
|
|
332
340
|
): {
|
|
333
341
|
context: FlowContext;
|
|
334
342
|
getPatch: () => Record<string, unknown | null> | undefined;
|
|
@@ -383,6 +391,7 @@ function createAuthFlowContext(
|
|
|
383
391
|
credential,
|
|
384
392
|
context: flowContextStore.context,
|
|
385
393
|
stt: options.stt ?? createSttClientFromEnv(provider.stt),
|
|
394
|
+
auth: createAuthFlowHelpers({ signal }),
|
|
386
395
|
},
|
|
387
396
|
getPatch: flowContextStore.getPatch,
|
|
388
397
|
};
|
|
@@ -1291,6 +1300,7 @@ async function handleAuthFlow(
|
|
|
1291
1300
|
request: AuthFlowRequest,
|
|
1292
1301
|
route: AuthRoute,
|
|
1293
1302
|
options: ProviderServerOptions = {},
|
|
1303
|
+
signal?: AbortSignal,
|
|
1294
1304
|
): Promise<Response | AuthFlowResponse> {
|
|
1295
1305
|
const flow = provider.auth?.flow;
|
|
1296
1306
|
if (!flow) {
|
|
@@ -1303,6 +1313,7 @@ async function handleAuthFlow(
|
|
|
1303
1313
|
provider,
|
|
1304
1314
|
request,
|
|
1305
1315
|
options,
|
|
1316
|
+
signal,
|
|
1306
1317
|
);
|
|
1307
1318
|
try {
|
|
1308
1319
|
const result =
|
|
@@ -1336,6 +1347,11 @@ async function handleAuthFlow(
|
|
|
1336
1347
|
? materializeAuthFlowTurn(provider, request, result)
|
|
1337
1348
|
: result;
|
|
1338
1349
|
return toAuthFlowResponse(materializedResult, getPatch());
|
|
1350
|
+
} catch (error) {
|
|
1351
|
+
if (error instanceof AuthAbortError) {
|
|
1352
|
+
return toAuthFlowResponse(error.turn, getPatch());
|
|
1353
|
+
}
|
|
1354
|
+
throw error;
|
|
1339
1355
|
} finally {
|
|
1340
1356
|
context.stealth.close?.();
|
|
1341
1357
|
}
|
|
@@ -1450,7 +1466,13 @@ export function createServerApp(
|
|
|
1450
1466
|
AuthFlowRequestSchema.parse(rawBody),
|
|
1451
1467
|
c.req.raw.headers,
|
|
1452
1468
|
);
|
|
1453
|
-
const response = await handleAuthFlow(
|
|
1469
|
+
const response = await handleAuthFlow(
|
|
1470
|
+
provider,
|
|
1471
|
+
body,
|
|
1472
|
+
"start",
|
|
1473
|
+
options,
|
|
1474
|
+
c.req.raw.signal,
|
|
1475
|
+
);
|
|
1454
1476
|
logProviderSuccess(
|
|
1455
1477
|
logger,
|
|
1456
1478
|
provider,
|
|
@@ -1495,6 +1517,7 @@ export function createServerApp(
|
|
|
1495
1517
|
body,
|
|
1496
1518
|
"continue",
|
|
1497
1519
|
options,
|
|
1520
|
+
c.req.raw.signal,
|
|
1498
1521
|
);
|
|
1499
1522
|
logProviderSuccess(
|
|
1500
1523
|
logger,
|
|
@@ -1535,7 +1558,13 @@ export function createServerApp(
|
|
|
1535
1558
|
AuthFlowRequestSchema.parse(rawBody),
|
|
1536
1559
|
c.req.raw.headers,
|
|
1537
1560
|
);
|
|
1538
|
-
const response = await handleAuthFlow(
|
|
1561
|
+
const response = await handleAuthFlow(
|
|
1562
|
+
provider,
|
|
1563
|
+
body,
|
|
1564
|
+
"poll",
|
|
1565
|
+
options,
|
|
1566
|
+
c.req.raw.signal,
|
|
1567
|
+
);
|
|
1539
1568
|
logProviderSuccess(
|
|
1540
1569
|
logger,
|
|
1541
1570
|
provider,
|
|
@@ -1575,7 +1604,13 @@ export function createServerApp(
|
|
|
1575
1604
|
AuthFlowRequestSchema.parse(rawBody),
|
|
1576
1605
|
c.req.raw.headers,
|
|
1577
1606
|
);
|
|
1578
|
-
const response = await handleAuthFlow(
|
|
1607
|
+
const response = await handleAuthFlow(
|
|
1608
|
+
provider,
|
|
1609
|
+
body,
|
|
1610
|
+
"refresh",
|
|
1611
|
+
options,
|
|
1612
|
+
c.req.raw.signal,
|
|
1613
|
+
);
|
|
1579
1614
|
logProviderSuccess(
|
|
1580
1615
|
logger,
|
|
1581
1616
|
provider,
|
|
@@ -1615,7 +1650,13 @@ export function createServerApp(
|
|
|
1615
1650
|
AuthFlowRequestSchema.parse(rawBody),
|
|
1616
1651
|
c.req.raw.headers,
|
|
1617
1652
|
);
|
|
1618
|
-
const response = await handleAuthFlow(
|
|
1653
|
+
const response = await handleAuthFlow(
|
|
1654
|
+
provider,
|
|
1655
|
+
body,
|
|
1656
|
+
"abort",
|
|
1657
|
+
options,
|
|
1658
|
+
c.req.raw.signal,
|
|
1659
|
+
);
|
|
1619
1660
|
logProviderSuccess(
|
|
1620
1661
|
logger,
|
|
1621
1662
|
provider,
|
|
@@ -1675,6 +1716,12 @@ function getBunServeRuntime(): BunServeRuntime | undefined {
|
|
|
1675
1716
|
export interface ServeOptions extends ProviderServerOptions {
|
|
1676
1717
|
host?: string;
|
|
1677
1718
|
port?: number;
|
|
1719
|
+
/**
|
|
1720
|
+
* Port for the internal self-test listener (default 3001 or
|
|
1721
|
+
* APIFUSE__PROVIDER_RUNTIME__SELF_TEST_PORT). The listener only starts
|
|
1722
|
+
* when APIFUSE__PROVIDER_RUNTIME__SELF_TEST_MASTER_SECRET is present.
|
|
1723
|
+
*/
|
|
1724
|
+
selfTestPort?: number;
|
|
1678
1725
|
}
|
|
1679
1726
|
|
|
1680
1727
|
export async function serve(
|
|
@@ -1702,5 +1749,21 @@ export async function serve(
|
|
|
1702
1749
|
hostname: options.host ?? DEFAULT_HOST,
|
|
1703
1750
|
fetch: app.fetch,
|
|
1704
1751
|
});
|
|
1752
|
+
|
|
1753
|
+
// Internal self-test listener (health dependency inversion): a SEPARATE
|
|
1754
|
+
// socket the tenant-facing gateway never dials. Off by default — it only
|
|
1755
|
+
// starts when the shared self-test master secret env is present.
|
|
1756
|
+
const selfTestSecrets = resolveSelfTestMasterSecrets();
|
|
1757
|
+
if (selfTestSecrets) {
|
|
1758
|
+
const selfTestApp = createSelfTestApp(provider, {
|
|
1759
|
+
secrets: selfTestSecrets,
|
|
1760
|
+
invoke: createSelfTestInvoke(app),
|
|
1761
|
+
});
|
|
1762
|
+
bunRuntime.serve({
|
|
1763
|
+
port: options.selfTestPort ?? resolveSelfTestPort(),
|
|
1764
|
+
hostname: options.host ?? DEFAULT_HOST,
|
|
1765
|
+
fetch: selfTestApp.fetch,
|
|
1766
|
+
});
|
|
1767
|
+
}
|
|
1705
1768
|
await Promise.resolve();
|
|
1706
1769
|
}
|
package/src/testing/run.ts
CHANGED
|
@@ -128,13 +128,21 @@ function inferFixtureDir(providerId: string): string {
|
|
|
128
128
|
}
|
|
129
129
|
|
|
130
130
|
function jsonResponse(data: unknown): HttpResponse {
|
|
131
|
+
const body = JSON.stringify(data);
|
|
132
|
+
const bodyBytes = new TextEncoder().encode(body);
|
|
131
133
|
return {
|
|
132
134
|
status: 200,
|
|
133
135
|
ok: true,
|
|
134
136
|
headers: {},
|
|
135
137
|
data,
|
|
136
138
|
json: async <_T = unknown>() => JSON.parse(JSON.stringify(data)),
|
|
137
|
-
text: async () =>
|
|
139
|
+
text: async () => body,
|
|
140
|
+
arrayBuffer: async () =>
|
|
141
|
+
bodyBytes.buffer.slice(
|
|
142
|
+
bodyBytes.byteOffset,
|
|
143
|
+
bodyBytes.byteOffset + bodyBytes.byteLength,
|
|
144
|
+
),
|
|
145
|
+
bytes: async () => bodyBytes.slice(0),
|
|
138
146
|
};
|
|
139
147
|
}
|
|
140
148
|
|
package/src/types.ts
CHANGED
|
@@ -331,9 +331,20 @@ export interface HealthJourneySchedule {
|
|
|
331
331
|
kind: "interval";
|
|
332
332
|
/** ISO 8601 duration, for example PT8H. */
|
|
333
333
|
interval: Iso8601Duration;
|
|
334
|
+
randomize?: HealthScheduleRandomization;
|
|
334
335
|
jitter?: Iso8601Duration;
|
|
335
336
|
}
|
|
336
337
|
|
|
338
|
+
export type HealthScheduleRandomization =
|
|
339
|
+
| {
|
|
340
|
+
mode: "centered";
|
|
341
|
+
maxOffset: Iso8601Duration;
|
|
342
|
+
}
|
|
343
|
+
| {
|
|
344
|
+
mode: "delayed";
|
|
345
|
+
maxDelay: Iso8601Duration;
|
|
346
|
+
};
|
|
347
|
+
|
|
337
348
|
export interface HealthJourneyStep {
|
|
338
349
|
id: string;
|
|
339
350
|
description?: string;
|
|
@@ -612,6 +623,9 @@ export interface HealthCheckCase<TInput = unknown, TOutput = unknown> {
|
|
|
612
623
|
export interface HealthCheckSuite<TInput = unknown, TOutput = unknown> {
|
|
613
624
|
/** Polling interval for the suite. All cases share this cadence. */
|
|
614
625
|
interval: ProbeInterval;
|
|
626
|
+
schedule?: {
|
|
627
|
+
randomize?: HealthScheduleRandomization;
|
|
628
|
+
};
|
|
615
629
|
/** Per-case timeout in milliseconds. Default: 30000. */
|
|
616
630
|
timeoutMs?: number;
|
|
617
631
|
/** Default degradation threshold for cases in this suite. Default: runtime threshold. */
|
|
@@ -687,6 +701,14 @@ export interface ProviderHealthMonitorConfig {
|
|
|
687
701
|
serviceAccount?: string;
|
|
688
702
|
}
|
|
689
703
|
|
|
704
|
+
/**
|
|
705
|
+
* New name for `ProviderHealthMonitorConfig` as part of the health dependency
|
|
706
|
+
* inversion (`healthMonitor` → `healthProbe`). Both provider-level fields are
|
|
707
|
+
* accepted transitionally with identical validation; declaring both is a
|
|
708
|
+
* `ValidationError`.
|
|
709
|
+
*/
|
|
710
|
+
export type ProviderHealthProbeConfig = ProviderHealthMonitorConfig;
|
|
711
|
+
|
|
690
712
|
export interface HealthMonitorProbeOverride {
|
|
691
713
|
/** Optional runtime interval override as a positive `ms`-style duration string. */
|
|
692
714
|
interval?: ProbeInterval;
|
|
@@ -979,6 +1001,7 @@ export type HttpMethod =
|
|
|
979
1001
|
export interface StealthFetchOptions extends RequestOptions {
|
|
980
1002
|
method?: HttpMethod;
|
|
981
1003
|
body?: string | Buffer;
|
|
1004
|
+
redirect?: "follow" | "manual" | "error";
|
|
982
1005
|
/**
|
|
983
1006
|
* Offsets policy-managed proxy pool selection for caller-managed retries.
|
|
984
1007
|
* Use when a request receives an upstream challenge page rather than a
|
|
@@ -1005,9 +1028,20 @@ export interface CookieJar {
|
|
|
1005
1028
|
find?(predicate: (cookie: string) => boolean): string | undefined;
|
|
1006
1029
|
}
|
|
1007
1030
|
|
|
1031
|
+
export interface StealthSessionCookies extends CookieJar {
|
|
1032
|
+
has(name: string): boolean;
|
|
1033
|
+
setFromCookieStrings(cookieStrings: readonly string[]): void;
|
|
1034
|
+
toHeader(): string;
|
|
1035
|
+
snapshot(): Record<string, string>;
|
|
1036
|
+
restore(cookies: Record<string, string>): void;
|
|
1037
|
+
clear(): void;
|
|
1038
|
+
}
|
|
1039
|
+
|
|
1008
1040
|
export interface DeclarativeStealthResponse {
|
|
1009
1041
|
status: number;
|
|
1010
1042
|
ok: boolean;
|
|
1043
|
+
url?: string;
|
|
1044
|
+
redirected?: boolean;
|
|
1011
1045
|
headers: Record<string, string>;
|
|
1012
1046
|
rawHeaders: [string, string][];
|
|
1013
1047
|
body: string;
|
|
@@ -1015,6 +1049,8 @@ export interface DeclarativeStealthResponse {
|
|
|
1015
1049
|
tlsInfo?: { protocol?: string; cipher?: string; [key: string]: unknown };
|
|
1016
1050
|
cookies: CookieJar;
|
|
1017
1051
|
json<T>(): Promise<T>;
|
|
1052
|
+
arrayBuffer(): Promise<ArrayBuffer>;
|
|
1053
|
+
bytes(): Promise<Uint8Array>;
|
|
1018
1054
|
}
|
|
1019
1055
|
|
|
1020
1056
|
export type StealthResponse = DeclarativeStealthResponse;
|
|
@@ -1024,8 +1060,34 @@ export type RequestWithMethodOptions = RequestOptions & {
|
|
|
1024
1060
|
body?: unknown;
|
|
1025
1061
|
};
|
|
1026
1062
|
|
|
1063
|
+
export interface StealthRedirectHop {
|
|
1064
|
+
url: string;
|
|
1065
|
+
status: number;
|
|
1066
|
+
method: string;
|
|
1067
|
+
location?: string;
|
|
1068
|
+
nextUrl?: string;
|
|
1069
|
+
}
|
|
1070
|
+
|
|
1071
|
+
export interface StealthRedirectRunOptions
|
|
1072
|
+
extends Omit<StealthFetchOptions, "redirect"> {
|
|
1073
|
+
url: string;
|
|
1074
|
+
maxHops?: number;
|
|
1075
|
+
stopWhen?: (hop: StealthRedirectHop) => boolean | Promise<boolean>;
|
|
1076
|
+
}
|
|
1077
|
+
|
|
1078
|
+
export interface StealthRedirectRunResult {
|
|
1079
|
+
final: StealthResponse;
|
|
1080
|
+
hops: StealthRedirectHop[];
|
|
1081
|
+
reason: "completed" | "stopped" | "max_hops" | "missing_location" | "loop";
|
|
1082
|
+
cookies: Record<string, string>;
|
|
1083
|
+
}
|
|
1084
|
+
|
|
1027
1085
|
export interface StealthSession {
|
|
1028
1086
|
fetch(url: string, options?: StealthFetchOptions): Promise<StealthResponse>;
|
|
1087
|
+
cookies: StealthSessionCookies;
|
|
1088
|
+
redirects: {
|
|
1089
|
+
run(options: StealthRedirectRunOptions): Promise<StealthRedirectRunResult>;
|
|
1090
|
+
};
|
|
1029
1091
|
close(): void;
|
|
1030
1092
|
}
|
|
1031
1093
|
|
|
@@ -1048,6 +1110,8 @@ export interface HttpResponse<T = unknown> {
|
|
|
1048
1110
|
data: T;
|
|
1049
1111
|
json<U = T>(): Promise<U>;
|
|
1050
1112
|
text(): Promise<string>;
|
|
1113
|
+
arrayBuffer(): Promise<ArrayBuffer>;
|
|
1114
|
+
bytes(): Promise<Uint8Array>;
|
|
1051
1115
|
}
|
|
1052
1116
|
|
|
1053
1117
|
export interface HttpStreamResponse {
|
|
@@ -1204,6 +1268,45 @@ export interface BrowserFrame {
|
|
|
1204
1268
|
locator(selector: string): BrowserLocator;
|
|
1205
1269
|
}
|
|
1206
1270
|
|
|
1271
|
+
export type BrowserResourceMethod = "GET" | "HEAD";
|
|
1272
|
+
|
|
1273
|
+
export type BrowserResourceRequest = {
|
|
1274
|
+
readonly url: string;
|
|
1275
|
+
readonly method: BrowserResourceMethod;
|
|
1276
|
+
readonly resourceType?: string;
|
|
1277
|
+
readonly headers: Readonly<Record<string, string>>;
|
|
1278
|
+
};
|
|
1279
|
+
|
|
1280
|
+
export type BrowserResourceBody = Buffer | Uint8Array | ArrayBuffer | string;
|
|
1281
|
+
|
|
1282
|
+
export type BrowserResourceDecision =
|
|
1283
|
+
| {
|
|
1284
|
+
readonly action: "fulfill";
|
|
1285
|
+
readonly status?: number;
|
|
1286
|
+
readonly headers?: Readonly<Record<string, string>>;
|
|
1287
|
+
readonly body?: BrowserResourceBody;
|
|
1288
|
+
}
|
|
1289
|
+
| {
|
|
1290
|
+
readonly action: "block";
|
|
1291
|
+
readonly reason?: string;
|
|
1292
|
+
};
|
|
1293
|
+
|
|
1294
|
+
export type BrowserResourceRoute = {
|
|
1295
|
+
readonly match:
|
|
1296
|
+
| string
|
|
1297
|
+
| RegExp
|
|
1298
|
+
| ((request: BrowserResourceRequest) => boolean);
|
|
1299
|
+
readonly handle: (
|
|
1300
|
+
request: BrowserResourceRequest,
|
|
1301
|
+
) => Promise<BrowserResourceDecision> | BrowserResourceDecision;
|
|
1302
|
+
};
|
|
1303
|
+
|
|
1304
|
+
export type BrowserResourcePolicy = {
|
|
1305
|
+
readonly defaultAction?: "block";
|
|
1306
|
+
readonly allowedMethods?: readonly BrowserResourceMethod[];
|
|
1307
|
+
readonly routes: readonly BrowserResourceRoute[];
|
|
1308
|
+
};
|
|
1309
|
+
|
|
1207
1310
|
export interface BrowserPage extends BrowserFrame {
|
|
1208
1311
|
close(): Promise<void>;
|
|
1209
1312
|
fill(selector: string, text: string): Promise<void>;
|
|
@@ -1217,6 +1320,10 @@ export interface BrowserPage extends BrowserFrame {
|
|
|
1217
1320
|
options?: { timeout?: number },
|
|
1218
1321
|
): Promise<void>;
|
|
1219
1322
|
frames(): Promise<BrowserFrame[]>;
|
|
1323
|
+
withResourcePolicy<T>(
|
|
1324
|
+
policy: BrowserResourcePolicy,
|
|
1325
|
+
run: () => Promise<T>,
|
|
1326
|
+
): Promise<T>;
|
|
1220
1327
|
}
|
|
1221
1328
|
|
|
1222
1329
|
export type BrowserChallengeRequest = {
|
|
@@ -1395,6 +1502,84 @@ export interface ContextScratchpad {
|
|
|
1395
1502
|
|
|
1396
1503
|
export type FlowContextStore = ContextScratchpad;
|
|
1397
1504
|
|
|
1505
|
+
export type AuthSafeJson =
|
|
1506
|
+
| string
|
|
1507
|
+
| number
|
|
1508
|
+
| boolean
|
|
1509
|
+
| null
|
|
1510
|
+
| readonly AuthSafeJson[]
|
|
1511
|
+
| { readonly [key: string]: AuthSafeJson };
|
|
1512
|
+
|
|
1513
|
+
export type AuthSafeData = { readonly [key: string]: AuthSafeJson };
|
|
1514
|
+
|
|
1515
|
+
export type AuthAbortRetry = "never" | "retry" | "after_user_action";
|
|
1516
|
+
|
|
1517
|
+
export type AuthAbortData = Record<string, unknown> & {
|
|
1518
|
+
readonly code: string;
|
|
1519
|
+
readonly message?: string;
|
|
1520
|
+
readonly retry?: AuthAbortRetry;
|
|
1521
|
+
readonly actionHint?: AuthSafeJson;
|
|
1522
|
+
readonly fieldErrors?: { readonly [field: string]: string };
|
|
1523
|
+
readonly details?: AuthSafeData;
|
|
1524
|
+
};
|
|
1525
|
+
|
|
1526
|
+
export interface AuthFlowTerminalContext {
|
|
1527
|
+
readonly signal?: AbortSignal;
|
|
1528
|
+
readonly deadline?: string;
|
|
1529
|
+
complete<TCredential extends Record<string, string>>(options: {
|
|
1530
|
+
readonly credential: TCredential;
|
|
1531
|
+
readonly metadata?: AuthSafeData;
|
|
1532
|
+
readonly data?: AuthSafeData;
|
|
1533
|
+
readonly turnId?: string;
|
|
1534
|
+
readonly expiresAt?: string;
|
|
1535
|
+
}): AuthTurn;
|
|
1536
|
+
abort(options: {
|
|
1537
|
+
readonly code: string;
|
|
1538
|
+
readonly message?: string;
|
|
1539
|
+
readonly retry?: AuthAbortRetry;
|
|
1540
|
+
readonly actionHint?: AuthSafeJson;
|
|
1541
|
+
readonly fieldErrors?: { readonly [field: string]: string };
|
|
1542
|
+
readonly data?: AuthSafeData;
|
|
1543
|
+
readonly turnId?: string;
|
|
1544
|
+
readonly expiresAt?: string;
|
|
1545
|
+
}): AuthTurn;
|
|
1546
|
+
nextForm(
|
|
1547
|
+
options: {
|
|
1548
|
+
readonly hintKey?: ProviderLocaleKeyInput;
|
|
1549
|
+
readonly data?: AuthSafeData;
|
|
1550
|
+
readonly turnId?: string;
|
|
1551
|
+
readonly expiresAt?: string;
|
|
1552
|
+
readonly timing?: AuthTurn["timing"];
|
|
1553
|
+
} & (
|
|
1554
|
+
| {
|
|
1555
|
+
readonly fields: Record<
|
|
1556
|
+
string,
|
|
1557
|
+
{
|
|
1558
|
+
readonly type?: "string" | "email" | "password" | "otp";
|
|
1559
|
+
readonly labelKey?: ProviderLocaleKeyInput;
|
|
1560
|
+
readonly descriptionKey?: ProviderLocaleKeyInput;
|
|
1561
|
+
readonly placeholderKey?: ProviderLocaleKeyInput;
|
|
1562
|
+
readonly required?: boolean;
|
|
1563
|
+
readonly sensitive?: boolean;
|
|
1564
|
+
}
|
|
1565
|
+
>;
|
|
1566
|
+
readonly expectedInput?: never;
|
|
1567
|
+
}
|
|
1568
|
+
| {
|
|
1569
|
+
readonly expectedInput: Record<string, unknown>;
|
|
1570
|
+
readonly fields?: never;
|
|
1571
|
+
}
|
|
1572
|
+
),
|
|
1573
|
+
): AuthTurn;
|
|
1574
|
+
nextPoll(options?: {
|
|
1575
|
+
readonly hintKey?: ProviderLocaleKeyInput;
|
|
1576
|
+
readonly data?: AuthSafeData;
|
|
1577
|
+
readonly turnId?: string;
|
|
1578
|
+
readonly expiresAt?: string;
|
|
1579
|
+
readonly timing?: AuthTurn["timing"];
|
|
1580
|
+
}): AuthTurn;
|
|
1581
|
+
}
|
|
1582
|
+
|
|
1398
1583
|
export interface FlowContext {
|
|
1399
1584
|
connectionId?: string;
|
|
1400
1585
|
externalRef?: string;
|
|
@@ -1406,6 +1591,7 @@ export interface FlowContext {
|
|
|
1406
1591
|
credential?: CredentialContext;
|
|
1407
1592
|
context: ContextScratchpad;
|
|
1408
1593
|
stt: SttContext;
|
|
1594
|
+
auth: AuthFlowTerminalContext;
|
|
1409
1595
|
}
|
|
1410
1596
|
|
|
1411
1597
|
export interface AuthTurn {
|
|
@@ -1634,5 +1820,7 @@ export interface ProviderDefinition {
|
|
|
1634
1820
|
meta: ProviderMeta;
|
|
1635
1821
|
operations: Record<string, OperationDefinition<SchemaLike, SchemaLike>>;
|
|
1636
1822
|
healthMonitor?: ProviderHealthMonitorConfig;
|
|
1823
|
+
/** Transitional alias for `healthMonitor`; `defineProvider` mirrors both. */
|
|
1824
|
+
healthProbe?: ProviderHealthProbeConfig;
|
|
1637
1825
|
healthJourneys?: readonly HealthJourneyDefinition[];
|
|
1638
1826
|
}
|