@poe-platform/safe-bash 0.1.695 → 0.1.697
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 +1 -1
- package/dist/safe-bash/playwright/adapter.d.ts +4 -2
- package/dist/safe-bash/playwright/adapter.d.ts.map +1 -1
- package/dist/safe-bash/playwright/adapter.js.map +1 -1
- package/dist/safe-bash/playwright/controller.d.ts.map +1 -1
- package/dist/safe-bash/playwright/controller.js +8 -2
- package/dist/safe-bash/playwright/controller.js.map +1 -1
- package/dist/safe-bash/playwright/index.d.ts +2 -1
- package/dist/safe-bash/playwright/index.d.ts.map +1 -1
- package/dist/safe-bash/playwright/index.js +2 -1
- package/dist/safe-bash/playwright/index.js.map +1 -1
- package/dist/safe-bash/playwright/native-storage-targets.d.ts.map +1 -1
- package/dist/safe-bash/playwright/native-storage-targets.js +19 -2
- package/dist/safe-bash/playwright/native-storage-targets.js.map +1 -1
- package/dist/safe-bash/playwright/profile.d.ts +38 -0
- package/dist/safe-bash/playwright/profile.d.ts.map +1 -0
- package/dist/safe-bash/playwright/profile.js +147 -0
- package/dist/safe-bash/playwright/profile.js.map +1 -0
- package/dist/safe-playwright-cloudflare/browser-artifact.js +46 -0
- package/dist/safe-playwright-cloudflare/browser-code-executor.d.ts +7 -0
- package/dist/safe-playwright-cloudflare/browser-code-executor.js +20 -0
- package/dist/safe-playwright-cloudflare/browser-codegen.generated.js +8701 -0
- package/dist/safe-playwright-cloudflare/browser-codegen.js +26 -0
- package/dist/safe-playwright-cloudflare/browser-page-cdp.js +21 -0
- package/dist/safe-playwright-cloudflare/browser-private-transport.js +338 -0
- package/dist/safe-playwright-cloudflare/browser-profile-runtime.js +33 -0
- package/dist/safe-playwright-cloudflare/browser-run-code-budget.js +130 -0
- package/dist/safe-playwright-cloudflare/browser-run-code-context-state.js +54 -0
- package/dist/safe-playwright-cloudflare/browser-run-code-contract.js +1 -0
- package/dist/safe-playwright-cloudflare/browser-run-code-guest.generated.js +2 -0
- package/dist/safe-playwright-cloudflare/browser-run-code-native.js +180 -0
- package/dist/safe-playwright-cloudflare/browser-run-code-relay.js +149 -0
- package/dist/safe-playwright-cloudflare/browser-run-code-state.js +102 -0
- package/dist/safe-playwright-cloudflare/browser-run-code.js +251 -0
- package/dist/safe-playwright-cloudflare/browser-snapshot-json-injected.js +80 -0
- package/dist/safe-playwright-cloudflare/browser-snapshot-json.js +89 -0
- package/dist/safe-playwright-cloudflare/browser-socket-closure.js +111 -0
- package/dist/safe-playwright-cloudflare/browser-storage-control.js +262 -0
- package/dist/safe-playwright-cloudflare/browser-trace.js +143 -0
- package/dist/safe-playwright-cloudflare/index.d.ts +2 -0
- package/dist/safe-playwright-cloudflare/index.js +1 -0
- package/dist/safe-playwright-cloudflare/shell-browser-resource.d.ts +17 -0
- package/dist/safe-playwright-cloudflare/shell-browser-resource.js +217 -0
- package/dist/safe-playwright-cloudflare/shell-playwright.d.ts +11 -0
- package/dist/safe-playwright-cloudflare/shell-playwright.js +110 -0
- package/package.json +10 -2
- package/third-party/safe-playwright-cloudflare/third-party/playwright/LICENSE +202 -0
- package/third-party/safe-playwright-cloudflare/third-party/playwright/NOTICE +12 -0
|
@@ -0,0 +1,147 @@
|
|
|
1
|
+
import { readPlaywrightStorageState } from './native-storage-replacement.js';
|
|
2
|
+
import { parsePlaywrightContextOptions } from './open-options.js';
|
|
3
|
+
import { parsePlaywrightSessionConfiguration } from './session-configuration.js';
|
|
4
|
+
import { parsePlaywrightStorageState } from './storage-state.js';
|
|
5
|
+
/** Validate persisted JSON before it can allocate or navigate a browser. */
|
|
6
|
+
export function parseBrowserProfile(bytes, limits) {
|
|
7
|
+
validateProfileLimits(limits);
|
|
8
|
+
if (bytes.byteLength > limits.maxBytes)
|
|
9
|
+
throw new Error("Browser profile byte limit exceeded");
|
|
10
|
+
const value = JSON.parse(new TextDecoder("utf-8", { fatal: true }).decode(bytes));
|
|
11
|
+
if (!value ||
|
|
12
|
+
typeof value !== "object" ||
|
|
13
|
+
!("state" in value) ||
|
|
14
|
+
!("tabs" in value) ||
|
|
15
|
+
!Array.isArray(value.tabs) ||
|
|
16
|
+
value.tabs.length > limits.maxTabs ||
|
|
17
|
+
!("selected" in value) ||
|
|
18
|
+
typeof value.selected !== "number" ||
|
|
19
|
+
!Number.isSafeInteger(value.selected) ||
|
|
20
|
+
value.selected < 0 ||
|
|
21
|
+
value.selected >= Math.max(1, value.tabs.length))
|
|
22
|
+
throw new Error("Invalid stored browser profile");
|
|
23
|
+
const tabs = [];
|
|
24
|
+
for (const tab of value.tabs) {
|
|
25
|
+
if (typeof tab !== "string" || !URL.canParse(tab))
|
|
26
|
+
throw new Error("Invalid stored browser tab");
|
|
27
|
+
tabs.push(tab);
|
|
28
|
+
}
|
|
29
|
+
return {
|
|
30
|
+
...profileSettings(value),
|
|
31
|
+
state: parsePlaywrightStorageState(value.state, { maxBytes: limits.maxBytes }),
|
|
32
|
+
tabs,
|
|
33
|
+
selected: value.selected,
|
|
34
|
+
...('runtimeState' in value ? { runtimeState: value.runtimeState } : {}),
|
|
35
|
+
};
|
|
36
|
+
}
|
|
37
|
+
function profileSettings(value) {
|
|
38
|
+
const settings = {};
|
|
39
|
+
if ("expiresAt" in value)
|
|
40
|
+
settings.expiresAt = timing(value.expiresAt);
|
|
41
|
+
if ("idleTimeoutMs" in value)
|
|
42
|
+
settings.idleTimeoutMs = timing(value.idleTimeoutMs);
|
|
43
|
+
if ("contextOptions" in value) {
|
|
44
|
+
settings.contextOptions = parsePlaywrightContextOptions(value.contextOptions);
|
|
45
|
+
if (settings.contextOptions.storageState)
|
|
46
|
+
throw new Error("Stored context options must use the current profile state");
|
|
47
|
+
}
|
|
48
|
+
if ("configuration" in value)
|
|
49
|
+
settings.configuration = parsePlaywrightSessionConfiguration(value.configuration);
|
|
50
|
+
return settings;
|
|
51
|
+
}
|
|
52
|
+
function timing(value) {
|
|
53
|
+
if (typeof value !== "number" || !Number.isSafeInteger(value) || value < 0)
|
|
54
|
+
throw new Error("Invalid stored browser expiry");
|
|
55
|
+
return value;
|
|
56
|
+
}
|
|
57
|
+
function validateProfileLimits(limits) {
|
|
58
|
+
if (!limits || !Number.isSafeInteger(limits.maxBytes) || limits.maxBytes <= 0 || !Number.isSafeInteger(limits.maxTabs) || limits.maxTabs <= 0)
|
|
59
|
+
throw new TypeError("Invalid browser profile limits");
|
|
60
|
+
}
|
|
61
|
+
export function encodeBrowserProfile(profile, limits) {
|
|
62
|
+
const bytes = new TextEncoder().encode(JSON.stringify(profile));
|
|
63
|
+
parseBrowserProfile(bytes, limits);
|
|
64
|
+
return bytes;
|
|
65
|
+
}
|
|
66
|
+
/** Return an initializer so the standard controller installs configuration before navigation. */
|
|
67
|
+
export async function restoreBrowserProfile(options) {
|
|
68
|
+
const { adapter, limits, name, signal } = options;
|
|
69
|
+
signal.throwIfAborted();
|
|
70
|
+
const profile = parseBrowserProfile(encodeBrowserProfile(options.profile, limits), limits);
|
|
71
|
+
const lease = await adapter.acquire({
|
|
72
|
+
acquisitionId: crypto.randomUUID(), session: name, browser: 'chromium', headless: true,
|
|
73
|
+
contextOptions: { ...profile.contextOptions, storageState: profile.state }, signal,
|
|
74
|
+
});
|
|
75
|
+
try {
|
|
76
|
+
const pages = [];
|
|
77
|
+
const urls = profile.tabs.length ? profile.tabs : ['about:blank'];
|
|
78
|
+
for (const ignoredUrl of urls) {
|
|
79
|
+
signal.throwIfAborted();
|
|
80
|
+
pages.push(await lease.context.newPage());
|
|
81
|
+
}
|
|
82
|
+
signal.throwIfAborted();
|
|
83
|
+
return {
|
|
84
|
+
lease, selectedPage: pages[profile.selected],
|
|
85
|
+
...(profile.configuration === undefined ? {} : { configuration: profile.configuration }),
|
|
86
|
+
...(profile.contextOptions === undefined ? {} : { contextOptions: profile.contextOptions }),
|
|
87
|
+
...(profile.expiresAt === undefined ? {} : { expiresAt: profile.expiresAt }),
|
|
88
|
+
...(profile.idleTimeoutMs === undefined ? {} : { idleTimeoutMs: profile.idleTimeoutMs }),
|
|
89
|
+
async initialize({ signal }) {
|
|
90
|
+
// The controller owns retirement after adoption, including failed navigation.
|
|
91
|
+
if (profile.runtimeState !== undefined) {
|
|
92
|
+
const runtime = lease.context.browserProfile;
|
|
93
|
+
if (!runtime)
|
|
94
|
+
throw new Error('Browser adapter cannot restore provider profile settings');
|
|
95
|
+
await runtime.restore(profile.runtimeState, signal);
|
|
96
|
+
}
|
|
97
|
+
for (let i = 0; i < pages.length; i++) {
|
|
98
|
+
signal.throwIfAborted();
|
|
99
|
+
await pages[i].goto(urls[i]);
|
|
100
|
+
}
|
|
101
|
+
},
|
|
102
|
+
};
|
|
103
|
+
}
|
|
104
|
+
catch (error) {
|
|
105
|
+
try {
|
|
106
|
+
await lease.release();
|
|
107
|
+
}
|
|
108
|
+
catch (cleanup) {
|
|
109
|
+
throw new AggregateError([error, cleanup], 'Browser profile restoration and cleanup failed');
|
|
110
|
+
}
|
|
111
|
+
throw error;
|
|
112
|
+
}
|
|
113
|
+
}
|
|
114
|
+
/** Read closed-origin IndexedDB using isolated targets and settle every registered reader cleanup. */
|
|
115
|
+
export async function checkpointBrowserProfile(session, limits, signal) {
|
|
116
|
+
validateProfileLimits(limits);
|
|
117
|
+
signal.throwIfAborted();
|
|
118
|
+
const cleanups = [];
|
|
119
|
+
const [result] = await Promise.allSettled([readPlaywrightStorageState(session.context, {
|
|
120
|
+
signal, indexedDB: true, maxBytes: limits.maxBytes, registerCleanup: cleanup => cleanups.push(cleanup),
|
|
121
|
+
})]);
|
|
122
|
+
const outcomes = await Promise.allSettled(cleanups.map(cleanup => Promise.resolve().then(cleanup)));
|
|
123
|
+
const failures = outcomes.filter((outcome) => outcome.status === 'rejected').map(outcome => outcome.reason);
|
|
124
|
+
if (result.status === 'rejected' || signal.aborted)
|
|
125
|
+
failures.unshift(result.status === 'rejected' ? result.reason : signal.reason);
|
|
126
|
+
if (failures.length === 1)
|
|
127
|
+
throw failures[0];
|
|
128
|
+
if (failures.length > 1)
|
|
129
|
+
throw new AggregateError(failures, 'Browser profile checkpoint and cleanup failed');
|
|
130
|
+
if (result.status !== 'fulfilled')
|
|
131
|
+
throw new Error('Browser profile checkpoint failed');
|
|
132
|
+
const pages = session.context.pages();
|
|
133
|
+
const contextOptions = { ...session.contextOptions };
|
|
134
|
+
delete contextOptions.storageState;
|
|
135
|
+
const runtime = session.context.browserProfile;
|
|
136
|
+
const runtimeState = await runtime?.capture(signal);
|
|
137
|
+
signal.throwIfAborted();
|
|
138
|
+
return encodeBrowserProfile({
|
|
139
|
+
state: result.value, contextOptions,
|
|
140
|
+
tabs: pages.map(page => page.url()), selected: Math.max(0, session.selectedPage ? pages.indexOf(session.selectedPage) : 0),
|
|
141
|
+
...(session.configuration === undefined ? {} : { configuration: session.configuration }),
|
|
142
|
+
...(session.expiresAt === undefined ? {} : { expiresAt: session.expiresAt }),
|
|
143
|
+
...(session.idleTimeoutMs === undefined ? {} : { idleTimeoutMs: session.idleTimeoutMs }),
|
|
144
|
+
...(runtimeState === undefined ? {} : { runtimeState }),
|
|
145
|
+
}, limits);
|
|
146
|
+
}
|
|
147
|
+
//# sourceMappingURL=profile.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"profile.js","sourceRoot":"","sources":["../../src/playwright/profile.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,46 @@
|
|
|
1
|
+
import { mkdtemp, open, rm } from "node:fs/promises";
|
|
2
|
+
/** Cloudflare's tracing client writes to its private /tmp filesystem. Read a
|
|
3
|
+
* bounded artifact only after the producer settles, and always retire its files. */
|
|
4
|
+
export const captureBrowserArtifact = async (produce, options) => {
|
|
5
|
+
const { signal, maxBytes, extension } = options;
|
|
6
|
+
signal.throwIfAborted();
|
|
7
|
+
if (!Number.isSafeInteger(maxBytes) ||
|
|
8
|
+
maxBytes < 1 ||
|
|
9
|
+
!extension ||
|
|
10
|
+
extension.length > 16 ||
|
|
11
|
+
[...extension].some((letter) => !"abcdefghijklmnopqrstuvwxyz0123456789".includes(letter)))
|
|
12
|
+
throw new Error("Invalid browser artifact options");
|
|
13
|
+
const directory = await mkdtemp("/tmp/poe-browser-artifact-");
|
|
14
|
+
try {
|
|
15
|
+
signal.throwIfAborted();
|
|
16
|
+
const path = `${directory}/artifact.${extension}`;
|
|
17
|
+
await produce(path);
|
|
18
|
+
signal.throwIfAborted();
|
|
19
|
+
const file = await open(path, "r");
|
|
20
|
+
try {
|
|
21
|
+
const stat = await file.stat();
|
|
22
|
+
if (!stat.isFile() || stat.size > maxBytes)
|
|
23
|
+
throw new Error("Browser artifact byte limit exceeded");
|
|
24
|
+
const bytes = new Uint8Array(stat.size + 1);
|
|
25
|
+
let offset = 0;
|
|
26
|
+
while (offset < bytes.byteLength) {
|
|
27
|
+
signal.throwIfAborted();
|
|
28
|
+
// biome-ignore lint/performance/noAwaitInLoops: Each short read advances the same file cursor and bounded destination.
|
|
29
|
+
const { bytesRead } = await file.read(bytes, offset, bytes.byteLength - offset, null);
|
|
30
|
+
if (!bytesRead)
|
|
31
|
+
break;
|
|
32
|
+
offset += bytesRead;
|
|
33
|
+
}
|
|
34
|
+
if (offset !== stat.size)
|
|
35
|
+
throw new Error("Browser artifact changed during capture");
|
|
36
|
+
signal.throwIfAborted();
|
|
37
|
+
return bytes.slice(0, offset);
|
|
38
|
+
}
|
|
39
|
+
finally {
|
|
40
|
+
await file.close();
|
|
41
|
+
}
|
|
42
|
+
}
|
|
43
|
+
finally {
|
|
44
|
+
await rm(directory, { recursive: true, force: true });
|
|
45
|
+
}
|
|
46
|
+
};
|
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
import type { PlaywrightCodeExecutor } from "../safe-bash/commands/playwright/index.js";
|
|
2
|
+
import type { acquireCloudflareBrowser } from "./shell-browser-resource.js";
|
|
3
|
+
export interface BrowserCodeRuntime {
|
|
4
|
+
ownerId: string;
|
|
5
|
+
loader?: WorkerLoader;
|
|
6
|
+
}
|
|
7
|
+
export declare function createBrowserCodeExecutor(resource: Awaited<ReturnType<typeof acquireCloudflareBrowser>>, runtime?: BrowserCodeRuntime): PlaywrightCodeExecutor;
|
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
import { createBrowserRunCode } from "./browser-run-code.js";
|
|
2
|
+
import { browserRunCodeGuestSource } from "./browser-run-code-guest.generated.js";
|
|
3
|
+
export function createBrowserCodeExecutor(resource, runtime) {
|
|
4
|
+
const execute = runtime?.loader
|
|
5
|
+
? createBrowserRunCode({
|
|
6
|
+
ownerId: runtime.ownerId,
|
|
7
|
+
loader: runtime.loader,
|
|
8
|
+
guestSource: browserRunCodeGuestSource,
|
|
9
|
+
browser: resource.browser,
|
|
10
|
+
connectSocket: resource.connectSocket,
|
|
11
|
+
retire: resource.release,
|
|
12
|
+
})
|
|
13
|
+
: undefined;
|
|
14
|
+
return async (input) => {
|
|
15
|
+
if (!execute)
|
|
16
|
+
throw new Error("Playwright run-code is unavailable: Worker Loader binding missing");
|
|
17
|
+
// The provider created this native Page; the portable adapter narrows its type.
|
|
18
|
+
return execute({ ...input, page: input.page });
|
|
19
|
+
};
|
|
20
|
+
}
|