effect-browser 0.2.0-beta.9 → 0.3.0-beta.6
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 +707 -1184
- package/dist/Browser-B5AV7zPS.mjs +437 -0
- package/dist/Browser-B5AV7zPS.mjs.map +1 -0
- package/dist/Browser.d.mts +115 -3
- package/dist/Browser.mjs +2 -22
- package/dist/BrowserError-DXXIA6Rk.d.mts +135 -0
- package/dist/BrowserError.d.mts +2 -0
- package/dist/BrowserError.mjs +202 -0
- package/dist/BrowserError.mjs.map +1 -0
- package/dist/BrowserEvent-DzdNdvoh.d.mts +277 -0
- package/dist/BrowserEvent.d.mts +2 -0
- package/dist/BrowserEvent.mjs +295 -0
- package/dist/BrowserEvent.mjs.map +1 -0
- package/dist/Cdp.d.mts +32 -0
- package/dist/Cdp.mjs +61 -0
- package/dist/Cdp.mjs.map +1 -0
- package/dist/Change-DNvztNLu.mjs +138 -0
- package/dist/Change-DNvztNLu.mjs.map +1 -0
- package/dist/Change-DVP2IJWm.d.mts +71 -0
- package/dist/Change.d.mts +2 -0
- package/dist/Change.mjs +2 -0
- package/dist/Chromium.d.mts +29 -81
- package/dist/Chromium.mjs +57 -392
- package/dist/Chromium.mjs.map +1 -1
- package/dist/Expect.d.mts +62 -0
- package/dist/Expect.mjs +114 -0
- package/dist/Expect.mjs.map +1 -0
- package/dist/Frame-BERmf_gM.d.mts +117 -0
- package/dist/Frame.d.mts +2 -0
- package/dist/Frame.mjs +123 -0
- package/dist/Frame.mjs.map +1 -0
- package/dist/Moment.d.mts +2 -0
- package/dist/Moment.mjs +288 -0
- package/dist/Moment.mjs.map +1 -0
- package/dist/Motion.d.mts +40 -0
- package/dist/Motion.mjs +122 -0
- package/dist/Motion.mjs.map +1 -0
- package/dist/Page-D4281dIi.mjs +618 -0
- package/dist/Page-D4281dIi.mjs.map +1 -0
- package/dist/Page-DYTdVhYa.d.mts +593 -0
- package/dist/Page.d.mts +2 -0
- package/dist/Page.mjs +2 -0
- package/dist/Plan-5MdsRzE5.mjs +314 -0
- package/dist/Plan-5MdsRzE5.mjs.map +1 -0
- package/dist/Plan-CNNOU1Tx.d.mts +112 -0
- package/dist/Plan.d.mts +2 -3
- package/dist/Plan.mjs +2 -2
- package/dist/Policy.d.mts +76 -0
- package/dist/Policy.mjs +237 -0
- package/dist/Policy.mjs.map +1 -0
- package/dist/Presentation.d.mts +48 -0
- package/dist/Presentation.mjs +117 -0
- package/dist/Presentation.mjs.map +1 -0
- package/dist/Snapshot-B34hZ4Jl.d.mts +68 -0
- package/dist/Snapshot.d.mts +2 -0
- package/dist/Snapshot.mjs +79 -0
- package/dist/Snapshot.mjs.map +1 -0
- package/dist/Stage.d.mts +54 -0
- package/dist/Stage.mjs +133 -0
- package/dist/Stage.mjs.map +1 -0
- package/dist/Supervisor-BtEG93gR.mjs +420 -0
- package/dist/Supervisor-BtEG93gR.mjs.map +1 -0
- package/dist/Supervisor-Im6-wbg5.d.mts +230 -0
- package/dist/Supervisor.d.mts +2 -0
- package/dist/Supervisor.mjs +2 -0
- package/dist/context-DAYjATgC.mjs +137 -0
- package/dist/context-DAYjATgC.mjs.map +1 -0
- package/dist/index.d.mts +17 -14
- package/dist/index.mjs +18 -13
- package/dist/match.inpage-xOe9LNO0.mjs +48 -0
- package/dist/match.inpage-xOe9LNO0.mjs.map +1 -0
- package/dist/page-BkRcLCWZ.mjs +5097 -0
- package/dist/page-BkRcLCWZ.mjs.map +1 -0
- package/dist/rolldown-runtime-D7D4PA-g.mjs +13 -0
- package/dist/url-CcL0K7S0.mjs +262 -0
- package/dist/url-CcL0K7S0.mjs.map +1 -0
- package/package.json +96 -61
- package/src/Browser.ts +625 -0
- package/src/BrowserError.ts +225 -0
- package/src/BrowserEvent.ts +294 -0
- package/src/Cdp.ts +101 -0
- package/src/Change.ts +88 -0
- package/src/Chromium.ts +102 -0
- package/src/Expect.ts +180 -0
- package/src/Frame.ts +130 -0
- package/src/Moment.ts +479 -0
- package/src/Motion.ts +166 -0
- package/src/Page.ts +520 -0
- package/src/Plan.ts +354 -0
- package/src/Policy.ts +325 -0
- package/src/Presentation.ts +195 -0
- package/src/Snapshot.ts +89 -0
- package/src/Stage.ts +223 -0
- package/src/Supervisor.ts +353 -0
- package/src/index.ts +20 -0
- package/src/internal/input/actions.ts +610 -0
- package/src/internal/input/dispatch.ts +161 -0
- package/src/internal/input/edit.inpage.ts +162 -0
- package/src/internal/input/evidence.inpage.ts +164 -0
- package/src/internal/input/guard.inpage.ts +605 -0
- package/src/internal/input/guard.ts +183 -0
- package/src/internal/input/keyboard.ts +112 -0
- package/src/internal/input/keys.ts +127 -0
- package/src/internal/input/perform.ts +322 -0
- package/src/internal/input/pointer.ts +153 -0
- package/src/internal/input/replies.ts +159 -0
- package/src/internal/input/settle.ts +50 -0
- package/src/internal/input/style.ts +186 -0
- package/src/internal/input/targets.inpage.ts +293 -0
- package/src/internal/input/targets.ts +148 -0
- package/src/internal/page/bridge.ts +386 -0
- package/src/internal/page/context.ts +302 -0
- package/src/internal/page/lane.ts +301 -0
- package/src/internal/page/navigation.ts +183 -0
- package/src/internal/page/openings.ts +87 -0
- package/src/internal/page/page.ts +137 -0
- package/src/internal/page/url.ts +100 -0
- package/src/internal/page/viewport.ts +43 -0
- package/src/internal/pictures/capture.ts +778 -0
- package/src/internal/pictures/clock.ts +141 -0
- package/src/internal/pictures/pictures.ts +520 -0
- package/src/internal/pictures/transport.ts +242 -0
- package/src/internal/reading/choose.ts +100 -0
- package/src/internal/reading/context.inpage.ts +201 -0
- package/src/internal/reading/controls.inpage.ts +158 -0
- package/src/internal/reading/expect.inpage.ts +70 -0
- package/src/internal/reading/match.inpage.ts +92 -0
- package/src/internal/reading/names.inpage.ts +306 -0
- package/src/internal/reading/outline.inpage.ts +260 -0
- package/src/internal/reading/reading.ts +223 -0
- package/src/internal/reading/ready.inpage.ts +154 -0
- package/src/internal/reading/ready.ts +105 -0
- package/src/internal/reading/subjects.inpage.ts +188 -0
- package/src/internal/reading/text.inpage.ts +135 -0
- package/src/internal/reading/walk.inpage.ts +220 -0
- package/src/internal/supervisor/lifecycle.ts +265 -0
- package/src/internal/timeline/changes.inpage.ts +216 -0
- package/src/internal/timeline/changes.ts +100 -0
- package/src/internal/timeline/events.ts +93 -0
- package/src/internal/timeline/fold.inpage.ts +123 -0
- package/src/internal/timeline/history.inpage.ts +229 -0
- package/src/internal/timeline/marks.inpage.ts +207 -0
- package/src/internal/timeline/record.inpage.ts +133 -0
- package/src/internal/timeline/sight.inpage.ts +122 -0
- package/src/internal/timeline/window.ts +96 -0
- package/src/internal/timeline/words.ts +65 -0
- package/dist/Bootstrap-B9UUXsvF.d.mts +0 -183
- package/dist/Bootstrap-CeQOWBy6.mjs +0 -189
- package/dist/Bootstrap-CeQOWBy6.mjs.map +0 -1
- package/dist/Bootstrap.d.mts +0 -3
- package/dist/Bootstrap.mjs +0 -2
- package/dist/Browser-BF9_sORP.d.mts +0 -388
- package/dist/Browser.mjs.map +0 -1
- package/dist/BrowserData-CPIIIHol.d.mts +0 -585
- package/dist/BrowserData.d.mts +0 -3
- package/dist/BrowserData.mjs +0 -695
- package/dist/BrowserData.mjs.map +0 -1
- package/dist/BrowserRuntime-B6nT1G4X.d.mts +0 -148
- package/dist/BrowserRuntime-C1r2aSRK.mjs +0 -6820
- package/dist/BrowserRuntime-C1r2aSRK.mjs.map +0 -1
- package/dist/BrowserRuntime.d.mts +0 -3
- package/dist/BrowserRuntime.mjs +0 -3
- package/dist/Capture.d.mts +0 -56
- package/dist/Capture.mjs +0 -678
- package/dist/Capture.mjs.map +0 -1
- package/dist/CaptureData-CYriZHX1.mjs +0 -201
- package/dist/CaptureData-CYriZHX1.mjs.map +0 -1
- package/dist/CaptureData.d.mts +0 -219
- package/dist/CaptureData.mjs +0 -2
- package/dist/Errors.d.mts +0 -158
- package/dist/Errors.mjs +0 -207
- package/dist/Errors.mjs.map +0 -1
- package/dist/Images-yCG9BmRU.mjs +0 -76
- package/dist/Images-yCG9BmRU.mjs.map +0 -1
- package/dist/OperationOptions-DAeRS6O9.mjs +0 -55
- package/dist/OperationOptions-DAeRS6O9.mjs.map +0 -1
- package/dist/PageControl.d.mts +0 -15
- package/dist/PageControl.mjs +0 -34
- package/dist/PageControl.mjs.map +0 -1
- package/dist/PageRegistry-B3q9DS3g.mjs +0 -164
- package/dist/PageRegistry-B3q9DS3g.mjs.map +0 -1
- package/dist/Plan-Dyxu2q8C.mjs +0 -543
- package/dist/Plan-Dyxu2q8C.mjs.map +0 -1
- package/dist/PlanData-B668RxbQ.d.mts +0 -4831
- package/dist/PlanData.d.mts +0 -3
- package/dist/PlanData.mjs +0 -268
- package/dist/PlanData.mjs.map +0 -1
- package/dist/PlanInput-BJcPPncs.mjs +0 -75
- package/dist/PlanInput-BJcPPncs.mjs.map +0 -1
- package/dist/PublicSession-DCSMMqOj.mjs +0 -5602
- package/dist/PublicSession-DCSMMqOj.mjs.map +0 -1
- package/dist/Testing.d.mts +0 -479
- package/dist/Testing.mjs +0 -2147
- package/dist/Testing.mjs.map +0 -1
- package/dist/Timeline-fV22Xk-S.d.mts +0 -29
- package/dist/Timeline.d.mts +0 -4
- package/dist/Timeline.mjs +0 -20
- package/dist/Timeline.mjs.map +0 -1
- package/dist/TimelineData-BsOn-YGZ.d.mts +0 -3818
- package/dist/TimelineData.d.mts +0 -3
- package/dist/TimelineData.mjs +0 -482
- package/dist/TimelineData.mjs.map +0 -1
|
@@ -0,0 +1,2 @@
|
|
|
1
|
+
import { C as TrackEvent, E as WheelScrolled, S as TextInserted, T as TrackPlanned, _ as PointerReleased, b as Subject, c as DisconnectCause, d as Navigated, f as PageClosed, g as PointerPressed, h as PageUntracked, i as BrowserEvent, l as Disconnected, m as PageOpened, n as ActionOptions, o as CursorChanged, p as PageLoaded, r as Box, s as DialogShown, t as Action, u as KeyChanged, v as RecordedEvent, w as TrackPerformed, x as SubjectContext, y as SessionEnding } from "./BrowserEvent-DzdNdvoh.mjs";
|
|
2
|
+
export { Action, ActionOptions, Box, BrowserEvent, CursorChanged, DialogShown, DisconnectCause, Disconnected, KeyChanged, Navigated, PageClosed, PageLoaded, PageOpened, PageUntracked, PointerPressed, PointerReleased, RecordedEvent, SessionEnding, Subject, SubjectContext, TextInserted, TrackEvent, TrackPerformed, TrackPlanned, WheelScrolled };
|
|
@@ -0,0 +1,295 @@
|
|
|
1
|
+
import { t as __exportAll } from "./rolldown-runtime-D7D4PA-g.mjs";
|
|
2
|
+
import { Plan, Point } from "./Motion.mjs";
|
|
3
|
+
import { Schema } from "effect";
|
|
4
|
+
//#region src/BrowserEvent.ts
|
|
5
|
+
/**
|
|
6
|
+
* What happened in a browser, in order: pages and their documents, actions, pointer motion, and
|
|
7
|
+
* the browser's own end.
|
|
8
|
+
*
|
|
9
|
+
* Every event carries `at`, host monotonic milliseconds from the owning browser’s Effect `Clock`.
|
|
10
|
+
* This clock also stamps screencast frames’ `receivedAt` and moments, so wall-clock corrections
|
|
11
|
+
* cannot disturb their order. Compare stamps only within the same browser clock, not across hosts.
|
|
12
|
+
* A page is named by its CDP target id, which stays the same across reconnects, and every URL is
|
|
13
|
+
* reported without its userinfo or known secret parameters.
|
|
14
|
+
*
|
|
15
|
+
* @since 0.3.0
|
|
16
|
+
*/
|
|
17
|
+
var BrowserEvent_exports = /* @__PURE__ */ __exportAll({
|
|
18
|
+
Action: () => Action,
|
|
19
|
+
ActionOptions: () => ActionOptions,
|
|
20
|
+
Box: () => Box,
|
|
21
|
+
BrowserEvent: () => BrowserEvent,
|
|
22
|
+
CursorChanged: () => CursorChanged,
|
|
23
|
+
DialogShown: () => DialogShown,
|
|
24
|
+
DisconnectCause: () => DisconnectCause,
|
|
25
|
+
Disconnected: () => Disconnected,
|
|
26
|
+
KeyChanged: () => KeyChanged,
|
|
27
|
+
Navigated: () => Navigated,
|
|
28
|
+
PageClosed: () => PageClosed,
|
|
29
|
+
PageLoaded: () => PageLoaded,
|
|
30
|
+
PageOpened: () => PageOpened,
|
|
31
|
+
PageUntracked: () => PageUntracked,
|
|
32
|
+
PointerPressed: () => PointerPressed,
|
|
33
|
+
PointerReleased: () => PointerReleased,
|
|
34
|
+
RecordedEvent: () => RecordedEvent,
|
|
35
|
+
SessionEnding: () => SessionEnding,
|
|
36
|
+
Subject: () => Subject,
|
|
37
|
+
SubjectContext: () => SubjectContext,
|
|
38
|
+
TextInserted: () => TextInserted,
|
|
39
|
+
TrackEvent: () => TrackEvent,
|
|
40
|
+
TrackPerformed: () => TrackPerformed,
|
|
41
|
+
TrackPlanned: () => TrackPlanned,
|
|
42
|
+
WheelScrolled: () => WheelScrolled
|
|
43
|
+
});
|
|
44
|
+
/** A page opened, and the page that opened it, as a link or `window.open` does, if one did. */
|
|
45
|
+
var PageOpened = class extends Schema.TaggedClass()("PageOpened", {
|
|
46
|
+
at: Schema.Finite,
|
|
47
|
+
page: Schema.String,
|
|
48
|
+
url: Schema.String,
|
|
49
|
+
opener: Schema.optional(Schema.String)
|
|
50
|
+
}) {};
|
|
51
|
+
/**
|
|
52
|
+
* The page closed (`page`), or crashed and was closed (`crashed`). A page lost with its browser
|
|
53
|
+
* has no event of its own: `Disconnected` stands for all of them.
|
|
54
|
+
*/
|
|
55
|
+
var PageClosed = class extends Schema.TaggedClass()("PageClosed", {
|
|
56
|
+
at: Schema.Finite,
|
|
57
|
+
page: Schema.String,
|
|
58
|
+
cause: Schema.Literals(["page", "crashed"])
|
|
59
|
+
}) {};
|
|
60
|
+
/**
|
|
61
|
+
* A tab the site opened that the library could not track, as its registration failed with
|
|
62
|
+
* `detail`. A tab that closed as it opened has no event.
|
|
63
|
+
*/
|
|
64
|
+
var PageUntracked = class extends Schema.TaggedClass()("PageUntracked", {
|
|
65
|
+
at: Schema.Finite,
|
|
66
|
+
url: Schema.String,
|
|
67
|
+
detail: Schema.String
|
|
68
|
+
}) {};
|
|
69
|
+
/**
|
|
70
|
+
* The page's main frame moved to `url`: into a new document, or within the current one
|
|
71
|
+
* (`sameDocument`), as `pushState` and fragment links do. Frames carry the document they followed.
|
|
72
|
+
*/
|
|
73
|
+
var Navigated = class extends Schema.TaggedClass()("Navigated", {
|
|
74
|
+
at: Schema.Finite,
|
|
75
|
+
page: Schema.String,
|
|
76
|
+
url: Schema.String,
|
|
77
|
+
/**
|
|
78
|
+
* The page's documents counted from 0, the one it had when this browser began tracking it, one
|
|
79
|
+
* more for each new document. The count belongs to the page within one `Browser` and starts at
|
|
80
|
+
* 0 again on a new connection, so compare it only with the same page's in the same browser.
|
|
81
|
+
*/
|
|
82
|
+
document: Schema.Int.check(Schema.isGreaterThanOrEqualTo(0)),
|
|
83
|
+
sameDocument: Schema.Boolean
|
|
84
|
+
}) {};
|
|
85
|
+
/** The page's document finished parsing (`domcontentloaded`) or loading (`load`). */
|
|
86
|
+
var PageLoaded = class extends Schema.TaggedClass()("PageLoaded", {
|
|
87
|
+
at: Schema.Finite,
|
|
88
|
+
page: Schema.String,
|
|
89
|
+
state: Schema.Literals(["domcontentloaded", "load"])
|
|
90
|
+
}) {};
|
|
91
|
+
/**
|
|
92
|
+
* Why a browser was lost to its owner: its connection dropped (`connection`), its provider ended
|
|
93
|
+
* its session, at or after the session's `expiresAt` (`session`), or its owner released it.
|
|
94
|
+
*/
|
|
95
|
+
const DisconnectCause = Schema.Literals([
|
|
96
|
+
"connection",
|
|
97
|
+
"session",
|
|
98
|
+
"released"
|
|
99
|
+
]);
|
|
100
|
+
/** The browser was lost to its owner, with every page in it. It happens once. */
|
|
101
|
+
var Disconnected = class extends Schema.TaggedClass()("Disconnected", {
|
|
102
|
+
at: Schema.Finite,
|
|
103
|
+
cause: DisconnectCause
|
|
104
|
+
}) {};
|
|
105
|
+
/** The provider ends this browser's session at `expiresAt`, a wall-clock instant. */
|
|
106
|
+
var SessionEnding = class extends Schema.TaggedClass()("SessionEnding", {
|
|
107
|
+
at: Schema.Finite,
|
|
108
|
+
expiresAt: Schema.DateTimeUtc
|
|
109
|
+
}) {};
|
|
110
|
+
/**
|
|
111
|
+
* The words around a subject that say which one it is, each bound to it in the page rather than
|
|
112
|
+
* read off nearby text later. In a table, `row` is the row's header or first cell with text and
|
|
113
|
+
* `column` the header over it; elsewhere, `label` is the words just before it in its row, item,
|
|
114
|
+
* group or block, at most 40 characters. `heading` is the nearest heading above it, left out for
|
|
115
|
+
* what is pinned to the viewport. Row, column and heading are at most 60 characters.
|
|
116
|
+
*/
|
|
117
|
+
const SubjectContext = Schema.Struct({
|
|
118
|
+
row: Schema.optional(Schema.String),
|
|
119
|
+
column: Schema.optional(Schema.String),
|
|
120
|
+
label: Schema.optional(Schema.String),
|
|
121
|
+
heading: Schema.optional(Schema.String)
|
|
122
|
+
});
|
|
123
|
+
/**
|
|
124
|
+
* What an input acted on, or what `Page.find` found, as the page named it then: its role (null
|
|
125
|
+
* when it has none), its accessible name (empty when it has none), its lowercase tag and its
|
|
126
|
+
* context. For a point, it is the control under the point, or else the element painted there.
|
|
127
|
+
* Unlike a ref, it keeps its meaning after the page changes.
|
|
128
|
+
*/
|
|
129
|
+
var Subject = class extends Schema.Class("effect-browser/Subject")({
|
|
130
|
+
role: Schema.NullOr(Schema.String),
|
|
131
|
+
name: Schema.String,
|
|
132
|
+
tag: Schema.String,
|
|
133
|
+
context: SubjectContext
|
|
134
|
+
}) {};
|
|
135
|
+
const Button = Schema.Literals([
|
|
136
|
+
"left",
|
|
137
|
+
"right",
|
|
138
|
+
"middle"
|
|
139
|
+
]);
|
|
140
|
+
/** An element's box in viewport CSS pixels; it may lie partly or wholly outside the viewport. */
|
|
141
|
+
const Box = Schema.Struct({
|
|
142
|
+
x: Schema.Finite,
|
|
143
|
+
y: Schema.Finite,
|
|
144
|
+
width: Schema.Finite,
|
|
145
|
+
height: Schema.Finite
|
|
146
|
+
});
|
|
147
|
+
/**
|
|
148
|
+
* What else an action was asked, where it changes what the action does: a click's button, count
|
|
149
|
+
* and hold, how `type` enters its text, how often and how long `press` holds its keys, how far
|
|
150
|
+
* `scroll` moves, and the options `select` chose. Only a completed action records them.
|
|
151
|
+
*/
|
|
152
|
+
const ActionOptions = Schema.Struct({
|
|
153
|
+
button: Schema.optional(Button),
|
|
154
|
+
clickCount: Schema.optional(Schema.Finite),
|
|
155
|
+
holdMillis: Schema.optional(Schema.Finite),
|
|
156
|
+
replace: Schema.optional(Schema.Boolean),
|
|
157
|
+
submit: Schema.optional(Schema.Boolean),
|
|
158
|
+
times: Schema.optional(Schema.Finite),
|
|
159
|
+
dx: Schema.optional(Schema.Finite),
|
|
160
|
+
dy: Schema.optional(Schema.Finite),
|
|
161
|
+
values: Schema.optional(Schema.Array(Schema.String))
|
|
162
|
+
});
|
|
163
|
+
/**
|
|
164
|
+
* One page operation ended, including one its caller interrupted (`error: "interrupted"`).
|
|
165
|
+
* `target` is what the caller asked for: a ref, a point, a URL or keys, and `options` the rest.
|
|
166
|
+
* `subject` is what an element or point action found there, and `to` where a drag ended; an
|
|
167
|
+
* action that failed before finding its target has neither. Point actions carry the viewport
|
|
168
|
+
* point they used. `correlation` is the id its caller gave it with `Page.correlate`, such as a
|
|
169
|
+
* model's tool call id.
|
|
170
|
+
*/
|
|
171
|
+
var Action = class extends Schema.TaggedClass()("Action", {
|
|
172
|
+
at: Schema.Finite,
|
|
173
|
+
startedAt: Schema.Finite,
|
|
174
|
+
page: Schema.String,
|
|
175
|
+
name: Schema.String,
|
|
176
|
+
correlation: Schema.optional(Schema.String),
|
|
177
|
+
target: Schema.optional(Schema.String),
|
|
178
|
+
options: Schema.optional(ActionOptions),
|
|
179
|
+
subject: Schema.optional(Subject),
|
|
180
|
+
to: Schema.optional(Subject),
|
|
181
|
+
/** For an action at a point, the box of what it found there. */
|
|
182
|
+
box: Schema.optional(Box),
|
|
183
|
+
text: Schema.optional(Schema.String),
|
|
184
|
+
x: Schema.optional(Schema.Finite),
|
|
185
|
+
y: Schema.optional(Schema.Finite),
|
|
186
|
+
ok: Schema.Boolean,
|
|
187
|
+
dispatched: Schema.Boolean,
|
|
188
|
+
error: Schema.optional(Schema.String)
|
|
189
|
+
}) {};
|
|
190
|
+
const Sequence = Schema.Int.check(Schema.isGreaterThan(0));
|
|
191
|
+
/** One whole glide, published before its first input. Offsets use the host monotonic clock. */
|
|
192
|
+
var TrackPlanned = class extends Schema.TaggedClass()("TrackPlanned", {
|
|
193
|
+
at: Schema.Finite,
|
|
194
|
+
page: Schema.String,
|
|
195
|
+
from: Point,
|
|
196
|
+
samples: Plan
|
|
197
|
+
}) {};
|
|
198
|
+
/**
|
|
199
|
+
* The submitted prefix of a glide. `plan` is its TrackPlanned envelope sequence; `dispatched`
|
|
200
|
+
* counts samples. `complete` means every sample was submitted, not acknowledged by the browser.
|
|
201
|
+
* The terminal point clips a canceled plan so a compositor never draws its unrealized future.
|
|
202
|
+
*/
|
|
203
|
+
var TrackPerformed = class extends Schema.TaggedClass()("TrackPerformed", {
|
|
204
|
+
at: Schema.Finite,
|
|
205
|
+
page: Schema.String,
|
|
206
|
+
plan: Sequence,
|
|
207
|
+
dispatched: Schema.Int.check(Schema.isGreaterThanOrEqualTo(0)),
|
|
208
|
+
x: Schema.Finite,
|
|
209
|
+
y: Schema.Finite,
|
|
210
|
+
complete: Schema.Boolean
|
|
211
|
+
}) {};
|
|
212
|
+
var PointerPressed = class extends Schema.TaggedClass()("PointerPressed", {
|
|
213
|
+
at: Schema.Finite,
|
|
214
|
+
page: Schema.String,
|
|
215
|
+
x: Schema.Finite,
|
|
216
|
+
y: Schema.Finite,
|
|
217
|
+
button: Button,
|
|
218
|
+
clickCount: Schema.Int.check(Schema.isGreaterThan(0))
|
|
219
|
+
}) {};
|
|
220
|
+
var PointerReleased = class extends Schema.TaggedClass()("PointerReleased", {
|
|
221
|
+
at: Schema.Finite,
|
|
222
|
+
page: Schema.String,
|
|
223
|
+
x: Schema.Finite,
|
|
224
|
+
y: Schema.Finite,
|
|
225
|
+
button: Button,
|
|
226
|
+
clickCount: Schema.Int.check(Schema.isGreaterThan(0))
|
|
227
|
+
}) {};
|
|
228
|
+
var WheelScrolled = class extends Schema.TaggedClass()("WheelScrolled", {
|
|
229
|
+
at: Schema.Finite,
|
|
230
|
+
page: Schema.String,
|
|
231
|
+
x: Schema.Finite,
|
|
232
|
+
y: Schema.Finite,
|
|
233
|
+
dx: Schema.Finite,
|
|
234
|
+
dy: Schema.Finite
|
|
235
|
+
}) {};
|
|
236
|
+
var KeyChanged = class extends Schema.TaggedClass()("KeyChanged", {
|
|
237
|
+
at: Schema.Finite,
|
|
238
|
+
page: Schema.String,
|
|
239
|
+
key: Schema.String,
|
|
240
|
+
phase: Schema.Literals(["down", "up"])
|
|
241
|
+
}) {};
|
|
242
|
+
/** Literal text insertion has no corresponding key events, including Unicode and newlines. */
|
|
243
|
+
var TextInserted = class extends Schema.TaggedClass()("TextInserted", {
|
|
244
|
+
at: Schema.Finite,
|
|
245
|
+
page: Schema.String,
|
|
246
|
+
text: Schema.String
|
|
247
|
+
}) {};
|
|
248
|
+
/** The target's CSS cursor, obtained during target resolution without another browser call. */
|
|
249
|
+
var CursorChanged = class extends Schema.TaggedClass()("CursorChanged", {
|
|
250
|
+
at: Schema.Finite,
|
|
251
|
+
page: Schema.String,
|
|
252
|
+
cursor: Schema.String
|
|
253
|
+
}) {};
|
|
254
|
+
const TrackEvent = Schema.Union([
|
|
255
|
+
TrackPlanned,
|
|
256
|
+
TrackPerformed,
|
|
257
|
+
PointerPressed,
|
|
258
|
+
PointerReleased,
|
|
259
|
+
WheelScrolled,
|
|
260
|
+
KeyChanged,
|
|
261
|
+
TextInserted,
|
|
262
|
+
CursorChanged
|
|
263
|
+
]);
|
|
264
|
+
/**
|
|
265
|
+
* A JavaScript dialog appeared and was answered: an alert or a leave-page prompt accepted, a
|
|
266
|
+
* confirm or a prompt dismissed, as if its Cancel were pressed.
|
|
267
|
+
*/
|
|
268
|
+
var DialogShown = class extends Schema.TaggedClass()("DialogShown", {
|
|
269
|
+
at: Schema.Finite,
|
|
270
|
+
page: Schema.String,
|
|
271
|
+
kind: Schema.String,
|
|
272
|
+
message: Schema.String,
|
|
273
|
+
answer: Schema.Literals(["accepted", "dismissed"])
|
|
274
|
+
}) {};
|
|
275
|
+
const BrowserEvent = Schema.Union([
|
|
276
|
+
PageOpened,
|
|
277
|
+
PageClosed,
|
|
278
|
+
PageUntracked,
|
|
279
|
+
Navigated,
|
|
280
|
+
PageLoaded,
|
|
281
|
+
Action,
|
|
282
|
+
...TrackEvent.members,
|
|
283
|
+
DialogShown,
|
|
284
|
+
Disconnected,
|
|
285
|
+
SessionEnding
|
|
286
|
+
]);
|
|
287
|
+
/** A position in the browser's one replayable event history. Sequences begin at one. */
|
|
288
|
+
var RecordedEvent = class extends Schema.Class("effect-browser/RecordedEvent")({
|
|
289
|
+
sequence: Sequence,
|
|
290
|
+
event: BrowserEvent
|
|
291
|
+
}) {};
|
|
292
|
+
//#endregion
|
|
293
|
+
export { Action, ActionOptions, Box, BrowserEvent, CursorChanged, DialogShown, DisconnectCause, Disconnected, KeyChanged, Navigated, PageClosed, PageLoaded, PageOpened, PageUntracked, PointerPressed, PointerReleased, RecordedEvent, SessionEnding, Subject, SubjectContext, TextInserted, TrackEvent, TrackPerformed, TrackPlanned, WheelScrolled, BrowserEvent_exports as t };
|
|
294
|
+
|
|
295
|
+
//# sourceMappingURL=BrowserEvent.mjs.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"BrowserEvent.mjs","names":["Motion.Point","Motion.Plan"],"sources":["../src/BrowserEvent.ts"],"sourcesContent":["/**\n * What happened in a browser, in order: pages and their documents, actions, pointer motion, and\n * the browser's own end.\n *\n * Every event carries `at`, host monotonic milliseconds from the owning browser’s Effect `Clock`.\n * This clock also stamps screencast frames’ `receivedAt` and moments, so wall-clock corrections\n * cannot disturb their order. Compare stamps only within the same browser clock, not across hosts.\n * A page is named by its CDP target id, which stays the same across reconnects, and every URL is\n * reported without its userinfo or known secret parameters.\n *\n * @since 0.3.0\n */\nimport { Schema } from \"effect\";\n\nimport * as Motion from \"./Motion.ts\";\n\n/** A page opened, and the page that opened it, as a link or `window.open` does, if one did. */\nexport class PageOpened extends Schema.TaggedClass<PageOpened>()(\"PageOpened\", {\n at: Schema.Finite,\n page: Schema.String,\n url: Schema.String,\n opener: Schema.optional(Schema.String),\n}) {}\n\n/**\n * The page closed (`page`), or crashed and was closed (`crashed`). A page lost with its browser\n * has no event of its own: `Disconnected` stands for all of them.\n */\nexport class PageClosed extends Schema.TaggedClass<PageClosed>()(\"PageClosed\", {\n at: Schema.Finite,\n page: Schema.String,\n cause: Schema.Literals([\"page\", \"crashed\"]),\n}) {}\n\n/**\n * A tab the site opened that the library could not track, as its registration failed with\n * `detail`. A tab that closed as it opened has no event.\n */\nexport class PageUntracked extends Schema.TaggedClass<PageUntracked>()(\"PageUntracked\", {\n at: Schema.Finite,\n url: Schema.String,\n detail: Schema.String,\n}) {}\n\n/**\n * The page's main frame moved to `url`: into a new document, or within the current one\n * (`sameDocument`), as `pushState` and fragment links do. Frames carry the document they followed.\n */\nexport class Navigated extends Schema.TaggedClass<Navigated>()(\"Navigated\", {\n at: Schema.Finite,\n page: Schema.String,\n url: Schema.String,\n /**\n * The page's documents counted from 0, the one it had when this browser began tracking it, one\n * more for each new document. The count belongs to the page within one `Browser` and starts at\n * 0 again on a new connection, so compare it only with the same page's in the same browser.\n */\n document: Schema.Int.check(Schema.isGreaterThanOrEqualTo(0)),\n sameDocument: Schema.Boolean,\n}) {}\n\n/** The page's document finished parsing (`domcontentloaded`) or loading (`load`). */\nexport class PageLoaded extends Schema.TaggedClass<PageLoaded>()(\"PageLoaded\", {\n at: Schema.Finite,\n page: Schema.String,\n state: Schema.Literals([\"domcontentloaded\", \"load\"]),\n}) {}\n\n/**\n * Why a browser was lost to its owner: its connection dropped (`connection`), its provider ended\n * its session, at or after the session's `expiresAt` (`session`), or its owner released it.\n */\nexport const DisconnectCause = Schema.Literals([\"connection\", \"session\", \"released\"]);\n\nexport type DisconnectCause = typeof DisconnectCause.Type;\n\n/** The browser was lost to its owner, with every page in it. It happens once. */\nexport class Disconnected extends Schema.TaggedClass<Disconnected>()(\"Disconnected\", {\n at: Schema.Finite,\n cause: DisconnectCause,\n}) {}\n\n/** The provider ends this browser's session at `expiresAt`, a wall-clock instant. */\nexport class SessionEnding extends Schema.TaggedClass<SessionEnding>()(\"SessionEnding\", {\n at: Schema.Finite,\n expiresAt: Schema.DateTimeUtc,\n}) {}\n\n/**\n * The words around a subject that say which one it is, each bound to it in the page rather than\n * read off nearby text later. In a table, `row` is the row's header or first cell with text and\n * `column` the header over it; elsewhere, `label` is the words just before it in its row, item,\n * group or block, at most 40 characters. `heading` is the nearest heading above it, left out for\n * what is pinned to the viewport. Row, column and heading are at most 60 characters.\n */\nexport const SubjectContext = Schema.Struct({\n row: Schema.optional(Schema.String),\n column: Schema.optional(Schema.String),\n label: Schema.optional(Schema.String),\n heading: Schema.optional(Schema.String),\n});\n\nexport type SubjectContext = typeof SubjectContext.Type;\n\n/**\n * What an input acted on, or what `Page.find` found, as the page named it then: its role (null\n * when it has none), its accessible name (empty when it has none), its lowercase tag and its\n * context. For a point, it is the control under the point, or else the element painted there.\n * Unlike a ref, it keeps its meaning after the page changes.\n */\nexport class Subject extends Schema.Class<Subject>(\"effect-browser/Subject\")({\n role: Schema.NullOr(Schema.String),\n name: Schema.String,\n tag: Schema.String,\n context: SubjectContext,\n}) {}\n\nconst Button = Schema.Literals([\"left\", \"right\", \"middle\"]);\n\n/** An element's box in viewport CSS pixels; it may lie partly or wholly outside the viewport. */\nexport const Box = Schema.Struct({\n x: Schema.Finite,\n y: Schema.Finite,\n width: Schema.Finite,\n height: Schema.Finite,\n});\n\nexport type Box = typeof Box.Type;\n\n/**\n * What else an action was asked, where it changes what the action does: a click's button, count\n * and hold, how `type` enters its text, how often and how long `press` holds its keys, how far\n * `scroll` moves, and the options `select` chose. Only a completed action records them.\n */\nexport const ActionOptions = Schema.Struct({\n button: Schema.optional(Button),\n clickCount: Schema.optional(Schema.Finite),\n holdMillis: Schema.optional(Schema.Finite),\n replace: Schema.optional(Schema.Boolean),\n submit: Schema.optional(Schema.Boolean),\n times: Schema.optional(Schema.Finite),\n dx: Schema.optional(Schema.Finite),\n dy: Schema.optional(Schema.Finite),\n values: Schema.optional(Schema.Array(Schema.String)),\n});\n\nexport type ActionOptions = typeof ActionOptions.Type;\n\n/**\n * One page operation ended, including one its caller interrupted (`error: \"interrupted\"`).\n * `target` is what the caller asked for: a ref, a point, a URL or keys, and `options` the rest.\n * `subject` is what an element or point action found there, and `to` where a drag ended; an\n * action that failed before finding its target has neither. Point actions carry the viewport\n * point they used. `correlation` is the id its caller gave it with `Page.correlate`, such as a\n * model's tool call id.\n */\nexport class Action extends Schema.TaggedClass<Action>()(\"Action\", {\n at: Schema.Finite,\n startedAt: Schema.Finite,\n page: Schema.String,\n name: Schema.String,\n correlation: Schema.optional(Schema.String),\n target: Schema.optional(Schema.String),\n options: Schema.optional(ActionOptions),\n subject: Schema.optional(Subject),\n to: Schema.optional(Subject),\n /** For an action at a point, the box of what it found there. */\n box: Schema.optional(Box),\n text: Schema.optional(Schema.String),\n x: Schema.optional(Schema.Finite),\n y: Schema.optional(Schema.Finite),\n ok: Schema.Boolean,\n dispatched: Schema.Boolean,\n error: Schema.optional(Schema.String),\n}) {}\n\nconst Sequence = Schema.Int.check(Schema.isGreaterThan(0));\n\n/** One whole glide, published before its first input. Offsets use the host monotonic clock. */\nexport class TrackPlanned extends Schema.TaggedClass<TrackPlanned>()(\"TrackPlanned\", {\n at: Schema.Finite,\n page: Schema.String,\n from: Motion.Point,\n samples: Motion.Plan,\n}) {}\n\n/**\n * The submitted prefix of a glide. `plan` is its TrackPlanned envelope sequence; `dispatched`\n * counts samples. `complete` means every sample was submitted, not acknowledged by the browser.\n * The terminal point clips a canceled plan so a compositor never draws its unrealized future.\n */\nexport class TrackPerformed extends Schema.TaggedClass<TrackPerformed>()(\"TrackPerformed\", {\n at: Schema.Finite,\n page: Schema.String,\n plan: Sequence,\n dispatched: Schema.Int.check(Schema.isGreaterThanOrEqualTo(0)),\n x: Schema.Finite,\n y: Schema.Finite,\n complete: Schema.Boolean,\n}) {}\n\nexport class PointerPressed extends Schema.TaggedClass<PointerPressed>()(\"PointerPressed\", {\n at: Schema.Finite,\n page: Schema.String,\n x: Schema.Finite,\n y: Schema.Finite,\n button: Button,\n clickCount: Schema.Int.check(Schema.isGreaterThan(0)),\n}) {}\n\nexport class PointerReleased extends Schema.TaggedClass<PointerReleased>()(\"PointerReleased\", {\n at: Schema.Finite,\n page: Schema.String,\n x: Schema.Finite,\n y: Schema.Finite,\n button: Button,\n clickCount: Schema.Int.check(Schema.isGreaterThan(0)),\n}) {}\n\nexport class WheelScrolled extends Schema.TaggedClass<WheelScrolled>()(\"WheelScrolled\", {\n at: Schema.Finite,\n page: Schema.String,\n x: Schema.Finite,\n y: Schema.Finite,\n dx: Schema.Finite,\n dy: Schema.Finite,\n}) {}\n\nexport class KeyChanged extends Schema.TaggedClass<KeyChanged>()(\"KeyChanged\", {\n at: Schema.Finite,\n page: Schema.String,\n key: Schema.String,\n phase: Schema.Literals([\"down\", \"up\"]),\n}) {}\n\n/** Literal text insertion has no corresponding key events, including Unicode and newlines. */\nexport class TextInserted extends Schema.TaggedClass<TextInserted>()(\"TextInserted\", {\n at: Schema.Finite,\n page: Schema.String,\n text: Schema.String,\n}) {}\n\n/** The target's CSS cursor, obtained during target resolution without another browser call. */\nexport class CursorChanged extends Schema.TaggedClass<CursorChanged>()(\"CursorChanged\", {\n at: Schema.Finite,\n page: Schema.String,\n cursor: Schema.String,\n}) {}\n\nexport const TrackEvent = Schema.Union([\n TrackPlanned,\n TrackPerformed,\n PointerPressed,\n PointerReleased,\n WheelScrolled,\n KeyChanged,\n TextInserted,\n CursorChanged,\n]);\n\nexport type TrackEvent = typeof TrackEvent.Type;\n\n/**\n * A JavaScript dialog appeared and was answered: an alert or a leave-page prompt accepted, a\n * confirm or a prompt dismissed, as if its Cancel were pressed.\n */\nexport class DialogShown extends Schema.TaggedClass<DialogShown>()(\"DialogShown\", {\n at: Schema.Finite,\n page: Schema.String,\n kind: Schema.String,\n message: Schema.String,\n answer: Schema.Literals([\"accepted\", \"dismissed\"]),\n}) {}\n\nexport const BrowserEvent = Schema.Union([\n PageOpened,\n PageClosed,\n PageUntracked,\n Navigated,\n PageLoaded,\n Action,\n ...TrackEvent.members,\n DialogShown,\n Disconnected,\n SessionEnding,\n]);\n\nexport type BrowserEvent = typeof BrowserEvent.Type;\n\n/** A position in the browser's one replayable event history. Sequences begin at one. */\nexport class RecordedEvent extends Schema.Class<RecordedEvent>(\"effect-browser/RecordedEvent\")({\n sequence: Sequence,\n event: BrowserEvent,\n}) {}\n"],"mappings":"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"}
|
package/dist/Cdp.d.mts
ADDED
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
import { t as BrowserError } from "./BrowserError-DXXIA6Rk.mjs";
|
|
2
|
+
import { Browser, CaptureSource, Options as Options$1, Service, t as Browser_d_exports } from "./Browser.mjs";
|
|
3
|
+
import { DateTime, Effect, Layer, Redacted } from "effect";
|
|
4
|
+
declare namespace Cdp_d_exports {
|
|
5
|
+
export { Options, layer, open };
|
|
6
|
+
}
|
|
7
|
+
export interface Options extends Options$1 {
|
|
8
|
+
/**
|
|
9
|
+
* `ws://`, `wss://` or `http://` DevTools endpoint. Often a credential, so it may be redacted;
|
|
10
|
+
* connect failures never include its userinfo, path or query.
|
|
11
|
+
*/
|
|
12
|
+
readonly endpoint: string | Redacted.Redacted<string>;
|
|
13
|
+
readonly headers?: Readonly<Record<string, string>> | undefined;
|
|
14
|
+
/** Identifies the session in `Browser.id`. Defaults to `"cdp"`. */
|
|
15
|
+
readonly id?: string | undefined;
|
|
16
|
+
readonly provider?: string | undefined;
|
|
17
|
+
/** Bound on connecting. Defaults to 30 seconds. */
|
|
18
|
+
readonly connectTimeoutMillis?: number | undefined;
|
|
19
|
+
/** When the provider ends the session on its own, as a hosted session's timeout does. */
|
|
20
|
+
readonly expiresAt?: DateTime.Utc | undefined;
|
|
21
|
+
/**
|
|
22
|
+
* A connection apart from this one for the pages' screencasts, as a hosted provider supplies.
|
|
23
|
+
* Without one, each page's capture runs on its own session.
|
|
24
|
+
*/
|
|
25
|
+
readonly capture?: CaptureSource | undefined;
|
|
26
|
+
}
|
|
27
|
+
/** Connect and open a `Browser` over the endpoint's first context. */
|
|
28
|
+
export declare const open: (options: Options) => Effect.Effect<Service, BrowserError, import("effect/Scope").Scope>;
|
|
29
|
+
export declare const layer: (options: Options) => Layer.Layer<Browser, BrowserError>;
|
|
30
|
+
//#endregion
|
|
31
|
+
export { Cdp_d_exports as t };
|
|
32
|
+
//# sourceMappingURL=Cdp.d.mts.map
|
package/dist/Cdp.mjs
ADDED
|
@@ -0,0 +1,61 @@
|
|
|
1
|
+
import { t as __exportAll } from "./rolldown-runtime-D7D4PA-g.mjs";
|
|
2
|
+
import { Failed } from "./BrowserError.mjs";
|
|
3
|
+
import { r as quoted } from "./url-CcL0K7S0.mjs";
|
|
4
|
+
import { o as reasonOf, s as undispatched } from "./context-DAYjATgC.mjs";
|
|
5
|
+
import { r as make, t as Browser } from "./Browser-B5AV7zPS.mjs";
|
|
6
|
+
import { Effect, Layer, Redacted } from "effect";
|
|
7
|
+
import { chromium } from "playwright-core";
|
|
8
|
+
//#region src/Cdp.ts
|
|
9
|
+
/**
|
|
10
|
+
* A browser reached over the Chrome DevTools Protocol: a Chrome started with
|
|
11
|
+
* `--remote-debugging-port`, or any provider that hands out a CDP WebSocket URL.
|
|
12
|
+
*
|
|
13
|
+
* Closing the scope disconnects. It does not close the remote browser; its owner does that.
|
|
14
|
+
*
|
|
15
|
+
* @since 0.3.0
|
|
16
|
+
*/
|
|
17
|
+
var Cdp_exports = /* @__PURE__ */ __exportAll({
|
|
18
|
+
layer: () => layer,
|
|
19
|
+
open: () => open
|
|
20
|
+
});
|
|
21
|
+
/**
|
|
22
|
+
* Playwright can echo the endpoint, or a URL derived from it with its query, userinfo or path, in
|
|
23
|
+
* a connect failure. Those parts are often the credential, so a URL keeps its scheme, host and
|
|
24
|
+
* port, and any other echo of the endpoint is replaced.
|
|
25
|
+
*/
|
|
26
|
+
const withoutEndpoint = (endpoint, reason) => {
|
|
27
|
+
if (reason._tag !== "Failed") return reason;
|
|
28
|
+
const origins = reason.detail.replace(quoted, (url) => {
|
|
29
|
+
const parsed = URL.parse(url);
|
|
30
|
+
return parsed === null || parsed.host === "" ? "<url>" : `${parsed.protocol}//${parsed.host}`;
|
|
31
|
+
});
|
|
32
|
+
return new Failed({ detail: endpoint === "" ? origins : origins.replaceAll(endpoint, "<endpoint>") });
|
|
33
|
+
};
|
|
34
|
+
/** Connect and open a `Browser` over the endpoint's first context. */
|
|
35
|
+
const open = Effect.fn("Cdp.open")(function* (options) {
|
|
36
|
+
const endpoint = Redacted.isRedacted(options.endpoint) ? Redacted.value(options.endpoint) : options.endpoint;
|
|
37
|
+
const timeout = options.connectTimeoutMillis ?? 3e4;
|
|
38
|
+
const failed = (cause, timeoutMillis) => undispatched("connect", withoutEndpoint(endpoint, reasonOf(cause, timeoutMillis)));
|
|
39
|
+
const connected = yield* Effect.acquireRelease(Effect.tryPromise({
|
|
40
|
+
try: () => chromium.connectOverCDP(endpoint, {
|
|
41
|
+
timeout,
|
|
42
|
+
...options.headers === void 0 ? {} : { headers: { ...options.headers } }
|
|
43
|
+
}),
|
|
44
|
+
catch: (cause) => failed(cause, timeout)
|
|
45
|
+
}).pipe(Effect.withSpan("Cdp.connect", {}, { captureStackTrace: false })), (browser) => Effect.tryPromise(() => browser.close()).pipe(Effect.ignore));
|
|
46
|
+
const context = connected.contexts()[0] ?? (yield* Effect.tryPromise({
|
|
47
|
+
try: () => connected.newContext(),
|
|
48
|
+
catch: (cause) => failed(cause)
|
|
49
|
+
}));
|
|
50
|
+
return yield* make(context, {
|
|
51
|
+
id: options.id ?? "cdp",
|
|
52
|
+
provider: options.provider ?? "cdp",
|
|
53
|
+
expiresAt: options.expiresAt,
|
|
54
|
+
capture: options.capture
|
|
55
|
+
}, options);
|
|
56
|
+
});
|
|
57
|
+
const layer = (options) => Layer.effect(Browser, open(options));
|
|
58
|
+
//#endregion
|
|
59
|
+
export { layer, open, Cdp_exports as t };
|
|
60
|
+
|
|
61
|
+
//# sourceMappingURL=Cdp.mjs.map
|
package/dist/Cdp.mjs.map
ADDED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"Cdp.mjs","names":["Url.quoted","Browser.make","Browser.Browser"],"sources":["../src/Cdp.ts"],"sourcesContent":["/**\n * A browser reached over the Chrome DevTools Protocol: a Chrome started with\n * `--remote-debugging-port`, or any provider that hands out a CDP WebSocket URL.\n *\n * Closing the scope disconnects. It does not close the remote browser; its owner does that.\n *\n * @since 0.3.0\n */\nimport { type DateTime, Effect, Layer, Redacted } from \"effect\";\nimport { chromium } from \"playwright-core\";\n\nimport * as Browser from \"./Browser.ts\";\nimport { type BrowserError, Failed, type Reason } from \"./BrowserError.ts\";\nimport { reasonOf, undispatched } from \"./internal/page/context.ts\";\nimport * as Url from \"./internal/page/url.ts\";\n\nexport interface Options extends Browser.Options {\n /**\n * `ws://`, `wss://` or `http://` DevTools endpoint. Often a credential, so it may be redacted;\n * connect failures never include its userinfo, path or query.\n */\n readonly endpoint: string | Redacted.Redacted<string>;\n readonly headers?: Readonly<Record<string, string>> | undefined;\n /** Identifies the session in `Browser.id`. Defaults to `\"cdp\"`. */\n readonly id?: string | undefined;\n readonly provider?: string | undefined;\n /** Bound on connecting. Defaults to 30 seconds. */\n readonly connectTimeoutMillis?: number | undefined;\n /** When the provider ends the session on its own, as a hosted session's timeout does. */\n readonly expiresAt?: DateTime.Utc | undefined;\n /**\n * A connection apart from this one for the pages' screencasts, as a hosted provider supplies.\n * Without one, each page's capture runs on its own session.\n */\n readonly capture?: Browser.CaptureSource | undefined;\n}\n\n/**\n * Playwright can echo the endpoint, or a URL derived from it with its query, userinfo or path, in\n * a connect failure. Those parts are often the credential, so a URL keeps its scheme, host and\n * port, and any other echo of the endpoint is replaced.\n */\nconst withoutEndpoint = (endpoint: string, reason: Reason): Reason => {\n if (reason._tag !== \"Failed\") return reason;\n\n const origins = reason.detail.replace(Url.quoted, (url) => {\n const parsed = URL.parse(url);\n\n return parsed === null || parsed.host === \"\" ? \"<url>\" : `${parsed.protocol}//${parsed.host}`;\n });\n\n return new Failed({\n detail: endpoint === \"\" ? origins : origins.replaceAll(endpoint, \"<endpoint>\"),\n });\n};\n\n/** Connect and open a `Browser` over the endpoint's first context. */\nexport const open = Effect.fn(\"Cdp.open\")(function* (options: Options) {\n const endpoint = Redacted.isRedacted(options.endpoint)\n ? Redacted.value(options.endpoint)\n : options.endpoint;\n\n const timeout = options.connectTimeoutMillis ?? 30_000;\n\n const failed = (cause: unknown, timeoutMillis?: number) =>\n undispatched(\"connect\", withoutEndpoint(endpoint, reasonOf(cause, timeoutMillis)));\n\n // The endpoint is often a credential, so the connect span names no part of it.\n const connected = yield* Effect.acquireRelease(\n Effect.tryPromise({\n try: () =>\n chromium.connectOverCDP(endpoint, {\n timeout,\n ...(options.headers === undefined ? {} : { headers: { ...options.headers } }),\n }),\n catch: (cause) => failed(cause, timeout),\n }).pipe(Effect.withSpan(\"Cdp.connect\", {}, { captureStackTrace: false })),\n (browser) => Effect.tryPromise(() => browser.close()).pipe(Effect.ignore),\n );\n\n const context =\n connected.contexts()[0] ??\n (yield* Effect.tryPromise({\n try: () => connected.newContext(),\n catch: (cause) => failed(cause),\n }));\n\n return yield* Browser.make(\n context,\n {\n id: options.id ?? \"cdp\",\n provider: options.provider ?? \"cdp\",\n expiresAt: options.expiresAt,\n capture: options.capture,\n },\n options,\n );\n});\n\nexport const layer = (options: Options): Layer.Layer<Browser.Browser, BrowserError> =>\n Layer.effect(Browser.Browser, open(options));\n"],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;AA0CA,MAAM,mBAAmB,UAAkB,WAA2B;CACpE,IAAI,OAAO,SAAS,UAAU,OAAO;CAErC,MAAM,UAAU,OAAO,OAAO,QAAQA,SAAa,QAAQ;EACzD,MAAM,SAAS,IAAI,MAAM,GAAG;EAE5B,OAAO,WAAW,QAAQ,OAAO,SAAS,KAAK,UAAU,GAAG,OAAO,SAAS,IAAI,OAAO;CACzF,CAAC;CAED,OAAO,IAAI,OAAO,EAChB,QAAQ,aAAa,KAAK,UAAU,QAAQ,WAAW,UAAU,YAAY,EAC/E,CAAC;AACH;;AAGA,MAAa,OAAO,OAAO,GAAG,UAAU,CAAC,CAAC,WAAW,SAAkB;CACrE,MAAM,WAAW,SAAS,WAAW,QAAQ,QAAQ,IACjD,SAAS,MAAM,QAAQ,QAAQ,IAC/B,QAAQ;CAEZ,MAAM,UAAU,QAAQ,wBAAwB;CAEhD,MAAM,UAAU,OAAgB,kBAC9B,aAAa,WAAW,gBAAgB,UAAU,SAAS,OAAO,aAAa,CAAC,CAAC;CAGnF,MAAM,YAAY,OAAO,OAAO,eAC9B,OAAO,WAAW;EAChB,WACE,SAAS,eAAe,UAAU;GAChC;GACA,GAAI,QAAQ,YAAY,KAAA,IAAY,CAAC,IAAI,EAAE,SAAS,EAAE,GAAG,QAAQ,QAAQ,EAAE;EAC7E,CAAC;EACH,QAAQ,UAAU,OAAO,OAAO,OAAO;CACzC,CAAC,CAAC,CAAC,KAAK,OAAO,SAAS,eAAe,CAAC,GAAG,EAAE,mBAAmB,MAAM,CAAC,CAAC,IACvE,YAAY,OAAO,iBAAiB,QAAQ,MAAM,CAAC,CAAC,CAAC,KAAK,OAAO,MAAM,CAC1E;CAEA,MAAM,UACJ,UAAU,SAAS,CAAC,CAAC,OACpB,OAAO,OAAO,WAAW;EACxB,WAAW,UAAU,WAAW;EAChC,QAAQ,UAAU,OAAO,KAAK;CAChC,CAAC;CAEH,OAAO,OAAOC,KACZ,SACA;EACE,IAAI,QAAQ,MAAM;EAClB,UAAU,QAAQ,YAAY;EAC9B,WAAW,QAAQ;EACnB,SAAS,QAAQ;CACnB,GACA,OACF;AACF,CAAC;AAED,MAAa,SAAS,YACpB,MAAM,OAAOC,SAAiB,KAAK,OAAO,CAAC"}
|
|
@@ -0,0 +1,138 @@
|
|
|
1
|
+
import { t as __exportAll } from "./rolldown-runtime-D7D4PA-g.mjs";
|
|
2
|
+
import { Subject } from "./BrowserEvent.mjs";
|
|
3
|
+
import { Schema } from "effect";
|
|
4
|
+
//#region src/internal/timeline/words.ts
|
|
5
|
+
const quoted = (value) => JSON.stringify(value ?? "");
|
|
6
|
+
/** A subject in words, such as `button "Play"`; one without a name says where it was. */
|
|
7
|
+
const named = (subject, point) => {
|
|
8
|
+
const kind = subject.role ?? subject.tag;
|
|
9
|
+
if (subject.name !== "") return `${kind} ${JSON.stringify(subject.name)}`;
|
|
10
|
+
return point === void 0 ? kind : `${kind} at ${point}`;
|
|
11
|
+
};
|
|
12
|
+
/** A change's context in words: `row "Ether", column "1h"` or `beside "Price", under "Bitcoin"`. */
|
|
13
|
+
const where = ({ row, column, label, heading }, grouped = false) => {
|
|
14
|
+
const parts = [
|
|
15
|
+
row === void 0 ? "" : `row ${quoted(row)}`,
|
|
16
|
+
column === void 0 || grouped ? "" : `column ${quoted(column)}`,
|
|
17
|
+
label === void 0 ? "" : `beside ${quoted(label)}`,
|
|
18
|
+
heading === void 0 || grouped ? "" : `under ${quoted(heading)}`
|
|
19
|
+
].filter((part) => part !== "");
|
|
20
|
+
return parts.length === 0 ? "" : ` (${parts.join(", ")})`;
|
|
21
|
+
};
|
|
22
|
+
/** A change in words, such as `"$61,240" became "$62,010" (row "Bitcoin", column "Price")`. */
|
|
23
|
+
const describe$1 = (change, grouped = false) => {
|
|
24
|
+
const { subject, before, after, count, lowest, highest } = change;
|
|
25
|
+
const context = where(subject.context, grouped);
|
|
26
|
+
const range = lowest === void 0 || highest === void 0 ? "" : `, from ${lowest} to ${highest}`;
|
|
27
|
+
const times = count > 1 ? ` (it changed ${count} times${range})` : "";
|
|
28
|
+
switch (change.kind) {
|
|
29
|
+
case "title": return `the title ${before === void 0 ? "now reads" : `${quoted(before)} became`} ${quoted(after)}`;
|
|
30
|
+
case "value": {
|
|
31
|
+
const field = named(subject, void 0);
|
|
32
|
+
if (after === "checked" || after === "not checked") return `${field} is now ${after}`;
|
|
33
|
+
if (after === void 0 || after === "") return `${field} was cleared`;
|
|
34
|
+
return after === "••••" || before === void 0 || before === "" ? `${field} was ${after === "••••" ? "edited" : `set to ${quoted(after)}`}` : `${field} changed from ${quoted(before)} to ${quoted(after)}`;
|
|
35
|
+
}
|
|
36
|
+
case "appeared": return `${quoted(after)} appeared${context}`;
|
|
37
|
+
case "disappeared": return `${quoted(before)} disappeared${context}`;
|
|
38
|
+
case "brief": return `${quoted(after)} appeared and went away again${context}`;
|
|
39
|
+
case "text": return before === void 0 ? `now reads ${quoted(after)}${context}${times}` : `${quoted(before)} became ${quoted(after)}${context}${times}`;
|
|
40
|
+
}
|
|
41
|
+
};
|
|
42
|
+
//#endregion
|
|
43
|
+
//#region src/Change.ts
|
|
44
|
+
/**
|
|
45
|
+
* What visibly changed on a page over a window, element by element: text that changed, appeared,
|
|
46
|
+
* disappeared or came and went, a field's value, and the document's title. A change says what was
|
|
47
|
+
* shown at the window's start and at its end, how often it changed between, where it is on the
|
|
48
|
+
* page, and the input it followed, where it was that input's doing.
|
|
49
|
+
*
|
|
50
|
+
* `Page.changes` reads it. A page records once something reads its changes: from then, and from the
|
|
51
|
+
* start of each later document once it is parsed, until nobody has read it for two minutes. A page
|
|
52
|
+
* nobody reads records nothing. The record keeps 256 elements, each with its last 32 changes, for a
|
|
53
|
+
* minute; an element that keeps changing gives way before news, and what gives way is counted in
|
|
54
|
+
* `dropped`, with `from` moved past it. A change is told when it was in view as the page rendered
|
|
55
|
+
* it, its style showing it, so one scrolled away later is still told, and something removed or
|
|
56
|
+
* hidden only if it was in view before. What the record cannot see: pictures, a canvas, frames,
|
|
57
|
+
* shadow roots and SVG; a value a script sets; and a class that reveals an element the record has
|
|
58
|
+
* not seen before, such as a toast already on the page, though its later changes are seen.
|
|
59
|
+
*
|
|
60
|
+
* @since 0.3.0
|
|
61
|
+
*/
|
|
62
|
+
var Change_exports = /* @__PURE__ */ __exportAll({
|
|
63
|
+
Change: () => Change,
|
|
64
|
+
Changes: () => Changes,
|
|
65
|
+
Kind: () => Kind,
|
|
66
|
+
describe: () => describe
|
|
67
|
+
});
|
|
68
|
+
/**
|
|
69
|
+
* `text` changed; `appeared` and `disappeared`, whether added or removed or shown or hidden;
|
|
70
|
+
* `brief`, appeared and gone again by the window's end; `value`, a field's; `title`, the document's.
|
|
71
|
+
*/
|
|
72
|
+
const Kind = Schema.Literals([
|
|
73
|
+
"text",
|
|
74
|
+
"appeared",
|
|
75
|
+
"disappeared",
|
|
76
|
+
"brief",
|
|
77
|
+
"value",
|
|
78
|
+
"title"
|
|
79
|
+
]);
|
|
80
|
+
var Change = class extends Schema.Class("effect-browser/Change")({
|
|
81
|
+
kind: Kind,
|
|
82
|
+
/**
|
|
83
|
+
* What changed, as the page names it now, or where it was for what went. Its own words are what
|
|
84
|
+
* changed, so its name is empty unless something else names it, as a field's label does.
|
|
85
|
+
*/
|
|
86
|
+
subject: Subject,
|
|
87
|
+
/** When it first changed in the window, in host monotonic milliseconds on the browser's clock. */
|
|
88
|
+
startedAt: Schema.Finite,
|
|
89
|
+
/** When it last changed in the window. */
|
|
90
|
+
at: Schema.Finite,
|
|
91
|
+
/**
|
|
92
|
+
* What it showed at the window's start; absent for what appeared and where the record let that go.
|
|
93
|
+
* What disappeared says what it showed as it went. A field's value reads `••••` unless unmasked.
|
|
94
|
+
*/
|
|
95
|
+
before: Schema.optional(Schema.String),
|
|
96
|
+
/** What it showed at the window's end; absent for what disappeared. What came and went says what it showed. */
|
|
97
|
+
after: Schema.optional(Schema.String),
|
|
98
|
+
/** How many times what it showed changed in the window. */
|
|
99
|
+
count: Schema.Int.check(Schema.isGreaterThan(0)),
|
|
100
|
+
/** For a number that changed more than once, its lowest and highest, as shown. */
|
|
101
|
+
lowest: Schema.optional(Schema.String),
|
|
102
|
+
highest: Schema.optional(Schema.String),
|
|
103
|
+
/** When it last changed before the window, as far back as the record keeps: in flux, not news. */
|
|
104
|
+
earlier: Schema.optional(Schema.Finite),
|
|
105
|
+
/**
|
|
106
|
+
* When the trusted input it followed reached the page, where it was that input's doing. It was not
|
|
107
|
+
* in flux: in the 10 s before the input it had not changed, and nothing had come into or left what
|
|
108
|
+
* it sits in, so a ticker's tick or a feed's line is not. Then it changed within 3 s inside what
|
|
109
|
+
* the input acted on or its row, form, dialog or controlled element; or, elsewhere, within 500 ms
|
|
110
|
+
* of an input on a page where nothing had changed in the 2 s before, as a menu a portal puts at
|
|
111
|
+
* the end of the page does. What holds the input's target, as a menu holds its item, does not
|
|
112
|
+
* count against it. The page's `Action` that sent it holds that time.
|
|
113
|
+
*/
|
|
114
|
+
cause: Schema.optional(Schema.Finite)
|
|
115
|
+
}) {};
|
|
116
|
+
var Changes = class extends Schema.Class("effect-browser/Changes")({
|
|
117
|
+
/** The page's document these changes belong to, as `Navigated` counts them. */
|
|
118
|
+
document: Schema.Int.check(Schema.isGreaterThanOrEqualTo(0)),
|
|
119
|
+
/** Where the record is whole: before it, changes may be missing. */
|
|
120
|
+
from: Schema.Finite,
|
|
121
|
+
/** Where the window ends: its `until`, or when the page was read. */
|
|
122
|
+
until: Schema.Finite,
|
|
123
|
+
/**
|
|
124
|
+
* Where the window ends on the page's own clock. Give these changes as the next read's `since` and
|
|
125
|
+
* the two windows meet exactly, whatever the clock mapping does meanwhile.
|
|
126
|
+
*/
|
|
127
|
+
cursor: Schema.Finite,
|
|
128
|
+
/** Changes in the window the record let go, at least; 0 when it kept them all. */
|
|
129
|
+
dropped: Schema.Int.check(Schema.isGreaterThanOrEqualTo(0)),
|
|
130
|
+
/** Oldest first, by when each began to change. */
|
|
131
|
+
changes: Schema.Array(Change)
|
|
132
|
+
}) {};
|
|
133
|
+
/** A change in words for a model, such as `"$61,240" became "$62,010" (row "Bitcoin", column "Price")`. */
|
|
134
|
+
const describe = (change) => describe$1(change);
|
|
135
|
+
//#endregion
|
|
136
|
+
export { describe as a, quoted as c, Kind as i, where as l, Change_exports as n, describe$1 as o, Changes as r, named as s, Change as t };
|
|
137
|
+
|
|
138
|
+
//# sourceMappingURL=Change-DNvztNLu.mjs.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"Change-DNvztNLu.mjs","names":["describe","Words.describe"],"sources":["../src/internal/timeline/words.ts","../src/Change.ts"],"sourcesContent":["/**\n * What changed on a page, in words for a model: a change with where it is, and what it is. A moment\n * tells its changes this way, and a tool's receipt the changes its action caused.\n */\nimport type { Subject, SubjectContext } from \"../../BrowserEvent.ts\";\nimport type { Change } from \"../../Change.ts\";\n\nexport const quoted = (value: string | undefined) => JSON.stringify(value ?? \"\");\n\n/** A subject in words, such as `button \"Play\"`; one without a name says where it was. */\nexport const named = (subject: Subject, point: string | undefined) => {\n const kind = subject.role ?? subject.tag;\n\n if (subject.name !== \"\") return `${kind} ${JSON.stringify(subject.name)}`;\n\n return point === undefined ? kind : `${kind} at ${point}`;\n};\n\n/** A change's context in words: `row \"Ether\", column \"1h\"` or `beside \"Price\", under \"Bitcoin\"`. */\nexport const where = ({ row, column, label, heading }: SubjectContext, grouped = false) => {\n const parts = [\n row === undefined ? \"\" : `row ${quoted(row)}`,\n column === undefined || grouped ? \"\" : `column ${quoted(column)}`,\n label === undefined ? \"\" : `beside ${quoted(label)}`,\n heading === undefined || grouped ? \"\" : `under ${quoted(heading)}`,\n ].filter((part) => part !== \"\");\n\n return parts.length === 0 ? \"\" : ` (${parts.join(\", \")})`;\n};\n\n/** A change in words, such as `\"$61,240\" became \"$62,010\" (row \"Bitcoin\", column \"Price\")`. */\nexport const describe = (change: Change, grouped = false): string => {\n const { subject, before, after, count, lowest, highest } = change;\n const context = where(subject.context, grouped);\n\n const range =\n lowest === undefined || highest === undefined ? \"\" : `, from ${lowest} to ${highest}`;\n\n const times = count > 1 ? ` (it changed ${count} times${range})` : \"\";\n\n switch (change.kind) {\n case \"title\":\n return `the title ${before === undefined ? \"now reads\" : `${quoted(before)} became`} ${quoted(after)}`;\n case \"value\": {\n const field = named(subject, undefined);\n\n if (after === \"checked\" || after === \"not checked\") return `${field} is now ${after}`;\n if (after === undefined || after === \"\") return `${field} was cleared`;\n\n return after === \"••••\" || before === undefined || before === \"\"\n ? `${field} was ${after === \"••••\" ? \"edited\" : `set to ${quoted(after)}`}`\n : `${field} changed from ${quoted(before)} to ${quoted(after)}`;\n }\n case \"appeared\":\n return `${quoted(after)} appeared${context}`;\n case \"disappeared\":\n return `${quoted(before)} disappeared${context}`;\n case \"brief\":\n return `${quoted(after)} appeared and went away again${context}`;\n case \"text\":\n return before === undefined\n ? `now reads ${quoted(after)}${context}${times}`\n : `${quoted(before)} became ${quoted(after)}${context}${times}`;\n }\n};\n","/**\n * What visibly changed on a page over a window, element by element: text that changed, appeared,\n * disappeared or came and went, a field's value, and the document's title. A change says what was\n * shown at the window's start and at its end, how often it changed between, where it is on the\n * page, and the input it followed, where it was that input's doing.\n *\n * `Page.changes` reads it. A page records once something reads its changes: from then, and from the\n * start of each later document once it is parsed, until nobody has read it for two minutes. A page\n * nobody reads records nothing. The record keeps 256 elements, each with its last 32 changes, for a\n * minute; an element that keeps changing gives way before news, and what gives way is counted in\n * `dropped`, with `from` moved past it. A change is told when it was in view as the page rendered\n * it, its style showing it, so one scrolled away later is still told, and something removed or\n * hidden only if it was in view before. What the record cannot see: pictures, a canvas, frames,\n * shadow roots and SVG; a value a script sets; and a class that reveals an element the record has\n * not seen before, such as a toast already on the page, though its later changes are seen.\n *\n * @since 0.3.0\n */\nimport { Schema } from \"effect\";\n\nimport { Subject } from \"./BrowserEvent.ts\";\nimport * as Words from \"./internal/timeline/words.ts\";\n\n/**\n * `text` changed; `appeared` and `disappeared`, whether added or removed or shown or hidden;\n * `brief`, appeared and gone again by the window's end; `value`, a field's; `title`, the document's.\n */\nexport const Kind = Schema.Literals([\"text\", \"appeared\", \"disappeared\", \"brief\", \"value\", \"title\"]);\n\nexport type Kind = typeof Kind.Type;\n\nexport class Change extends Schema.Class<Change>(\"effect-browser/Change\")({\n kind: Kind,\n /**\n * What changed, as the page names it now, or where it was for what went. Its own words are what\n * changed, so its name is empty unless something else names it, as a field's label does.\n */\n subject: Subject,\n /** When it first changed in the window, in host monotonic milliseconds on the browser's clock. */\n startedAt: Schema.Finite,\n /** When it last changed in the window. */\n at: Schema.Finite,\n /**\n * What it showed at the window's start; absent for what appeared and where the record let that go.\n * What disappeared says what it showed as it went. A field's value reads `••••` unless unmasked.\n */\n before: Schema.optional(Schema.String),\n /** What it showed at the window's end; absent for what disappeared. What came and went says what it showed. */\n after: Schema.optional(Schema.String),\n /** How many times what it showed changed in the window. */\n count: Schema.Int.check(Schema.isGreaterThan(0)),\n /** For a number that changed more than once, its lowest and highest, as shown. */\n lowest: Schema.optional(Schema.String),\n highest: Schema.optional(Schema.String),\n /** When it last changed before the window, as far back as the record keeps: in flux, not news. */\n earlier: Schema.optional(Schema.Finite),\n /**\n * When the trusted input it followed reached the page, where it was that input's doing. It was not\n * in flux: in the 10 s before the input it had not changed, and nothing had come into or left what\n * it sits in, so a ticker's tick or a feed's line is not. Then it changed within 3 s inside what\n * the input acted on or its row, form, dialog or controlled element; or, elsewhere, within 500 ms\n * of an input on a page where nothing had changed in the 2 s before, as a menu a portal puts at\n * the end of the page does. What holds the input's target, as a menu holds its item, does not\n * count against it. The page's `Action` that sent it holds that time.\n */\n cause: Schema.optional(Schema.Finite),\n}) {}\n\nexport class Changes extends Schema.Class<Changes>(\"effect-browser/Changes\")({\n /** The page's document these changes belong to, as `Navigated` counts them. */\n document: Schema.Int.check(Schema.isGreaterThanOrEqualTo(0)),\n /** Where the record is whole: before it, changes may be missing. */\n from: Schema.Finite,\n /** Where the window ends: its `until`, or when the page was read. */\n until: Schema.Finite,\n /**\n * Where the window ends on the page's own clock. Give these changes as the next read's `since` and\n * the two windows meet exactly, whatever the clock mapping does meanwhile.\n */\n cursor: Schema.Finite,\n /** Changes in the window the record let go, at least; 0 when it kept them all. */\n dropped: Schema.Int.check(Schema.isGreaterThanOrEqualTo(0)),\n /** Oldest first, by when each began to change. */\n changes: Schema.Array(Change),\n}) {}\n\n/** A change in words for a model, such as `\"$61,240\" became \"$62,010\" (row \"Bitcoin\", column \"Price\")`. */\nexport const describe = (change: Change): string => Words.describe(change);\n"],"mappings":"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"}
|