reactor-effect-browser 0.0.0-reserved.0 → 0.2.0

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.
@@ -0,0 +1,294 @@
1
+ import * as Effect from "effect/Effect";
2
+ import { ReactorError } from "reactor-effect-client";
3
+ import { errorOf } from "reactor-effect-client/host";
4
+ const attempt = (body) => Effect.try({ try: body, catch: (e) => errorOf(e, "InvalidState") });
5
+ export const requireBrowserPeer = () => {
6
+ if (typeof RTCPeerConnection !== "function" || typeof MediaStream !== "function")
7
+ throw new ReactorError("UnsupportedHost", "Browser transport requires RTCPeerConnection and MediaStream; choose the native peer layer explicitly on a supported server runtime.", { outcome: "not-submitted" });
8
+ };
9
+ export class BrowserPeer {
10
+ bufferedLimit;
11
+ nativeTracks = true;
12
+ pc;
13
+ channels;
14
+ transceivers = new Map();
15
+ received = new Map();
16
+ leases = new Set();
17
+ messageLimit = 262_144;
18
+ constructor(bufferedLimit = 1_048_576) {
19
+ this.bufferedLimit = bufferedLimit;
20
+ }
21
+ prepare(servers, tracks, emit) {
22
+ const self = this;
23
+ return Effect.gen(function* () {
24
+ const pc = yield* attempt(() => {
25
+ requireBrowserPeer();
26
+ self.close();
27
+ const pc = new RTCPeerConnection({ iceServers: [...servers] });
28
+ self.pc = pc;
29
+ // Reliable, ordered defaults; preserve the source's control-before-data ordering.
30
+ const control = pc.createDataChannel("control"), data = pc.createDataChannel("data");
31
+ self.channels = { control, data };
32
+ const live = () => self.pc === pc;
33
+ const wire = (channel, kind) => {
34
+ channel.binaryType = "arraybuffer";
35
+ channel.onopen = () => {
36
+ if (live())
37
+ emit({ type: "channel", channel: kind, open: true });
38
+ };
39
+ channel.onclose = () => {
40
+ if (live())
41
+ emit({ type: "channel", channel: kind, open: false });
42
+ };
43
+ channel.onerror = () => {
44
+ if (live())
45
+ emit({
46
+ type: "error",
47
+ error: new ReactorError("Disconnected", `${kind} channel error`),
48
+ });
49
+ };
50
+ channel.onmessage = (event) => {
51
+ if (!live())
52
+ return;
53
+ if (!(event.data instanceof ArrayBuffer)) {
54
+ emit({
55
+ type: "error",
56
+ error: new ReactorError("Protocol", "nonbinary channel message"),
57
+ });
58
+ return;
59
+ }
60
+ if (event.data.byteLength > self.messageLimit) {
61
+ emit({
62
+ type: "error",
63
+ error: new ReactorError("Overflow", "received message exceeds negotiated/local bound"),
64
+ });
65
+ return;
66
+ }
67
+ emit({ type: "message", channel: kind, bytes: new Uint8Array(event.data) });
68
+ };
69
+ };
70
+ wire(control, "control");
71
+ wire(data, "data");
72
+ for (const declared of tracks)
73
+ self.transceivers.set(declared.name, {
74
+ declared,
75
+ transceiver: pc.addTransceiver(declared.kind, { direction: declared.direction }),
76
+ });
77
+ pc.onconnectionstatechange = () => {
78
+ if (live())
79
+ emit({ type: "state", state: pc.connectionState });
80
+ };
81
+ pc.onicecandidate = (event) => {
82
+ if (!live())
83
+ return;
84
+ if (event.candidate === null) {
85
+ emit({ type: "ice" });
86
+ return;
87
+ }
88
+ const c = event.candidate;
89
+ emit({
90
+ type: "ice",
91
+ candidate: {
92
+ candidate: c.candidate,
93
+ ...(c.sdpMid === null ? {} : { sdp_mid: c.sdpMid }),
94
+ ...(c.sdpMLineIndex === null ? {} : { sdp_mline_index: c.sdpMLineIndex }),
95
+ },
96
+ });
97
+ };
98
+ pc.ontrack = (event) => {
99
+ if (!live()) {
100
+ event.track.stop();
101
+ return;
102
+ }
103
+ const entry = [...self.transceivers.entries()].find(([, item]) => item.transceiver === event.transceiver);
104
+ if (entry === undefined || event.transceiver.mid === null) {
105
+ event.track.stop();
106
+ emit({
107
+ type: "error",
108
+ error: new ReactorError("Protocol", "received track has no declared mapping"),
109
+ });
110
+ return;
111
+ }
112
+ const [name] = entry;
113
+ self.received.get(name)?.stop();
114
+ self.received.set(name, event.track);
115
+ emit({ type: "track", name, mid: event.transceiver.mid });
116
+ };
117
+ return pc;
118
+ });
119
+ return yield* Effect.tryPromise({
120
+ try: async (signal) => {
121
+ const abort = () => {
122
+ if (self.pc === pc)
123
+ self.close();
124
+ };
125
+ signal.addEventListener("abort", abort, { once: true });
126
+ try {
127
+ const offer = await pc.createOffer();
128
+ if (signal.aborted || self.pc !== pc)
129
+ throw new ReactorError("Aborted", "peer preparation interrupted");
130
+ if (offer.sdp === undefined || offer.sdp.length === 0)
131
+ throw new ReactorError("Protocol", "createOffer returned no SDP");
132
+ await pc.setLocalDescription(offer);
133
+ if (signal.aborted || self.pc !== pc)
134
+ throw new ReactorError("Aborted", "peer preparation interrupted");
135
+ const mapping = tracks.map((track) => {
136
+ const mid = self.transceivers.get(track.name)?.transceiver.mid;
137
+ if (mid == null)
138
+ throw new ReactorError("Protocol", `missing mid after setLocalDescription: ${track.name}`);
139
+ return Object.freeze({ ...track, mid });
140
+ });
141
+ return { sdp: offer.sdp, mapping: Object.freeze(mapping) };
142
+ }
143
+ finally {
144
+ signal.removeEventListener("abort", abort);
145
+ }
146
+ },
147
+ catch: (e) => errorOf(e, "Disconnected", "prepare peer"),
148
+ });
149
+ });
150
+ }
151
+ answer(sdp) {
152
+ return Effect.tryPromise({
153
+ try: async () => {
154
+ const pc = this.require();
155
+ await pc.setRemoteDescription({ type: "answer", sdp });
156
+ if (this.pc !== pc)
157
+ throw new ReactorError("Disconnected", "peer closed while applying SDP answer");
158
+ const negotiated = pc.sctp?.maxMessageSize;
159
+ this.messageLimit =
160
+ typeof negotiated === "number" && Number.isFinite(negotiated) && negotiated >= 1
161
+ ? Math.min(Math.floor(negotiated), 262_144)
162
+ : 262_144;
163
+ },
164
+ catch: (e) => errorOf(e, "Disconnected", "apply SDP answer"),
165
+ });
166
+ }
167
+ require() {
168
+ if (this.pc === undefined)
169
+ throw new ReactorError("InvalidState", "peer is closed");
170
+ return this.pc;
171
+ }
172
+ named(name) {
173
+ this.require();
174
+ const entry = this.transceivers.get(name);
175
+ if (entry === undefined)
176
+ throw new ReactorError("InvalidState", `unknown track: ${name}`);
177
+ return entry;
178
+ }
179
+ send(kind, bytes) {
180
+ return attempt(() => {
181
+ const channel = this.channels?.[kind];
182
+ if (channel === undefined || channel.readyState !== "open")
183
+ throw new ReactorError("Disconnected", `${kind} channel is not open`, {
184
+ outcome: "not-submitted",
185
+ });
186
+ if (bytes.byteLength > this.messageLimit ||
187
+ channel.bufferedAmount + bytes.byteLength > this.bufferedLimit)
188
+ throw new ReactorError("Overflow", `${kind} message/send buffer bound exceeded`, {
189
+ outcome: "not-submitted",
190
+ });
191
+ try {
192
+ channel.send(bytes);
193
+ }
194
+ catch (e) {
195
+ throw errorOf(e, "Disconnected", `send ${kind}`);
196
+ }
197
+ });
198
+ }
199
+ lease(name) {
200
+ this.require();
201
+ const track = this.received.get(name);
202
+ if (track === undefined || track.readyState !== "live")
203
+ throw new ReactorError("InvalidState", `no live received track: ${name}`);
204
+ const clone = track.clone();
205
+ this.leases.add(clone);
206
+ return clone;
207
+ }
208
+ release(track) {
209
+ this.leases.delete(track);
210
+ track.stop();
211
+ }
212
+ direction(name, active) {
213
+ return attempt(() => {
214
+ const entry = this.named(name);
215
+ entry.transceiver.direction = active ? entry.declared.direction : "inactive";
216
+ });
217
+ }
218
+ replace(name, track) {
219
+ return Effect.tryPromise({
220
+ try: async () => {
221
+ const entry = this.named(name), pc = this.require();
222
+ if (entry.declared.direction !== "sendonly")
223
+ throw new ReactorError("InvalidState", `${name} is not an outgoing track`);
224
+ if (track !== null && (track.kind !== entry.declared.kind || track.readyState !== "live"))
225
+ throw new ReactorError("InvalidState", "outgoing track kind/liveness mismatch");
226
+ await entry.transceiver.sender.replaceTrack(track);
227
+ if (this.pc !== pc)
228
+ throw new ReactorError("Disconnected", "peer closed during replaceTrack");
229
+ },
230
+ catch: (e) => errorOf(e, "InvalidState", "replace track"),
231
+ });
232
+ }
233
+ maxBitrate(name, bitsPerSecond) {
234
+ return Effect.tryPromise({
235
+ try: async () => {
236
+ const entry = this.named(name);
237
+ if (entry.declared.direction !== "sendonly" ||
238
+ !Number.isSafeInteger(bitsPerSecond) ||
239
+ bitsPerSecond < 1)
240
+ throw new ReactorError("InvalidState", "maxBitrate requires an outgoing track and positive integral bits/sec");
241
+ const sender = entry.transceiver.sender, parameters = sender.getParameters();
242
+ if (parameters.encodings.length === 0)
243
+ throw new ReactorError("UnsupportedCapability", "sender has no mutable encodings yet");
244
+ for (const encoding of parameters.encodings)
245
+ encoding.maxBitrate = bitsPerSecond;
246
+ await sender.setParameters(parameters);
247
+ },
248
+ catch: (e) => errorOf(e, "UnsupportedCapability", "sender bitrate"),
249
+ });
250
+ }
251
+ stats() {
252
+ return Effect.tryPromise({
253
+ try: async () => {
254
+ const pc = this.require(), report = await pc.getStats();
255
+ if (this.pc !== pc)
256
+ throw new ReactorError("Disconnected", "stale stats generation");
257
+ const entries = [];
258
+ report.forEach((entry) => {
259
+ entries.push(entry);
260
+ });
261
+ return entries;
262
+ },
263
+ catch: (e) => errorOf(e, "UnsupportedCapability", "WebRTC statistics"),
264
+ });
265
+ }
266
+ close() {
267
+ const pc = this.pc, channels = this.channels;
268
+ this.pc = undefined;
269
+ this.channels = undefined;
270
+ if (channels !== undefined)
271
+ for (const channel of [channels.control, channels.data]) {
272
+ channel.onopen = null;
273
+ channel.onclose = null;
274
+ channel.onerror = null;
275
+ channel.onmessage = null;
276
+ channel.close();
277
+ }
278
+ if (pc !== undefined) {
279
+ pc.onconnectionstatechange = null;
280
+ pc.onicecandidate = null;
281
+ pc.ontrack = null;
282
+ pc.close();
283
+ }
284
+ for (const track of this.received.values())
285
+ track.stop();
286
+ for (const track of this.leases)
287
+ track.stop();
288
+ this.received.clear();
289
+ this.leases.clear();
290
+ this.transceivers.clear();
291
+ this.messageLimit = 262_144;
292
+ }
293
+ }
294
+ //# sourceMappingURL=peer.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"peer.js","sourceRoot":"","sources":["../../src/_internal/peer.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,23 @@
1
+ import * as Effect from "effect/Effect";
2
+ import { ReactorError } from "reactor-effect-client";
3
+ import { CoordinatorClient } from "reactor-effect-client/host";
4
+ import type { ClipReady } from "reactor-effect-client/wire";
5
+ export interface Segment {
6
+ readonly url: string;
7
+ readonly kind: "init" | "media";
8
+ }
9
+ export interface DownloadOptions {
10
+ readonly timeoutMs?: number;
11
+ readonly maxManifestBytes?: number;
12
+ readonly maxSegmentBytes?: number;
13
+ readonly maxTotalBytes?: number;
14
+ readonly maxSegments?: number;
15
+ }
16
+ export declare const parsePlaylist: (text: string, baseUrl: string, maxSegments?: number) => readonly Segment[];
17
+ /** Bounded transport of a prepared recording. Does not decode, play, or assert further generation.
18
+ * This API intentionally uses a caller wall deadline, not an unbounded wait based on a prediction. */
19
+ export declare const downloadClip: (http: CoordinatorClient, clip: ClipReady, options?: DownloadOptions) => Effect.Effect<{
20
+ readonly bytes: Uint8Array<ArrayBuffer>;
21
+ readonly segments: readonly Segment[];
22
+ }, ReactorError>;
23
+ //# sourceMappingURL=recording.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"recording.d.ts","sourceRoot":"","sources":["../../src/_internal/recording.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,MAAM,MAAM,eAAe,CAAC;AACxC,OAAO,EAAE,YAAY,EAAE,MAAM,uBAAuB,CAAC;AACrD,OAAO,EACL,iBAAiB,EAKlB,MAAM,4BAA4B,CAAC;AACpC,OAAO,KAAK,EAAE,SAAS,EAAE,MAAM,4BAA4B,CAAC;AAC5D,MAAM,WAAW,OAAO;IACtB,QAAQ,CAAC,GAAG,EAAE,MAAM,CAAC;IACrB,QAAQ,CAAC,IAAI,EAAE,MAAM,GAAG,OAAO,CAAC;CACjC;AACD,MAAM,WAAW,eAAe;IAC9B,QAAQ,CAAC,SAAS,CAAC,EAAE,MAAM,CAAC;IAC5B,QAAQ,CAAC,gBAAgB,CAAC,EAAE,MAAM,CAAC;IACnC,QAAQ,CAAC,eAAe,CAAC,EAAE,MAAM,CAAC;IAClC,QAAQ,CAAC,aAAa,CAAC,EAAE,MAAM,CAAC;IAChC,QAAQ,CAAC,WAAW,CAAC,EAAE,MAAM,CAAC;CAC/B;AAGD,eAAO,MAAM,aAAa,SAClB,MAAM,WACH,MAAM,2BAEd,SAAS,OAAO,EAqDlB,CAAC;AACF;sGACsG;AACtG,eAAO,MAAM,YAAY,SACjB,iBAAiB,QACjB,SAAS,YACN,eAAe,KACvB,MAAM,CAAC,MAAM,CACd;IACE,QAAQ,CAAC,KAAK,EAAE,UAAU,CAAC,WAAW,CAAC,CAAC;IACxC,QAAQ,CAAC,QAAQ,EAAE,SAAS,OAAO,EAAE,CAAC;CACvC,EACD,YAAY,CA6FV,CAAC"}
@@ -0,0 +1,110 @@
1
+ import * as Effect from "effect/Effect";
2
+ import { ReactorError } from "reactor-effect-client";
3
+ import { CoordinatorClient, errorOf, positiveLimit, retryAfterMs, terminal, } from "reactor-effect-client/host";
4
+ const pure = (body) => Effect.try({ try: body, catch: errorOf });
5
+ export const parsePlaylist = (text, baseUrl, maxSegments = 1024) => {
6
+ positiveLimit(maxSegments, "clip segments", 16_384);
7
+ if (text.trimStart().split(/\r?\n/, 1)[0]?.trim() !== "#EXTM3U")
8
+ throw new ReactorError("Protocol", "not an HLS playlist");
9
+ let init;
10
+ const media = [];
11
+ for (const line of text
12
+ .split(/\r?\n/)
13
+ .map((s) => s.trim())
14
+ .filter(Boolean)) {
15
+ if (/^#EXT-X-(STREAM-INF|I-FRAME-STREAM-INF|BYTERANGE|DISCONTINUITY|PART|PRELOAD-HINT|SKIP|GAP|SESSION-KEY|DEFINE)(:|$)/.test(line))
16
+ throw new ReactorError("UnsupportedCapability", "master, byte-range, discontinuous, encrypted, gap, variable, or low-latency playlists require an HLS player, not byte concatenation");
17
+ if (line.startsWith("#EXT-X-KEY:") && !/(?:^|,)METHOD=NONE(?:,|$)/.test(line.slice(11)))
18
+ throw new ReactorError("UnsupportedCapability", "encrypted clips are not assembled by this client");
19
+ if (line.startsWith("#EXT-X-MAP:")) {
20
+ if (line.includes("BYTERANGE="))
21
+ throw new ReactorError("UnsupportedCapability", "byte-range init segments unsupported");
22
+ const match = /(?:^|,)URI="([^"]+)"/.exec(line.slice(11)), uri = match?.[1];
23
+ if (uri === undefined || (init !== undefined && init !== uri))
24
+ throw new ReactorError("Protocol", "missing or changing HLS init URI");
25
+ init = uri;
26
+ }
27
+ else if (!line.startsWith("#")) {
28
+ if (media.length >= maxSegments)
29
+ throw new ReactorError("Overflow", "clip segment count bound exceeded");
30
+ media.push(line);
31
+ }
32
+ }
33
+ if (media.length === 0)
34
+ throw new ReactorError("Protocol", "empty clip playlist");
35
+ const resolve = (uri) => {
36
+ const url = new URL(uri, baseUrl);
37
+ if (!(url.protocol === "http:" || url.protocol === "https:") || url.username || url.password)
38
+ throw new ReactorError("Protocol", "clip URL must use http(s) with no embedded credentials");
39
+ return url.href;
40
+ };
41
+ if (init === undefined &&
42
+ media.some((uri) => /\.(?:m4s|mp4|m4a|m4v)$/i.test(new URL(uri, baseUrl).pathname)))
43
+ throw new ReactorError("Protocol", "fragmented MP4 playlist lacks EXT-X-MAP init segment");
44
+ const segments = init === undefined ? [] : [{ kind: "init", url: resolve(init) }];
45
+ for (const uri of media)
46
+ segments.push({ kind: "media", url: resolve(uri) });
47
+ return Object.freeze(segments.map((s) => Object.freeze(s)));
48
+ };
49
+ /** Bounded transport of a prepared recording. Does not decode, play, or assert further generation.
50
+ * This API intentionally uses a caller wall deadline, not an unbounded wait based on a prediction. */
51
+ export const downloadClip = (http, clip, options = {}) => Effect.suspend(() => {
52
+ const action = Effect.gen(function* () {
53
+ const bounds = yield* pure(() => ({
54
+ timeout: positiveLimit(options.timeoutMs ?? 60_000, "clip timeout", 600_000),
55
+ manifest: positiveLimit(options.maxManifestBytes ?? 262_144, "manifest bytes", 2_097_152),
56
+ segment: positiveLimit(options.maxSegmentBytes ?? 16_777_216, "segment bytes", 64 * 1024 * 1024),
57
+ total: positiveLimit(options.maxTotalBytes ?? 64 * 1024 * 1024, "clip bytes", 64 * 1024 * 1024),
58
+ count: positiveLimit(options.maxSegments ?? 1024, "clip segments", 16_384),
59
+ }));
60
+ const fetchAndAssemble = Effect.gen(function* () {
61
+ let segments;
62
+ while (true) {
63
+ const response = yield* http.request({
64
+ operation: "clip playlist",
65
+ url: clip.playlist_url,
66
+ auth: "same-origin",
67
+ maxBytes: bounds.manifest,
68
+ });
69
+ if (response.status !== 202) {
70
+ segments = yield* pure(() => parsePlaylist(new TextDecoder("utf-8", { fatal: true }).decode(response.bytes), clip.playlist_url, bounds.count));
71
+ break;
72
+ }
73
+ // A local peer disconnection does not prove stopped inference. Query the remote descriptor.
74
+ const descriptor = yield* http.read(clip.session_id);
75
+ if (terminal(descriptor.state))
76
+ return yield* Effect.fail(new ReactorError("TerminalSession", "session terminated before playlist became available"));
77
+ yield* Effect.sleep(Math.max(200, Math.min(retryAfterMs(response.headers) ?? 2000, 2000)));
78
+ }
79
+ let size = 0;
80
+ const chunks = [];
81
+ for (const segment of segments) {
82
+ const response = yield* http.request({
83
+ operation: "clip segment",
84
+ url: segment.url,
85
+ auth: "same-origin",
86
+ maxBytes: Math.min(bounds.segment, bounds.total - size || 1),
87
+ });
88
+ if (response.status === 202)
89
+ return yield* Effect.fail(new ReactorError("Protocol", "playlist referenced a segment that is not ready"));
90
+ size += response.bytes.length;
91
+ if (size > bounds.total)
92
+ return yield* Effect.fail(new ReactorError("Overflow", "assembled clip byte bound exceeded"));
93
+ chunks.push(response.bytes);
94
+ }
95
+ const bytes = new Uint8Array(size);
96
+ let at = 0;
97
+ for (const chunk of chunks) {
98
+ bytes.set(chunk, at);
99
+ at += chunk.length;
100
+ }
101
+ return { bytes, segments };
102
+ });
103
+ return yield* fetchAndAssemble.pipe(Effect.timeoutOrElse({
104
+ duration: bounds.timeout,
105
+ orElse: () => Effect.fail(new ReactorError("Timeout", "clip download deadline; remote generation outcome unchanged")),
106
+ }));
107
+ });
108
+ return action;
109
+ });
110
+ //# sourceMappingURL=recording.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"recording.js","sourceRoot":"","sources":["../../src/_internal/recording.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,21 @@
1
+ import * as Effect from "effect/Effect";
2
+ import * as Crypto from "effect/Crypto";
3
+ import * as Layer from "effect/Layer";
4
+ import * as Http from "effect/unstable/http/HttpClient";
5
+ import type * as Scope from "effect/Scope";
6
+ import { PeerFactory } from "reactor-effect-client";
7
+ import type { Configuration, Factory, ReactorError, Session } from "reactor-effect-client";
8
+ import type { TrackGeneration } from "reactor-effect-client/host";
9
+ export declare const layer: Layer.Layer<PeerFactory, never, never>;
10
+ /** Browser peer selection; acquisition and cleanup remain owned by the client. */
11
+ export declare const make: (configuration?: Configuration) => Effect.Effect<Factory, never, Http.HttpClient | Crypto.Crypto>;
12
+ export interface MediaGeneration extends Omit<TrackGeneration, "track" | "publish"> {
13
+ readonly track: (name: string) => Effect.Effect<MediaStreamTrack, ReactorError, Scope.Scope>;
14
+ readonly publish: (name: string, source: MediaStreamTrack) => Effect.Effect<void, ReactorError>;
15
+ }
16
+ /** Track leases and publication retain the generation that negotiated them. */
17
+ export declare const media: (session: Session) => Effect.Effect<MediaGeneration, ReactorError>;
18
+ export * as Recording from "./_internal/recording.js";
19
+ export { videoFrames, audioSamples, mediaFacilities, audioContext, webAudioSamples, play, nextPresentation, } from "./_internal/media.js";
20
+ export type { VideoSample, AudioSample, MediaOptions, Presentation, WebAudioOptions, WebAudioSample, } from "./_internal/media.js";
21
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,MAAM,MAAM,eAAe,CAAC;AACxC,OAAO,KAAK,MAAM,MAAM,eAAe,CAAC;AACxC,OAAO,KAAK,KAAK,MAAM,cAAc,CAAC;AACtC,OAAO,KAAK,IAAI,MAAM,iCAAiC,CAAC;AACxD,OAAO,KAAK,KAAK,KAAK,MAAM,cAAc,CAAC;AAC3C,OAAO,EAAE,WAAW,EAAsB,MAAM,uBAAuB,CAAC;AACxE,OAAO,KAAK,EAAE,aAAa,EAAE,OAAO,EAAE,YAAY,EAAE,OAAO,EAAE,MAAM,uBAAuB,CAAC;AAE3F,OAAO,KAAK,EAAE,eAAe,EAAE,MAAM,4BAA4B,CAAC;AAGlE,eAAO,MAAM,KAAK,wCAGhB,CAAC;AAEH,kFAAkF;AAClF,eAAO,MAAM,IAAI,mBACA,aAAa,KAC3B,MAAM,CAAC,MAAM,CAAC,OAAO,EAAE,KAAK,EAAE,IAAI,CAAC,UAAU,GAAG,MAAM,CAAC,MAAM,CACT,CAAC;AAExD,MAAM,WAAW,eAAgB,SAAQ,IAAI,CAAC,eAAe,EAAE,OAAO,GAAG,SAAS,CAAC;IACjF,QAAQ,CAAC,KAAK,EAAE,CAAC,IAAI,EAAE,MAAM,KAAK,MAAM,CAAC,MAAM,CAAC,gBAAgB,EAAE,YAAY,EAAE,KAAK,CAAC,KAAK,CAAC,CAAC;IAC7F,QAAQ,CAAC,OAAO,EAAE,CAAC,IAAI,EAAE,MAAM,EAAE,MAAM,EAAE,gBAAgB,KAAK,MAAM,CAAC,MAAM,CAAC,IAAI,EAAE,YAAY,CAAC,CAAC;CACjG;AAED,+EAA+E;AAC/E,eAAO,MAAM,KAAK,YAAa,OAAO,KAAG,MAAM,CAAC,MAAM,CAAC,eAAe,EAAE,YAAY,CASjF,CAAC;AAEJ,OAAO,KAAK,SAAS,MAAM,0BAA0B,CAAC;AACtD,OAAO,EACL,WAAW,EACX,YAAY,EACZ,eAAe,EACf,YAAY,EACZ,eAAe,EACf,IAAI,EACJ,gBAAgB,GACjB,MAAM,sBAAsB,CAAC;AAC9B,YAAY,EACV,WAAW,EACX,WAAW,EACX,YAAY,EACZ,YAAY,EACZ,eAAe,EACf,cAAc,GACf,MAAM,sBAAsB,CAAC"}
package/dist/index.js ADDED
@@ -0,0 +1,23 @@
1
+ import * as Effect from "effect/Effect";
2
+ import * as Crypto from "effect/Crypto";
3
+ import * as Layer from "effect/Layer";
4
+ import * as Http from "effect/unstable/http/HttpClient";
5
+ import { PeerFactory, make as makeClient } from "reactor-effect-client";
6
+ import { errorOf, trackGeneration } from "reactor-effect-client/host";
7
+ import { BrowserPeer, requireBrowserPeer } from "./_internal/peer.js";
8
+ export const layer = Layer.succeed(PeerFactory, {
9
+ check: Effect.try({ try: requireBrowserPeer, catch: errorOf }),
10
+ make: () => new BrowserPeer(),
11
+ });
12
+ /** Browser peer selection; acquisition and cleanup remain owned by the client. */
13
+ export const make = (configuration = {}) => makeClient(configuration).pipe(Effect.provide(layer));
14
+ /** Track leases and publication retain the generation that negotiated them. */
15
+ export const media = (session) => trackGeneration(session).pipe(Effect.map((generation) => ({
16
+ ...generation,
17
+ // The browser peer advertises this capability and is the only producer of
18
+ // these DOM tracks. The portable session keeps their lifetime contract.
19
+ track: (name) => generation.track(name).pipe(Effect.map((track) => track)),
20
+ })));
21
+ export * as Recording from "./_internal/recording.js";
22
+ export { videoFrames, audioSamples, mediaFacilities, audioContext, webAudioSamples, play, nextPresentation, } from "./_internal/media.js";
23
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,MAAM,MAAM,eAAe,CAAC;AACxC,OAAO,KAAK,MAAM,MAAM,eAAe,CAAC;AACxC,OAAO,KAAK,KAAK,MAAM,cAAc,CAAC;AACtC,OAAO,KAAK,IAAI,MAAM,iCAAiC,CAAC;AAExD,OAAO,EAAE,WAAW,EAAE,IAAI,IAAI,UAAU,EAAE,MAAM,uBAAuB,CAAC;AAExE,OAAO,EAAE,OAAO,EAAE,eAAe,EAAE,MAAM,4BAA4B,CAAC;AAEtE,OAAO,EAAE,WAAW,EAAE,kBAAkB,EAAE,MAAM,qBAAqB,CAAC;AAEtE,MAAM,CAAC,MAAM,KAAK,GAAG,KAAK,CAAC,OAAO,CAAC,WAAW,EAAE;IAC9C,KAAK,EAAE,MAAM,CAAC,GAAG,CAAC,EAAE,GAAG,EAAE,kBAAkB,EAAE,KAAK,EAAE,OAAO,EAAE,CAAC;IAC9D,IAAI,EAAE,GAAG,EAAE,CAAC,IAAI,WAAW,EAAE;CAC9B,CAAC,CAAC;AAEH,kFAAkF;AAClF,MAAM,CAAC,MAAM,IAAI,GAAG,CAClB,aAAa,GAAkB,EAAE,EAC+B,EAAE,CAClE,UAAU,CAAC,aAAa,CAAC,CAAC,IAAI,CAAC,MAAM,CAAC,OAAO,CAAC,KAAK,CAAC,CAAC,CAAC;AAOxD,+EAA+E;AAC/E,MAAM,CAAC,MAAM,KAAK,GAAG,CAAC,OAAgB,EAAgD,EAAE,CACtF,eAAe,CAAC,OAAO,CAAC,CAAC,IAAI,CAC3B,MAAM,CAAC,GAAG,CAAC,CAAC,UAAU,EAAE,EAAE,CAAC,CAAC;IAC1B,GAAG,UAAU;IACb,0EAA0E;IAC1E,wEAAwE;IACxE,KAAK,EAAE,CAAC,IAAY,EAAE,EAAE,CACtB,UAAU,CAAC,KAAK,CAAC,IAAI,CAAC,CAAC,IAAI,CAAC,MAAM,CAAC,GAAG,CAAC,CAAC,KAAK,EAAE,EAAE,CAAC,KAAyB,CAAC,CAAC;CAChF,CAAC,CAAC,CACJ,CAAC;AAEJ,OAAO,KAAK,SAAS,MAAM,0BAA0B,CAAC;AACtD,OAAO,EACL,WAAW,EACX,YAAY,EACZ,eAAe,EACf,YAAY,EACZ,eAAe,EACf,IAAI,EACJ,gBAAgB,GACjB,MAAM,sBAAsB,CAAC"}
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2023 Effectful Technologies Inc
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
package/package.json CHANGED
@@ -1,17 +1,45 @@
1
1
  {
2
2
  "name": "reactor-effect-browser",
3
- "version": "0.0.0-reserved.0",
4
- "description": "Namespace bootstrap only; wait for the first qualified SDK release.",
3
+ "version": "0.2.0",
4
+ "description": "Browser WebRTC host for reactor-effect-client: built-in peer connections, generation-scoped tracks, media conversion and recording",
5
+ "type": "module",
5
6
  "license": "Apache-2.0",
6
7
  "repository": {
7
8
  "type": "git",
8
- "url": "git+https://github.com/mannyc2/reactor-effect-client.git"
9
+ "url": "git+https://github.com/mannyc2/reactor-effect-client.git",
10
+ "directory": "packages/browser"
9
11
  },
12
+ "sideEffects": false,
10
13
  "files": [
14
+ "dist",
15
+ "notices",
16
+ "LICENSE",
17
+ "NOTICE",
11
18
  "README.md"
12
19
  ],
20
+ "exports": {
21
+ ".": {
22
+ "types": "./dist/index.d.ts",
23
+ "import": "./dist/index.js"
24
+ }
25
+ },
26
+ "peerDependencies": {
27
+ "effect": "4.0.0-rc.115",
28
+ "reactor-effect-client": "0.2.0"
29
+ },
30
+ "devDependencies": {
31
+ "@types/bun": "1.4.2",
32
+ "effect": "4.0.0-rc.115",
33
+ "reactor-effect-client": "0.2.0",
34
+ "reactor-effect-test-kit": "0.2.0"
35
+ },
36
+ "scripts": {
37
+ "build": "rm -rf dist && tsc -p tsconfig.build.json",
38
+ "typecheck": "tsc -p tsconfig.json --noEmit",
39
+ "test": "bun test"
40
+ },
13
41
  "publishConfig": {
14
42
  "access": "public",
15
- "provenance": false
43
+ "provenance": true
16
44
  }
17
45
  }