@effect-agent/platform-cloudflare 0.1.0-beta.106 → 0.1.0-beta.107
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/dist/CloudflareThreadClient.d.mts +50 -50
- package/dist/{InteractiveBrowser-BR16UPbF.d.mts → InteractiveBrowser-B3S8if51.d.mts} +3 -2
- package/dist/{InteractiveBrowser-BCS9g0tn.mjs → InteractiveBrowser-xVNX7ARl.mjs} +96 -4
- package/dist/InteractiveBrowser-xVNX7ARl.mjs.map +1 -0
- package/dist/InteractiveBrowser.d.mts +1 -1
- package/dist/InteractiveBrowser.mjs +1 -1
- package/dist/ProtectedBrowser.d.mts +1 -1
- package/dist/ProtectedBrowser.mjs +1 -1
- package/dist/{ThreadObject-CLBMWEPn.d.mts → ThreadObject-CnqCuWlA.d.mts} +6 -6
- package/dist/ThreadObject.d.mts +1 -1
- package/dist/index.d.mts +1 -1
- package/package.json +1 -1
- package/src/InteractiveBrowser.ts +53 -2
- package/src/internal/browser-file-selection.ts +126 -0
- package/dist/InteractiveBrowser-BCS9g0tn.mjs.map +0 -1
|
@@ -475,13 +475,13 @@ export declare const encodeUnknownResolutionCommand: (input: UnknownResolutionCo
|
|
|
475
475
|
readonly author: string;
|
|
476
476
|
readonly reason: string;
|
|
477
477
|
readonly resolution: {
|
|
478
|
+
readonly _tag: "SafeToRetry";
|
|
479
|
+
} | {
|
|
478
480
|
readonly _tag: "CompletedWithResult";
|
|
479
481
|
readonly result: Schema.Json;
|
|
480
482
|
readonly isFailure: boolean;
|
|
481
483
|
} | {
|
|
482
484
|
readonly _tag: "NeverHappened";
|
|
483
|
-
} | {
|
|
484
|
-
readonly _tag: "SafeToRetry";
|
|
485
485
|
} | {
|
|
486
486
|
readonly _tag: "AbortSubmission";
|
|
487
487
|
};
|
|
@@ -645,6 +645,11 @@ export declare const encodeHostResponse: (input: AbortRecorded | ApprovalRecorde
|
|
|
645
645
|
readonly createdAt: string;
|
|
646
646
|
readonly deploymentId: string;
|
|
647
647
|
readonly payload: {
|
|
648
|
+
readonly _tag: "AbortRequested";
|
|
649
|
+
readonly submissionId: string;
|
|
650
|
+
readonly author: string;
|
|
651
|
+
readonly reason: string;
|
|
652
|
+
} | {
|
|
648
653
|
readonly _tag: "ThreadCreated";
|
|
649
654
|
readonly agentId: string;
|
|
650
655
|
readonly definitions: {
|
|
@@ -922,11 +927,6 @@ export declare const encodeHostResponse: (input: AbortRecorded | ApprovalRecorde
|
|
|
922
927
|
readonly runDisposition?: Schema.Json | undefined;
|
|
923
928
|
readonly finishReason?: "budget-exhausted" | undefined;
|
|
924
929
|
readonly exhausted?: "tokens" | "tool-calls" | "turns" | undefined;
|
|
925
|
-
} | {
|
|
926
|
-
readonly _tag: "AbortRequested";
|
|
927
|
-
readonly submissionId: string;
|
|
928
|
-
readonly author: string;
|
|
929
|
-
readonly reason: string;
|
|
930
930
|
} | {
|
|
931
931
|
readonly _tag: "SubmissionSettled";
|
|
932
932
|
readonly submissionId: string;
|
|
@@ -1465,13 +1465,13 @@ export declare const encodeHostResponse: (input: AbortRecorded | ApprovalRecorde
|
|
|
1465
1465
|
readonly author: string;
|
|
1466
1466
|
readonly reason: string;
|
|
1467
1467
|
readonly resolution: {
|
|
1468
|
+
readonly _tag: "SafeToRetry";
|
|
1469
|
+
} | {
|
|
1468
1470
|
readonly _tag: "CompletedWithResult";
|
|
1469
1471
|
readonly result: Schema.Json;
|
|
1470
1472
|
readonly isFailure: boolean;
|
|
1471
1473
|
} | {
|
|
1472
1474
|
readonly _tag: "NeverHappened";
|
|
1473
|
-
} | {
|
|
1474
|
-
readonly _tag: "SafeToRetry";
|
|
1475
1475
|
} | {
|
|
1476
1476
|
readonly _tag: "AbortSubmission";
|
|
1477
1477
|
};
|
|
@@ -1481,10 +1481,31 @@ export declare const encodeHostResponse: (input: AbortRecorded | ApprovalRecorde
|
|
|
1481
1481
|
} | {
|
|
1482
1482
|
readonly _tag: "HostFailed";
|
|
1483
1483
|
readonly failure: {
|
|
1484
|
-
readonly _tag: "
|
|
1484
|
+
readonly _tag: "AdmissionConflict";
|
|
1485
|
+
readonly threadId: string;
|
|
1486
|
+
readonly principal: string;
|
|
1487
|
+
readonly idempotencyKey: string;
|
|
1488
|
+
readonly existingInputDigest: string;
|
|
1489
|
+
readonly attemptedInputDigest: string;
|
|
1490
|
+
} | {
|
|
1491
|
+
readonly _tag: "AdmissionPolicyError";
|
|
1492
|
+
readonly reason: "occupied" | "refused" | "unavailable";
|
|
1493
|
+
readonly code: string;
|
|
1494
|
+
readonly cause?: import("effect-agent/failure-diagnostic").Diagnostic | undefined;
|
|
1495
|
+
readonly stack?: string | undefined;
|
|
1496
|
+
} | {
|
|
1497
|
+
readonly _tag: "SettlementConflict";
|
|
1498
|
+
readonly submissionId: string;
|
|
1499
|
+
readonly existingOutcome: "aborted" | "completed" | "failed";
|
|
1500
|
+
} | {
|
|
1501
|
+
readonly _tag: "JoinedToHost";
|
|
1502
|
+
readonly submissionId: string;
|
|
1503
|
+
readonly hostSubmissionId: string;
|
|
1504
|
+
} | {
|
|
1505
|
+
readonly _tag: "LedgerError";
|
|
1485
1506
|
readonly operation: string;
|
|
1486
1507
|
readonly message: string;
|
|
1487
|
-
readonly cause?:
|
|
1508
|
+
readonly cause?: import("effect-agent/failure-diagnostic").Diagnostic | undefined;
|
|
1488
1509
|
} | {
|
|
1489
1510
|
readonly _tag: "ThreadStoreError";
|
|
1490
1511
|
readonly operation: string;
|
|
@@ -1493,11 +1514,6 @@ export declare const encodeHostResponse: (input: AbortRecorded | ApprovalRecorde
|
|
|
1493
1514
|
} | {
|
|
1494
1515
|
readonly _tag: "ThreadNotMaterialized";
|
|
1495
1516
|
readonly threadId: string;
|
|
1496
|
-
} | {
|
|
1497
|
-
readonly _tag: "LedgerError";
|
|
1498
|
-
readonly operation: string;
|
|
1499
|
-
readonly message: string;
|
|
1500
|
-
readonly cause?: import("effect-agent/failure-diagnostic").Diagnostic | undefined;
|
|
1501
1517
|
} | {
|
|
1502
1518
|
readonly _tag: "AppendConflict";
|
|
1503
1519
|
readonly threadId: string;
|
|
@@ -1511,24 +1527,8 @@ export declare const encodeHostResponse: (input: AbortRecorded | ApprovalRecorde
|
|
|
1511
1527
|
readonly actualEpoch: number;
|
|
1512
1528
|
readonly attemptedEpoch: number;
|
|
1513
1529
|
} | {
|
|
1514
|
-
readonly _tag: "
|
|
1515
|
-
readonly
|
|
1516
|
-
readonly reason: string;
|
|
1517
|
-
readonly threadId?: string | undefined;
|
|
1518
|
-
readonly submissionId?: string | undefined;
|
|
1519
|
-
} | {
|
|
1520
|
-
readonly _tag: "AdmissionConflict";
|
|
1521
|
-
readonly threadId: string;
|
|
1522
|
-
readonly principal: string;
|
|
1523
|
-
readonly idempotencyKey: string;
|
|
1524
|
-
readonly existingInputDigest: string;
|
|
1525
|
-
readonly attemptedInputDigest: string;
|
|
1526
|
-
} | {
|
|
1527
|
-
readonly _tag: "AdmissionPolicyError";
|
|
1528
|
-
readonly reason: "occupied" | "refused" | "unavailable";
|
|
1529
|
-
readonly code: string;
|
|
1530
|
-
readonly cause?: import("effect-agent/failure-diagnostic").Diagnostic | undefined;
|
|
1531
|
-
readonly stack?: string | undefined;
|
|
1530
|
+
readonly _tag: "HostProtocolError";
|
|
1531
|
+
readonly message: string;
|
|
1532
1532
|
} | {
|
|
1533
1533
|
readonly _tag: "AgentInputError";
|
|
1534
1534
|
readonly message: string;
|
|
@@ -1537,33 +1537,33 @@ export declare const encodeHostResponse: (input: AbortRecorded | ApprovalRecorde
|
|
|
1537
1537
|
readonly message: string;
|
|
1538
1538
|
readonly cause?: Schema.Json | undefined;
|
|
1539
1539
|
} | {
|
|
1540
|
-
readonly _tag: "
|
|
1541
|
-
readonly location: "abort:after-intent" | "approval:after-request-append" | "approval:after-suspend" | "checkpoint:after-save" | "checkpoint:before-save" | "claim:after-claim" | "compaction:after-canonical-append" | "compaction:before-canonical-append" | "input:after-canonical-append" | "join:after-canonical-append" | "join:after-claim" | "policy:after-reservation-append" | "policy:before-reservation-append" | "resolve:after-intent" | "run:after-duration-append" | "run:after-start-append" | "run:before-duration-append" | "run:before-start-append" | "step:after-step-append" | "subagent:after-admit" | "subagent:after-child-abort-intent" | "subagent:after-child-ready" | "subagent:after-join-append" | "subagent:after-release" | "subagent:after-release-pending" | "subagent:after-request-append" | "subagent:after-reserve" | "subagent:after-sibling-settle" | "subagent:after-start-append" | "subagent:after-suspend" | "subagent:before-join-append" | "submit:after-admit" | "submit:after-materialize" | "terminalize:after-canonical-append" | "terminalize:after-reserve" | "tools:after-prepared-append" | "tools:after-unavailable-append" | "tools:before-prepared-append" | "tools:before-unavailable-append" | "turn:after-canonical-append" | "turn:after-response-append" | "turn:after-results-append" | "update:after-canonical-append" | "update:after-delivery-insert" | "update:before-canonical-append" | "update:before-delivery-insert" | "worker:after-completion-append" | "worker:after-origin-append" | "worker:after-report-append" | "worker:after-report-delivery" | "worker:after-source-append" | "worker:after-subtree-append" | "worker:before-completion-append" | "worker:before-origin-append" | "worker:before-report-append" | "worker:before-report-delivery" | "worker:before-source-append" | "worker:before-subtree-append";
|
|
1542
|
-
} | {
|
|
1543
|
-
readonly _tag: "SettlementConflict";
|
|
1540
|
+
readonly _tag: "ApprovalConflict";
|
|
1544
1541
|
readonly submissionId: string;
|
|
1545
|
-
readonly
|
|
1542
|
+
readonly toolCallId: string;
|
|
1543
|
+
readonly existingDecision: "approved" | "denied";
|
|
1546
1544
|
} | {
|
|
1547
|
-
readonly _tag: "
|
|
1545
|
+
readonly _tag: "UnknownResolutionConflict";
|
|
1548
1546
|
readonly submissionId: string;
|
|
1549
|
-
readonly
|
|
1547
|
+
readonly toolCallId: string;
|
|
1548
|
+
} | {
|
|
1549
|
+
readonly _tag: "DurableRuntimeFailpointError";
|
|
1550
|
+
readonly location: "abort:after-intent" | "approval:after-request-append" | "approval:after-suspend" | "checkpoint:after-save" | "checkpoint:before-save" | "claim:after-claim" | "compaction:after-canonical-append" | "compaction:before-canonical-append" | "input:after-canonical-append" | "join:after-canonical-append" | "join:after-claim" | "policy:after-reservation-append" | "policy:before-reservation-append" | "resolve:after-intent" | "run:after-duration-append" | "run:after-start-append" | "run:before-duration-append" | "run:before-start-append" | "step:after-step-append" | "subagent:after-admit" | "subagent:after-child-abort-intent" | "subagent:after-child-ready" | "subagent:after-join-append" | "subagent:after-release" | "subagent:after-release-pending" | "subagent:after-request-append" | "subagent:after-reserve" | "subagent:after-sibling-settle" | "subagent:after-start-append" | "subagent:after-suspend" | "subagent:before-join-append" | "submit:after-admit" | "submit:after-materialize" | "terminalize:after-canonical-append" | "terminalize:after-reserve" | "tools:after-prepared-append" | "tools:after-unavailable-append" | "tools:before-prepared-append" | "tools:before-unavailable-append" | "turn:after-canonical-append" | "turn:after-response-append" | "turn:after-results-append" | "update:after-canonical-append" | "update:after-delivery-insert" | "update:before-canonical-append" | "update:before-delivery-insert" | "worker:after-completion-append" | "worker:after-origin-append" | "worker:after-report-append" | "worker:after-report-delivery" | "worker:after-source-append" | "worker:after-subtree-append" | "worker:before-completion-append" | "worker:before-origin-append" | "worker:before-report-append" | "worker:before-report-delivery" | "worker:before-source-append" | "worker:before-subtree-append";
|
|
1550
1551
|
} | {
|
|
1551
1552
|
readonly _tag: "AdmissionLimitExceeded";
|
|
1552
1553
|
readonly limit: "database-bytes" | "input-bytes" | "queue-depth";
|
|
1553
1554
|
readonly actual: number;
|
|
1554
1555
|
readonly maximum: number;
|
|
1555
1556
|
} | {
|
|
1556
|
-
readonly _tag: "
|
|
1557
|
+
readonly _tag: "DurableAlarmError";
|
|
1558
|
+
readonly operation: string;
|
|
1557
1559
|
readonly message: string;
|
|
1560
|
+
readonly cause?: Schema.Json | undefined;
|
|
1558
1561
|
} | {
|
|
1559
|
-
readonly _tag: "
|
|
1560
|
-
readonly
|
|
1561
|
-
readonly
|
|
1562
|
-
readonly
|
|
1563
|
-
|
|
1564
|
-
readonly _tag: "UnknownResolutionConflict";
|
|
1565
|
-
readonly submissionId: string;
|
|
1566
|
-
readonly toolCallId: string;
|
|
1562
|
+
readonly _tag: "OperationDenied";
|
|
1563
|
+
readonly operation: "abort" | "awaitSettlement" | "explain" | "observe" | "resolveApproval" | "resolveUnknown" | "retry" | "scanObligations" | "verify" | "wake";
|
|
1564
|
+
readonly reason: string;
|
|
1565
|
+
readonly threadId?: string | undefined;
|
|
1566
|
+
readonly submissionId?: string | undefined;
|
|
1567
1567
|
};
|
|
1568
1568
|
}, Schema.SchemaError, never>;
|
|
1569
1569
|
export declare const decodeHostResponse: (input: unknown, options?: import("effect/SchemaAST").ParseOptions) => Effect.Effect<AbortRecorded | ApprovalRecorded | HostFailed | ObservedPage | ProgressCancelled | ProgressObserved | SettlementReached | SubmissionStatusResponse | SubmitSucceeded | UnknownResolutionRecorded, Schema.SchemaError, never>;
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import { Context, Effect, Layer, Redacted, Schema, Scope } from "effect";
|
|
2
2
|
import { SandboxImplementation } from "effect-agent/sandbox";
|
|
3
3
|
import { HttpClient } from "effect/unstable/http";
|
|
4
|
-
import { BrowserHandle, InteractiveBrowser, InteractiveBrowserError, InteractiveBrowserPolicy, InteractiveBrowserPolicyDeniedError } from "effect-agent/interactive-browser";
|
|
4
|
+
import { BrowserHandle, BrowserSelectFileRequest, InteractiveBrowser, InteractiveBrowserError, InteractiveBrowserPolicy, InteractiveBrowserPolicyDeniedError } from "effect-agent/interactive-browser";
|
|
5
5
|
//#region src/internal/browser-session-lifecycle.d.ts
|
|
6
6
|
declare const BrowserRunCleanupError_base: Schema.Class<BrowserRunCleanupError, Schema.TaggedStruct<"BrowserRunCleanupError", {
|
|
7
7
|
readonly reason: Schema.Literals<readonly ["configuration", "authorization", "rate-limited", "provider", "malformed", "timeout", "pending"]>;
|
|
@@ -83,6 +83,7 @@ interface BrowserRunInteractivePage {
|
|
|
83
83
|
readonly readText: (selector: string | undefined, maximumBytes: number) => Promise<unknown>;
|
|
84
84
|
readonly fill: (selector: string, value: string, signal: AbortSignal, onDispatch: () => void) => Promise<unknown>;
|
|
85
85
|
readonly click: (selector: string, signal: AbortSignal, onDispatch: () => void) => Promise<unknown>;
|
|
86
|
+
readonly selectFile: (request: BrowserSelectFileRequest, signal: AbortSignal, onDispatch: () => void) => Promise<unknown>;
|
|
86
87
|
readonly screenshot: (fullPage: boolean) => Promise<unknown>;
|
|
87
88
|
readonly scroll: (deltaX: number, deltaY: number) => Promise<void>;
|
|
88
89
|
readonly setViewport: (viewport: BrowserRunViewport) => Promise<void>;
|
|
@@ -166,4 +167,4 @@ declare const CloudflareInteractiveBrowser: {
|
|
|
166
167
|
};
|
|
167
168
|
//#endregion
|
|
168
169
|
export { isBrowserRunUndispatchedActionError as C, browserRunInteractiveLayer as S, BrowserRunSessionLifecycle as T, BrowserRunViewport as _, BrowserRunInteractiveAcquisition as a, browserRunInteractiveHostLayer as b, BrowserRunInteractiveCdpSession as c, BrowserRunInteractivePage as d, BrowserRunInteractiveRequest as f, BrowserRunLiveViewResult as g, BrowserRunLiveViewRequest as h, BrowserRunHandoffState as i, BrowserRunInteractiveContext as l, BrowserRunInteractiveSession as m, BrowserRunHandoffRequest as n, BrowserRunInteractiveBinding as o, BrowserRunInteractiveRequestListener as p, BrowserRunHandoffResult as r, BrowserRunInteractiveBrowser as s, BrowserRunCloudflareCommand as t, BrowserRunInteractiveHost as u, CloudflareInteractiveBrowser as v, BrowserRunCleanupError as w, browserRunInteractiveImplementation as x, CloudflareInteractiveBrowserOptions as y };
|
|
169
|
-
//# sourceMappingURL=InteractiveBrowser-
|
|
170
|
+
//# sourceMappingURL=InteractiveBrowser-B3S8if51.d.mts.map
|
|
@@ -1,9 +1,80 @@
|
|
|
1
|
-
import { Clock, Context, Duration, Effect, Layer, Option, Redacted, Ref, Schema, Scope, Semaphore, Stream } from "effect";
|
|
1
|
+
import { Clock, Context, Duration, Effect, Encoding, Layer, Option, Redacted, Ref, Schema, Scope, Semaphore, Stream } from "effect";
|
|
2
2
|
import { PageScreenshotResult } from "effect-agent/page-screenshot";
|
|
3
3
|
import { SandboxImplementation } from "effect-agent/sandbox";
|
|
4
4
|
import { FetchHttpClient, HttpClient, HttpClientRequest } from "effect/unstable/http";
|
|
5
5
|
import puppeteer from "@cloudflare/puppeteer";
|
|
6
|
-
import { BrowserActionResult, BrowserNavigationResult, BrowserScreenshotRequest, BrowserScrollRequest, BrowserTextResult, InteractiveBrowser, InteractiveBrowserActionError, InteractiveBrowserBusyError, InteractiveBrowserCapacityError, InteractiveBrowserExpiredError, InteractiveBrowserLimitError, InteractiveBrowserPolicy, InteractiveBrowserPolicyDeniedError, InteractiveBrowserProtocolError, InteractiveBrowserTargetUrl, InteractiveBrowserUnsupportedError } from "effect-agent/interactive-browser";
|
|
6
|
+
import { BrowserActionResult, BrowserFileSelectionResult, BrowserNavigationResult, BrowserScreenshotRequest, BrowserScrollRequest, BrowserSelectFileRequest, BrowserTextResult, InteractiveBrowser, InteractiveBrowserActionError, InteractiveBrowserBusyError, InteractiveBrowserCapacityError, InteractiveBrowserExpiredError, InteractiveBrowserLimitError, InteractiveBrowserPolicy, InteractiveBrowserPolicyDeniedError, InteractiveBrowserProtocolError, InteractiveBrowserTargetUrl, InteractiveBrowserUnsupportedError } from "effect-agent/interactive-browser";
|
|
7
|
+
//#region src/internal/browser-file-selection.ts
|
|
8
|
+
function setFileSelection(element, encoded, name, type) {
|
|
9
|
+
if (Reflect.get(element, "type") !== "file" || Reflect.get(element, "disabled") || Reflect.get(element, "webkitdirectory")) throw new Error("The target is not an enabled file input");
|
|
10
|
+
const bytes = Uint8Array.from(atob(encoded), (character) => character.charCodeAt(0));
|
|
11
|
+
const transfer = new (Reflect.get(globalThis, "DataTransfer"))();
|
|
12
|
+
transfer.items.add(new File([bytes], name, { type }));
|
|
13
|
+
Reflect.set(element, "files", transfer.files);
|
|
14
|
+
const selected = Reflect.get(element, "files");
|
|
15
|
+
if (selected?.length !== 1 || selected[0]?.size !== bytes.length || selected[0]?.name !== name || selected[0]?.type !== type) throw new Error("The input did not retain the selected file");
|
|
16
|
+
const dispatch = Reflect.get(element, "dispatchEvent");
|
|
17
|
+
Reflect.apply(dispatch, element, [new Event("input", { bubbles: true })]);
|
|
18
|
+
Reflect.apply(dispatch, element, [new Event("change", { bubbles: true })]);
|
|
19
|
+
}
|
|
20
|
+
const makeFileSelection = (page) => async (request, signal) => {
|
|
21
|
+
const encoded = Encoding.encodeBase64(request.bytes);
|
|
22
|
+
const session = request.target === "chooser" ? await page.createCDPSession() : void 0;
|
|
23
|
+
if (session !== void 0) try {
|
|
24
|
+
await session.send("Page.enable");
|
|
25
|
+
await session.send("Page.setInterceptFileChooserDialog", { enabled: true });
|
|
26
|
+
} catch (cause) {
|
|
27
|
+
await session.detach();
|
|
28
|
+
throw cause;
|
|
29
|
+
}
|
|
30
|
+
const select = async (element) => {
|
|
31
|
+
if (session === void 0) return element.evaluate(setFileSelection, encoded, request.fileName, request.mediaType);
|
|
32
|
+
let onOpened = () => {};
|
|
33
|
+
let onAbort = () => {};
|
|
34
|
+
let timer;
|
|
35
|
+
const opened = new Promise((resolve, reject) => {
|
|
36
|
+
onOpened = (event) => event.backendNodeId === void 0 ? reject(/* @__PURE__ */ new Error("The chooser has no file input")) : resolve(event.backendNodeId);
|
|
37
|
+
onAbort = () => reject(/* @__PURE__ */ new Error("File selection interrupted"));
|
|
38
|
+
session.on("Page.fileChooserOpened", onOpened);
|
|
39
|
+
signal.addEventListener("abort", onAbort, { once: true });
|
|
40
|
+
timer = setTimeout(() => reject(/* @__PURE__ */ new Error("No file chooser opened")), 5e3);
|
|
41
|
+
if (signal.aborted) onAbort();
|
|
42
|
+
});
|
|
43
|
+
try {
|
|
44
|
+
const [backendNodeId] = await Promise.all([opened, element.click()]);
|
|
45
|
+
if (signal.aborted) throw new Error("File selection interrupted");
|
|
46
|
+
const objectId = (await session.send("DOM.resolveNode", { backendNodeId })).object.objectId;
|
|
47
|
+
if (objectId === void 0) throw new Error("The chooser has no file input");
|
|
48
|
+
if (signal.aborted) throw new Error("File selection interrupted");
|
|
49
|
+
if ((await session.send("Runtime.callFunctionOn", {
|
|
50
|
+
objectId,
|
|
51
|
+
functionDeclaration: `function(encoded, name, type) { (${setFileSelection.toString()})(this, encoded, name, type); }`,
|
|
52
|
+
arguments: [
|
|
53
|
+
{ value: encoded },
|
|
54
|
+
{ value: request.fileName },
|
|
55
|
+
{ value: request.mediaType }
|
|
56
|
+
],
|
|
57
|
+
returnByValue: true
|
|
58
|
+
})).exceptionDetails !== void 0) throw new Error("The chooser did not select the file");
|
|
59
|
+
} finally {
|
|
60
|
+
clearTimeout(timer);
|
|
61
|
+
session.off("Page.fileChooserOpened", onOpened);
|
|
62
|
+
signal.removeEventListener("abort", onAbort);
|
|
63
|
+
}
|
|
64
|
+
};
|
|
65
|
+
return {
|
|
66
|
+
validate: async (element) => request.target === "chooser" || await element.evaluate((input) => Reflect.get(input, "type") === "file" && !Reflect.get(input, "disabled") && !Reflect.get(input, "webkitdirectory")),
|
|
67
|
+
select,
|
|
68
|
+
close: async () => {
|
|
69
|
+
if (session !== void 0) try {
|
|
70
|
+
await session.send("Page.setInterceptFileChooserDialog", { enabled: false });
|
|
71
|
+
} finally {
|
|
72
|
+
await session.detach();
|
|
73
|
+
}
|
|
74
|
+
}
|
|
75
|
+
};
|
|
76
|
+
};
|
|
77
|
+
//#endregion
|
|
7
78
|
//#region src/internal/browser-session-lifecycle.ts
|
|
8
79
|
var BrowserRunCleanupError = class extends Schema.TaggedError()("BrowserRunCleanupError", {
|
|
9
80
|
reason: Schema.Literals([
|
|
@@ -413,7 +484,7 @@ const makeActionRequestTracker = (page, signal) => {
|
|
|
413
484
|
const disposeActionHandles = async (handles) => {
|
|
414
485
|
await boundedBestEffort(Promise.allSettled(handles.map(async (handle) => handle.dispose())), ACTION_POST_STATE_MILLIS);
|
|
415
486
|
};
|
|
416
|
-
const runObservedPageAction = async (page, selector, signal, onDispatch, action) => {
|
|
487
|
+
const runObservedPageAction = async (page, selector, signal, onDispatch, action, validate) => {
|
|
417
488
|
if (signal.aborted) throw new BrowserRunActionUndispatched(0);
|
|
418
489
|
const before = Schema.decodeUnknownSync(ActionTargetState)(await readActionTarget(page, selector));
|
|
419
490
|
if (before.matchCount !== 1 || before.invalidSelector === true) throw new BrowserRunActionUndispatched(before.matchCount);
|
|
@@ -434,6 +505,7 @@ const runObservedPageAction = async (page, selector, signal, onDispatch, action)
|
|
|
434
505
|
};
|
|
435
506
|
signal.addEventListener("abort", onAbort, { once: true });
|
|
436
507
|
try {
|
|
508
|
+
if (validate !== void 0 && !await validate(matches[0])) throw new BrowserRunActionUndispatched(1);
|
|
437
509
|
tracker = makeActionRequestTracker(page, signal);
|
|
438
510
|
if (signal.aborted) throw new BrowserRunActionUndispatched(1);
|
|
439
511
|
onDispatch();
|
|
@@ -454,6 +526,7 @@ const runObservedPageAction = async (page, selector, signal, onDispatch, action)
|
|
|
454
526
|
}
|
|
455
527
|
};
|
|
456
528
|
const makeProductionPage = (page) => {
|
|
529
|
+
const prepareFileSelection = makeFileSelection(page);
|
|
457
530
|
const listeners = /* @__PURE__ */ new Map();
|
|
458
531
|
return {
|
|
459
532
|
close: () => page.close(),
|
|
@@ -613,6 +686,14 @@ const makeProductionPage = (page) => {
|
|
|
613
686
|
}
|
|
614
687
|
}, value)),
|
|
615
688
|
click: (selector, signal, onDispatch) => runObservedPageAction(page, selector, signal, onDispatch, (element) => element.click()),
|
|
689
|
+
selectFile: async (request, signal, onDispatch) => {
|
|
690
|
+
const selection = await prepareFileSelection(request, signal);
|
|
691
|
+
try {
|
|
692
|
+
return await runObservedPageAction(page, request.selector, signal, onDispatch, selection.select, selection.validate);
|
|
693
|
+
} finally {
|
|
694
|
+
await selection.close();
|
|
695
|
+
}
|
|
696
|
+
},
|
|
616
697
|
screenshot: (fullPage) => page.screenshot({
|
|
617
698
|
type: "png",
|
|
618
699
|
fullPage
|
|
@@ -941,6 +1022,17 @@ const makeHandle = Effect.fn("BrowserRunInteractive.makeHandle")(function* (page
|
|
|
941
1022
|
yield* logActionObservation("click", observation);
|
|
942
1023
|
return yield* decodeActionResult(page, policy);
|
|
943
1024
|
})),
|
|
1025
|
+
selectFile: (request) => Schema.decodeEffect(BrowserSelectFileRequest)(request).pipe(Effect.mapError(() => policyError("The browser file selection request is malformed")), Effect.flatMap((decoded) => run(Effect.gen(function* () {
|
|
1026
|
+
const observation = yield* observedAction("select-file", (signal, onDispatch) => page.selectFile(decoded, signal, onDispatch)).pipe(Effect.flatMap(decodeActionObservation));
|
|
1027
|
+
yield* logActionObservation("select-file", observation);
|
|
1028
|
+
const result = yield* decodeActionResult(page, policy);
|
|
1029
|
+
return BrowserFileSelectionResult.make({
|
|
1030
|
+
url: result.url,
|
|
1031
|
+
fileName: decoded.fileName,
|
|
1032
|
+
mediaType: decoded.mediaType,
|
|
1033
|
+
size: decoded.bytes.length
|
|
1034
|
+
});
|
|
1035
|
+
})))),
|
|
944
1036
|
screenshot: (request) => Schema.decodeEffect(BrowserScreenshotRequest)(request).pipe(Effect.mapError(() => policyError("The browser screenshot request is malformed")), Effect.flatMap((decoded) => run(Effect.gen(function* () {
|
|
945
1037
|
const raw = yield* remote("screenshot", () => page.screenshot(decoded.fullPage));
|
|
946
1038
|
const bytes = yield* Schema.decodeUnknownEffect(PngBytes)(raw).pipe(Effect.mapError(() => protocolError("The browser returned a malformed PNG screenshot")));
|
|
@@ -1177,4 +1269,4 @@ const CloudflareInteractiveBrowser = {
|
|
|
1177
1269
|
//#endregion
|
|
1178
1270
|
export { BrowserRunInteractiveHost as a, BrowserRunViewport as c, browserRunInteractiveImplementation as d, browserRunInteractiveLayer as f, BrowserRunSessionLifecycle as h, BrowserRunInteractiveBinding as i, CloudflareInteractiveBrowser as l, BrowserRunCleanupError as m, BrowserRunHandoffResult as n, BrowserRunLiveViewRequest as o, isBrowserRunUndispatchedActionError as p, BrowserRunHandoffState as r, BrowserRunLiveViewResult as s, BrowserRunHandoffRequest as t, browserRunInteractiveHostLayer as u };
|
|
1179
1271
|
|
|
1180
|
-
//# sourceMappingURL=InteractiveBrowser-
|
|
1272
|
+
//# sourceMappingURL=InteractiveBrowser-xVNX7ARl.mjs.map
|