@aperture-browser/live-session 0.0.0-init.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 @@
1
+ {"version":3,"file":"index.js","names":[],"sources":["../src/input-keycodes.ts","../src/keyboard.ts","../src/protocol.ts","../src/viewport.ts","../src/connection.ts"],"sourcesContent":["export const evdevKeycodeByCode: Readonly<Record<string, number>> = {\n Escape: 1,\n Digit1: 2,\n Digit2: 3,\n Digit3: 4,\n Digit4: 5,\n Digit5: 6,\n Digit6: 7,\n Digit7: 8,\n Digit8: 9,\n Digit9: 10,\n Digit0: 11,\n Minus: 12,\n Equal: 13,\n Backspace: 14,\n Tab: 15,\n KeyQ: 16,\n KeyW: 17,\n KeyE: 18,\n KeyR: 19,\n KeyT: 20,\n KeyY: 21,\n KeyU: 22,\n KeyI: 23,\n KeyO: 24,\n KeyP: 25,\n BracketLeft: 26,\n BracketRight: 27,\n Enter: 28,\n ControlLeft: 29,\n KeyA: 30,\n KeyS: 31,\n KeyD: 32,\n KeyF: 33,\n KeyG: 34,\n KeyH: 35,\n KeyJ: 36,\n KeyK: 37,\n KeyL: 38,\n Semicolon: 39,\n Quote: 40,\n Backquote: 41,\n ShiftLeft: 42,\n Backslash: 43,\n KeyZ: 44,\n KeyX: 45,\n KeyC: 46,\n KeyV: 47,\n KeyB: 48,\n KeyN: 49,\n KeyM: 50,\n Comma: 51,\n Period: 52,\n Slash: 53,\n ShiftRight: 54,\n NumpadMultiply: 55,\n AltLeft: 56,\n Space: 57,\n CapsLock: 58,\n F1: 59,\n F2: 60,\n F3: 61,\n F4: 62,\n F5: 63,\n F6: 64,\n F7: 65,\n F8: 66,\n F9: 67,\n F10: 68,\n NumLock: 69,\n ScrollLock: 70,\n Numpad7: 71,\n Numpad8: 72,\n Numpad9: 73,\n NumpadSubtract: 74,\n Numpad4: 75,\n Numpad5: 76,\n Numpad6: 77,\n NumpadAdd: 78,\n Numpad1: 79,\n Numpad2: 80,\n Numpad3: 81,\n Numpad0: 82,\n NumpadDecimal: 83,\n IntlBackslash: 86,\n F11: 87,\n F12: 88,\n NumpadEnter: 96,\n ControlRight: 97,\n NumpadDivide: 98,\n PrintScreen: 99,\n AltRight: 100,\n Home: 102,\n ArrowUp: 103,\n PageUp: 104,\n ArrowLeft: 105,\n ArrowRight: 106,\n End: 107,\n ArrowDown: 108,\n PageDown: 109,\n Insert: 110,\n Delete: 111,\n Pause: 119,\n MetaLeft: 125,\n MetaRight: 126,\n ContextMenu: 127,\n};\n","import type { BrowserInputMessage } from \"./browser-input.ts\";\n\ntype KeyboardInputMessage = Extract<BrowserInputMessage, { type: \"input.key\" }>;\n\nconst CODE_TO_WINDOWS_VIRTUAL_KEY: Record<string, number> = {\n Backspace: 8,\n Tab: 9,\n Enter: 13,\n NumpadEnter: 13,\n ShiftLeft: 16,\n ShiftRight: 16,\n ControlLeft: 17,\n ControlRight: 17,\n AltLeft: 18,\n AltRight: 18,\n Pause: 19,\n CapsLock: 20,\n Escape: 27,\n Space: 32,\n PageUp: 33,\n PageDown: 34,\n End: 35,\n Home: 36,\n ArrowLeft: 37,\n ArrowUp: 38,\n ArrowRight: 39,\n ArrowDown: 40,\n Insert: 45,\n Delete: 46,\n MetaLeft: 91,\n MetaRight: 92,\n ContextMenu: 93,\n Semicolon: 186,\n Equal: 187,\n Comma: 188,\n Minus: 189,\n Period: 190,\n Slash: 191,\n Backquote: 192,\n BracketLeft: 219,\n Backslash: 220,\n BracketRight: 221,\n Quote: 222,\n};\n\nconst KEY_TO_WINDOWS_VIRTUAL_KEY: Record<string, number> = {\n Backspace: 8,\n Tab: 9,\n Enter: 13,\n Shift: 16,\n Control: 17,\n Alt: 18,\n Pause: 19,\n CapsLock: 20,\n Escape: 27,\n \" \": 32,\n PageUp: 33,\n PageDown: 34,\n End: 35,\n Home: 36,\n ArrowLeft: 37,\n ArrowUp: 38,\n ArrowRight: 39,\n ArrowDown: 40,\n Insert: 45,\n Delete: 46,\n Meta: 91,\n ContextMenu: 93,\n};\n\nconst FORWARDED_BROWSER_SHORTCUT_CODES = new Set([\n \"KeyA\",\n \"KeyC\",\n \"KeyF\",\n \"KeyG\",\n \"KeyH\",\n \"KeyJ\",\n \"KeyK\",\n \"KeyL\",\n \"KeyN\",\n \"KeyO\",\n \"KeyP\",\n \"KeyR\",\n \"KeyS\",\n \"KeyT\",\n \"KeyW\",\n \"KeyX\",\n \"KeyV\",\n \"KeyZ\",\n \"KeyY\",\n \"BracketLeft\",\n \"BracketRight\",\n \"ArrowLeft\",\n \"ArrowRight\",\n \"ArrowUp\",\n \"ArrowDown\",\n \"Backspace\",\n \"Delete\",\n \"Enter\",\n \"Tab\",\n]);\n\nexport function keyboardModifiers(event: KeyboardEvent | MouseEvent | WheelEvent): number {\n let modifiers = 0;\n if (event.altKey) {\n modifiers |= 1;\n }\n if (event.ctrlKey) {\n modifiers |= 2;\n }\n if (event.metaKey) {\n modifiers |= 4;\n }\n if (event.shiftKey) {\n modifiers |= 8;\n }\n return modifiers;\n}\n\nexport function isPrintableKey(event: KeyboardEvent): boolean {\n return event.key.length === 1 && !event.ctrlKey && !event.metaKey && !event.altKey;\n}\n\nexport function keyboardInputMessage(\n event: KeyboardEvent,\n action: KeyboardInputMessage[\"action\"],\n): Omit<KeyboardInputMessage, \"type\" | \"targetId\" | \"action\"> {\n const virtualKeyCode = windowsVirtualKeyCodeForCodeOrKey(event.code, event.key);\n const modifiers = keyboardModifiers(event);\n const text = action === \"down\" && isPrintableKey(event) ? event.key : undefined;\n const unmodifiedText = event.key.length === 1 ? event.key : undefined;\n\n return {\n key: event.key,\n code: event.code,\n text,\n unmodifiedText,\n modifiers,\n windowsVirtualKeyCode: virtualKeyCode,\n nativeVirtualKeyCode: virtualKeyCode,\n location: event.location,\n autoRepeat: event.repeat,\n isKeypad: event.location === KeyboardEvent.DOM_KEY_LOCATION_NUMPAD,\n };\n}\n\nexport function shouldForwardBrowserShortcut(event: KeyboardEvent): boolean {\n if (event.key === \"Escape\") {\n return false;\n }\n\n if (isModifierCode(event.code)) {\n return true;\n }\n\n const mod = event.metaKey || event.ctrlKey;\n if (!mod) {\n return true;\n }\n\n return FORWARDED_BROWSER_SHORTCUT_CODES.has(event.code);\n}\n\nexport function windowsVirtualKeyCodeForCodeOrKey(\n code: string | undefined,\n key: string | undefined,\n): number {\n const byCode = code ? CODE_TO_WINDOWS_VIRTUAL_KEY[code] : undefined;\n if (byCode !== undefined) {\n return byCode;\n }\n\n if (code?.startsWith(\"Key\") && code.length === 4) {\n return code.charCodeAt(3);\n }\n\n if (code?.startsWith(\"Digit\") && code.length === 6) {\n return code.charCodeAt(5);\n }\n\n if (code?.startsWith(\"Numpad\") && code.length === 7) {\n const digit = Number(code.slice(6));\n if (Number.isInteger(digit) && digit >= 0 && digit <= 9) {\n return 96 + digit;\n }\n }\n\n if (code?.startsWith(\"F\")) {\n const functionKey = Number(code.slice(1));\n if (Number.isInteger(functionKey) && functionKey >= 1 && functionKey <= 24) {\n return 111 + functionKey;\n }\n }\n\n const byKey = key ? KEY_TO_WINDOWS_VIRTUAL_KEY[key] : undefined;\n if (byKey !== undefined) {\n return byKey;\n }\n\n if (key?.length === 1) {\n return key.toUpperCase().charCodeAt(0);\n }\n\n return 0;\n}\n\nfunction isModifierCode(code: string): boolean {\n return (\n code === \"AltLeft\" ||\n code === \"AltRight\" ||\n code === \"ControlLeft\" ||\n code === \"ControlRight\" ||\n code === \"MetaLeft\" ||\n code === \"MetaRight\" ||\n code === \"ShiftLeft\" ||\n code === \"ShiftRight\"\n );\n}\n","import * as Effect from \"effect/Effect\";\nimport * as Schema from \"effect/Schema\";\nimport { Recording } from \"@aperture-browser/api-client\";\n\nexport const LIVE_SESSION_PROTOCOL = \"aperture-session.v1\";\n\nexport type CollaborationRole = \"owner\" | \"editor\" | \"viewer\";\nexport type CollaborationLeaseMode = \"implicit\" | \"explicit\";\nexport type CollaborationPhase = \"idle\" | \"connecting\" | \"connected\" | \"disconnected\";\n\nexport interface CollaborationCursor {\n clientId: string;\n targetId: string;\n x: number;\n y: number;\n}\n\nexport type CollaborationPaintPhase = \"start\" | \"move\" | \"end\";\n\nexport interface CollaborationPaintPoint {\n targetId: string;\n strokeId: string;\n color: string;\n width: number;\n phase: CollaborationPaintPhase;\n x: number;\n y: number;\n}\n\nexport type CollaborationPaintEvent =\n | { type: \"point\"; message: CollaborationPaintPoint & { clientId: string } }\n | { type: \"clear\" };\n\nexport interface CollaborationError {\n code: string;\n message: string;\n}\n\n/**\n * Server messages are decoded strictly: an unknown property means the server speaks a\n * protocol revision this client does not understand.\n */\nexport const strictParseOptions = { onExcessProperty: \"error\" } as const;\n\nconst int = Schema.Number.check(Schema.isInt());\nconst positive = Schema.Number.check(Schema.isGreaterThan(0));\nconst positiveInt = int.check(Schema.isGreaterThan(0));\nconst unitInterval = Schema.Number.check(Schema.isBetween({ minimum: 0, maximum: 1 }));\nconst emptyArray = Effect.succeed([]);\n\nfunction arrayOrEmpty<S extends Schema.Top>(item: S) {\n return Schema.Array(item).pipe(Schema.withDecodingDefaultKey(emptyArray));\n}\n\nconst LeaseMode = Schema.Literals([\"implicit\", \"explicit\"]);\n\nconst PresentationQuality = Schema.Struct({\n profile: Schema.String,\n fps: int.check(Schema.isBetween({ minimum: 1, maximum: 120 })),\n bitrateKbps: int.check(Schema.isGreaterThanOrEqualTo(100)),\n keyframeInterval: positiveInt,\n});\n\nconst PresentationProfile = Schema.Struct({\n id: Schema.String,\n label: Schema.String,\n codec: Schema.String,\n mimeType: Schema.String,\n sdpFmtpLine: Schema.String,\n});\n\nconst Presentation = Schema.Struct({\n quality: Schema.optionalKey(PresentationQuality),\n profiles: Schema.Array(PresentationProfile),\n cursorVisible: Schema.Boolean,\n});\n\nconst Target = Schema.Struct({\n id: Schema.String,\n type: Schema.String,\n title: Schema.String,\n url: Schema.String,\n loading: Schema.Boolean,\n viewport: Schema.optionalKey(\n Schema.Struct({\n width: positive,\n height: positive,\n contentWidth: positive,\n contentHeight: positive,\n canvasWidth: positive,\n canvasHeight: positive,\n deviceScaleFactor: positive,\n }),\n ),\n});\n\nconst Participant = Schema.Struct({\n clientId: Schema.String,\n name: Schema.String,\n avatarHash: Schema.String,\n role: Schema.Literals([\"owner\", \"editor\", \"viewer\", \"automation\"]),\n activeTargetId: Schema.optionalKey(Schema.String),\n followingClientId: Schema.optionalKey(Schema.String),\n holdingInput: Schema.Boolean,\n leaseMode: Schema.optionalKey(LeaseMode),\n recovering: Schema.optionalKey(Schema.Boolean),\n});\n\nconst Snapshot = Schema.Struct({\n type: Schema.Literal(\"session.snapshot\"),\n clientId: Schema.String,\n resumeSecret: Schema.String,\n role: Schema.Literals([\"owner\", \"editor\", \"viewer\"]),\n transport: Schema.Literals([\"webrtc\", \"websocket\"]),\n holderClientId: Schema.optionalKey(Schema.String),\n mode: Schema.optionalKey(LeaseMode),\n activeTargetId: Schema.optionalKey(Schema.String),\n targets: arrayOrEmpty(Target),\n participants: arrayOrEmpty(Participant),\n recordings: arrayOrEmpty(Recording),\n presentation: Presentation,\n});\n\nconst PresenceState = Schema.Struct({\n type: Schema.Literal(\"presence.state\"),\n participants: arrayOrEmpty(Participant),\n});\n\nconst InputState = Schema.Struct({\n type: Schema.Literal(\"input.state\"),\n holderClientId: Schema.optionalKey(Schema.String),\n mode: Schema.optionalKey(LeaseMode),\n});\n\nconst Cursor = Schema.Struct({\n type: Schema.Literal(\"presence.cursor\"),\n clientId: Schema.String,\n targetId: Schema.String,\n x: unitInterval,\n y: unitInterval,\n realtimeCounter: positiveInt,\n});\n\nconst CursorClear = Schema.Struct({\n type: Schema.Literal(\"presence.cursor.clear\"),\n clientId: Schema.String,\n realtimeCounter: positiveInt,\n});\n\nconst Paint = Schema.Struct({\n type: Schema.Literal(\"paint.point\"),\n clientId: Schema.String,\n targetId: Schema.String,\n strokeId: Schema.String,\n color: Schema.String.check(Schema.isPattern(/^#[0-9a-fA-F]{6}$/)),\n width: Schema.Number.check(Schema.isBetween({ minimum: 1, maximum: 16 })),\n phase: Schema.Literals([\"start\", \"move\", \"end\"]),\n x: unitInterval,\n y: unitInterval,\n realtimeCounter: Schema.optionalKey(positiveInt),\n});\n\nconst TargetsState = Schema.Struct({\n type: Schema.Literal(\"targets.state\"),\n activeTargetId: Schema.optionalKey(Schema.String),\n targets: arrayOrEmpty(Target),\n});\n\nconst RecordingsState = Schema.Struct({\n type: Schema.Literal(\"recordings.state\"),\n recordings: arrayOrEmpty(Recording),\n});\n\nconst PresentationState = Schema.Struct({\n type: Schema.Literal(\"presentation.state\"),\n presentation: Presentation,\n});\n\nconst ErrorMessage = Schema.Struct({\n type: Schema.Literal(\"error\"),\n code: Schema.String,\n message: Schema.String,\n});\n\nconst CommandResult = Schema.Struct({\n type: Schema.Literals([\n \"target.select.result\",\n \"target.create.result\",\n \"target.close.result\",\n \"page.navigate.result\",\n \"page.history-back.result\",\n \"page.history-forward.result\",\n \"page.reload.result\",\n \"page.stop-loading.result\",\n \"viewport.set.result\",\n \"presentation.quality.set.result\",\n \"presentation.cursor.set.result\",\n \"recording.start.result\",\n \"recording.stop.result\",\n \"recording.cancel.result\",\n ]),\n requestId: Schema.String,\n ok: Schema.Boolean,\n code: Schema.optionalKey(Schema.String),\n message: Schema.optionalKey(Schema.String),\n targetId: Schema.optionalKey(Schema.String),\n recording: Schema.optionalKey(Recording),\n presentation: Schema.optionalKey(Presentation),\n});\n\nexport const LiveSessionServerMessage = Schema.Union([\n Snapshot,\n PresenceState,\n InputState,\n Cursor,\n CursorClear,\n Paint,\n TargetsState,\n RecordingsState,\n PresentationState,\n ErrorMessage,\n CommandResult,\n]);\n\n/** Decodes one JSON text frame from the server, or returns undefined when it is invalid. */\nexport const decodeServerMessage = Schema.decodeUnknownOption(\n Schema.fromJsonString(LiveSessionServerMessage),\n strictParseOptions,\n);\n\nexport type LiveSessionServerMessage = typeof LiveSessionServerMessage.Type;\nexport type LiveSessionSnapshot = typeof Snapshot.Type;\nexport type LiveSessionTarget = typeof Target.Type;\nexport type LiveSessionCommandResult = typeof CommandResult.Type;\nexport type LiveSessionPresentation = typeof Presentation.Type;\nexport type LiveSessionPresentationQuality = typeof PresentationQuality.Type;\nexport type CollaborationParticipant = typeof Participant.Type;\n\nexport const RasterFrameHeader = Schema.Struct({\n type: Schema.Literal(\"presentation.frame\"),\n targetId: Schema.String,\n width: positive,\n height: positive,\n});\n\nexport type LiveSessionRasterFrame = Omit<typeof RasterFrameHeader.Type, \"type\"> & {\n data: Blob;\n};\n","export interface ViewportPreset {\n id: string;\n label: string;\n width: number;\n height: number;\n deviceScaleFactor: number;\n}\n\nexport const VIEWPORT_PRESETS: ViewportPreset[] = [\n createViewportPreset(1280, 720, 1),\n createViewportPreset(1440, 900, 1),\n createViewportPreset(1920, 1080, 1),\n createViewportPreset(2560, 1440, 1),\n createViewportPreset(768, 1024, 1),\n createViewportPreset(390, 844, 1),\n];\n\nexport const DEFAULT_VIEWPORT = VIEWPORT_PRESETS[0];\n\nexport const VIEWPORT_DEVICE_SCALE_FACTORS = [1, 1.5, 2, 3] as const;\n\nexport const STALE_FRAME_MS = 3000;\n\nexport interface RenderMetrics {\n scale: number;\n offsetX: number;\n offsetY: number;\n renderedWidth: number;\n renderedHeight: number;\n}\n\nexport function createViewportPreset(\n width: number,\n height: number,\n deviceScaleFactor: number,\n): ViewportPreset {\n const scaleLabel = formatViewportScale(deviceScaleFactor);\n return {\n id: `${width}x${height}@${scaleLabel}`,\n label: `${width}×${height}`,\n width,\n height,\n deviceScaleFactor,\n };\n}\n\nexport function formatViewportScale(deviceScaleFactor: number): string {\n return Number.isInteger(deviceScaleFactor)\n ? String(deviceScaleFactor)\n : String(deviceScaleFactor).replace(/0+$/, \"\").replace(/\\.$/, \"\");\n}\n\nexport function computeRenderMetrics(\n containerWidth: number,\n containerHeight: number,\n viewportWidth: number,\n viewportHeight: number,\n): RenderMetrics {\n if (viewportWidth <= 0 || viewportHeight <= 0 || containerWidth <= 0 || containerHeight <= 0) {\n return {\n scale: 1,\n offsetX: 0,\n offsetY: 0,\n renderedWidth: containerWidth,\n renderedHeight: containerHeight,\n };\n }\n\n const scale = Math.min(containerWidth / viewportWidth, containerHeight / viewportHeight);\n const renderedWidth = viewportWidth * scale;\n const renderedHeight = viewportHeight * scale;\n\n return {\n scale,\n offsetX: (containerWidth - renderedWidth) / 2,\n offsetY: (containerHeight - renderedHeight) / 2,\n renderedWidth,\n renderedHeight,\n };\n}\n\nexport function mapClientToViewport(\n clientX: number,\n clientY: number,\n rect: DOMRect,\n viewportWidth: number,\n viewportHeight: number,\n): { x: number; y: number } | null {\n const metrics = computeRenderMetrics(rect.width, rect.height, viewportWidth, viewportHeight);\n const localX = clientX - rect.left - metrics.offsetX;\n const localY = clientY - rect.top - metrics.offsetY;\n\n if (\n localX < 0 ||\n localY < 0 ||\n localX > metrics.renderedWidth ||\n localY > metrics.renderedHeight\n ) {\n return null;\n }\n\n return {\n x: Math.round(localX / metrics.scale),\n y: Math.round(localY / metrics.scale),\n };\n}\n","import * as Data from \"effect/Data\";\nimport * as Deferred from \"effect/Deferred\";\nimport * as Effect from \"effect/Effect\";\nimport * as Fiber from \"effect/Fiber\";\nimport * as FiberSet from \"effect/FiberSet\";\nimport * as Option from \"effect/Option\";\nimport * as Schema from \"effect/Schema\";\nimport {\n resolveTenantHeader,\n type ApiCredentials,\n type IceServer,\n} from \"@aperture-browser/api-client\";\nimport {\n decodeServerMessage,\n LIVE_SESSION_PROTOCOL,\n RasterFrameHeader,\n strictParseOptions,\n type LiveSessionCommandResult,\n type LiveSessionRasterFrame,\n type LiveSessionServerMessage,\n type LiveSessionSnapshot,\n} from \"./protocol.ts\";\n\n/** A live session operation that could not complete. */\nexport class LiveSessionError extends Data.TaggedError(\"LiveSessionError\")<{\n readonly message: string;\n}> {}\n\ninterface SessionIdentity {\n clientId: string;\n resumeSecret: string;\n}\n\ninterface SessionHelloIdentity {\n name: string;\n avatarHash: string;\n}\n\nexport type LiveSessionTransportKind = \"webrtc\" | \"websocket\";\n\ninterface LiveSessionConnectionCallbacks {\n onPhase: (phase: \"connecting\" | \"connected\" | \"disconnected\" | \"error\") => void;\n onMessage: (message: LiveSessionServerMessage) => void;\n onFrame: (frame: LiveSessionRasterFrame | null) => void;\n onStream: (stream: MediaStream | null) => void;\n onTransport: (transport: LiveSessionTransportKind | null) => void;\n onError: (message: string) => void;\n}\n\ninterface LiveSessionConnectionOptions {\n baseUrl?: string;\n sessionId: string;\n credentials: ApiCredentials;\n sessionToken?: string;\n identity: SessionHelloIdentity;\n iceServers: readonly IceServer[];\n webrtcSupported: boolean;\n callbacks: LiveSessionConnectionCallbacks;\n}\n\nexport interface LiveSessionConnection {\n /** Replaces the current session transport with a fresh one. */\n readonly reconnect: Effect.Effect<void>;\n /** Switches presentation to the given transport once it is ready. */\n readonly selectTransport: (\n kind: LiveSessionTransportKind,\n ) => Effect.Effect<void, LiveSessionError>;\n readonly sendReliable: (message: Record<string, unknown>) => boolean;\n readonly sendRealtime: (message: Record<string, unknown>) => boolean;\n /** Sends a command and waits for its result message. */\n readonly command: (\n type: string,\n payload?: Record<string, unknown>,\n ) => Effect.Effect<LiveSessionCommandResult, LiveSessionError>;\n}\n\ninterface TransportRequest {\n kind: LiveSessionTransportKind;\n deferred: Deferred.Deferred<void, LiveSessionError>;\n}\n\n/** Forks a background effect into the connection's scope. */\ntype Fork = (effect: Effect.Effect<void>) => Fiber.Fiber<void>;\n\ninterface TransportCallbacks {\n hello: () => Record<string, unknown>;\n message: (transport: SessionTransport, message: LiveSessionServerMessage) => void;\n ready: (transport: SessionTransport) => void;\n failed: (transport: SessionTransport, error: LiveSessionError) => void;\n frame: (transport: SessionTransport, frame: LiveSessionRasterFrame) => void;\n}\n\ninterface SessionTransport {\n readonly kind: LiveSessionTransportKind;\n sendReliable(message: Record<string, unknown>): boolean;\n sendRealtime(message: Record<string, unknown>): boolean;\n close(): void;\n}\n\nconst SignalResponse = Schema.Union([\n Schema.Struct({ version: Schema.Literal(1), type: Schema.Literal(\"answer\"), sdp: Schema.String }),\n Schema.Struct({\n version: Schema.Literal(1),\n type: Schema.Literal(\"ice-candidate\"),\n candidate: Schema.Struct({\n candidate: Schema.String,\n sdpMid: Schema.optionalKey(Schema.NullOr(Schema.String)),\n sdpMLineIndex: Schema.optionalKey(Schema.NullOr(Schema.Number.check(Schema.isInt()))),\n usernameFragment: Schema.optionalKey(Schema.NullOr(Schema.String)),\n }),\n }),\n Schema.Struct({\n version: Schema.Literal(1),\n type: Schema.Literal(\"error\"),\n error: Schema.Struct({ code: Schema.String, message: Schema.String }),\n }),\n]);\n\nconst decodeSignalResponse = Schema.decodeUnknownOption(\n Schema.fromJsonString(SignalResponse),\n strictParseOptions,\n);\n\nconst decodeRasterFrameHeader = Schema.decodeUnknownOption(\n Schema.fromJsonString(RasterFrameHeader),\n strictParseOptions,\n);\n\nconst WEBRTC_DEADLINE_MS = 5_000;\nconst WEBSOCKET_RETRY_MS = 500;\nconst WEBRTC_RETRY_MAX_MS = 15_000;\n\n/**\n * Opens a live session connection. It prefers WebRTC presentation, falls back to\n * WebSocket raster frames, and keeps retrying WebRTC in the background. Closing the scope\n * closes every transport and fails pending commands.\n */\nexport const make = Effect.fnUntraced(function* (options: LiveSessionConnectionOptions) {\n const { callbacks } = options;\n const runFork = yield* FiberSet.makeRuntime<never, void, never>();\n const fork: Fork = (effect) => runFork(effect);\n const after = (millis: number, f: () => void) =>\n fork(Effect.sleep(millis).pipe(Effect.andThen(Effect.sync(f))));\n\n let active: SessionTransport | null = null;\n let candidate: SessionTransport | null = null;\n let identity: SessionIdentity | null = null;\n let preferredTransport: LiveSessionTransportKind = options.webrtcSupported\n ? \"webrtc\"\n : \"websocket\";\n let transportRequest: TransportRequest | null = null;\n let disposed = false;\n let retryTimer: Fiber.Fiber<void> | null = null;\n let webrtcRetryMs = 1_000;\n let nextRequestId = 0;\n let realtimeCounter = 0;\n let inboundRealtimeCounter = 0;\n let candidateMessages: LiveSessionServerMessage[] = [];\n let candidateFrame: LiveSessionRasterFrame | null = null;\n const pendingCommands = new Map<\n string,\n Deferred.Deferred<LiveSessionCommandResult, LiveSessionError>\n >();\n\n const hello = () => ({ type: \"session.hello\", ...(identity ?? options.identity) });\n\n const transportCallbacks: TransportCallbacks = {\n hello,\n message: (transport, message) => handleMessage(transport, message),\n ready: (transport) => activate(transport),\n failed: (transport, error) => transportFailed(transport, error),\n frame: (transport, frame) => {\n if (active === transport) {\n callbacks.onFrame(frame);\n } else if (candidate === transport) {\n candidateFrame = frame;\n }\n },\n };\n\n const dropCandidate = () => {\n candidate?.close();\n candidate = null;\n candidateMessages = [];\n candidateFrame = null;\n };\n\n const clearRetry = () => {\n retryTimer?.interruptUnsafe();\n retryTimer = null;\n };\n\n const rejectPending = (message: string) => {\n const error = new LiveSessionError({ message });\n for (const deferred of pendingCommands.values()) {\n Deferred.doneUnsafe(deferred, Effect.fail(error));\n }\n pendingCommands.clear();\n };\n\n const rejectTransportRequest = (message: string) => {\n if (!transportRequest) {\n return;\n }\n const request = transportRequest;\n transportRequest = null;\n Deferred.doneUnsafe(request.deferred, Effect.fail(new LiveSessionError({ message })));\n };\n\n const startPreferredTransport = () => {\n if (preferredTransport === \"webrtc\" && options.webrtcSupported) {\n startWebRTC();\n } else {\n startWebSocket();\n }\n };\n\n const startWebRTC = () => {\n if (disposed || candidate) {\n return;\n }\n let transport: WebRTCSessionTransport;\n try {\n transport = new WebRTCSessionTransport({\n baseUrl: options.baseUrl,\n sessionId: options.sessionId,\n credentials: options.credentials,\n sessionToken: options.sessionToken,\n iceServers: options.iceServers,\n callbacks: transportCallbacks,\n fork,\n });\n } catch (cause) {\n candidateFailed(\"webrtc\", setupError(cause, \"WebRTC setup failed\"));\n return;\n }\n candidate = transport;\n candidateMessages = [];\n candidateFrame = null;\n transport.connect();\n after(WEBRTC_DEADLINE_MS, () => {\n if (candidate !== transport) {\n return;\n }\n dropCandidate();\n candidateFailed(\"webrtc\", new LiveSessionError({ message: \"WebRTC presentation timed out\" }));\n });\n };\n\n const startWebSocket = () => {\n if (disposed || candidate) {\n return;\n }\n let transport: WebSocketSessionTransport;\n try {\n transport = new WebSocketSessionTransport({\n baseUrl: options.baseUrl,\n sessionId: options.sessionId,\n credentials: options.credentials,\n sessionToken: options.sessionToken,\n callbacks: transportCallbacks,\n fork,\n });\n } catch (cause) {\n candidateFailed(\"websocket\", setupError(cause, \"WebSocket setup failed\"));\n return;\n }\n candidate = transport;\n candidateMessages = [];\n candidateFrame = null;\n transport.connect();\n };\n\n const startWebSocketLater = (millis: number) =>\n after(millis, () => {\n if (!disposed && active === null && candidate === null) {\n startWebSocket();\n }\n });\n\n const activate = (transport: SessionTransport) => {\n if (disposed || candidate !== transport) {\n transport.close();\n return;\n }\n const previous = active;\n const messages = candidateMessages;\n const frame = candidateFrame;\n if (previous && previous !== transport) {\n rejectPending(\"live session transport replaced\");\n }\n candidate = null;\n candidateMessages = [];\n candidateFrame = null;\n active = transport;\n realtimeCounter = 0;\n inboundRealtimeCounter = 0;\n webrtcRetryMs = 1_000;\n callbacks.onPhase(\"connected\");\n callbacks.onTransport(transport.kind);\n if (transportRequest?.kind === transport.kind) {\n const request = transportRequest;\n transportRequest = null;\n Deferred.doneUnsafe(request.deferred, Effect.void);\n }\n if (transport instanceof WebRTCSessionTransport) {\n callbacks.onFrame(null);\n callbacks.onStream(transport.mediaStream());\n } else {\n callbacks.onStream(null);\n if (frame) {\n callbacks.onFrame(frame);\n }\n }\n for (const message of messages) {\n deliverMessage(message);\n }\n if (\n transport.kind === \"websocket\" &&\n preferredTransport === \"webrtc\" &&\n options.webrtcSupported\n ) {\n scheduleWebRTCRetry();\n }\n if (previous && previous !== transport) {\n previous.close();\n }\n };\n\n const transportFailed = (transport: SessionTransport, error: LiveSessionError) => {\n if (disposed) {\n return;\n }\n if (candidate === transport) {\n dropCandidate();\n candidateFailed(transport.kind, error);\n return;\n }\n if (active !== transport) {\n return;\n }\n active = null;\n transport.close();\n rejectPending(\"live session transport was lost\");\n callbacks.onPhase(\"disconnected\");\n callbacks.onError(error.message);\n callbacks.onFrame(null);\n callbacks.onStream(null);\n callbacks.onTransport(null);\n startWebSocketLater(transport.kind === \"webrtc\" ? 0 : WEBSOCKET_RETRY_MS);\n };\n\n const handleMessage = (transport: SessionTransport, message: LiveSessionServerMessage) => {\n if (\n message.type === \"error\" &&\n message.code === \"resume_rejected\" &&\n candidate === transport &&\n active === null\n ) {\n identity = null;\n }\n if (message.type === \"session.snapshot\") {\n identity = { clientId: message.clientId, resumeSecret: message.resumeSecret };\n }\n if (active !== transport) {\n if (candidate !== transport) {\n return;\n }\n candidateMessages.push(message);\n if (message.type === \"session.snapshot\" && transport.kind === \"websocket\") {\n activate(transport);\n }\n return;\n }\n deliverMessage(message);\n };\n\n const deliverMessage = (message: LiveSessionServerMessage) => {\n if (\"realtimeCounter\" in message && message.realtimeCounter !== undefined) {\n if (message.realtimeCounter <= inboundRealtimeCounter) {\n return;\n }\n inboundRealtimeCounter = message.realtimeCounter;\n }\n if (\"requestId\" in message) {\n const deferred = pendingCommands.get(message.requestId);\n if (deferred) {\n pendingCommands.delete(message.requestId);\n Deferred.doneUnsafe(\n deferred,\n message.ok\n ? Effect.succeed(message)\n : Effect.fail(\n new LiveSessionError({\n message: message.message ?? \"live session command failed\",\n }),\n ),\n );\n }\n }\n callbacks.onMessage(message);\n };\n\n const scheduleWebRTCRetry = () => {\n if (\n disposed ||\n preferredTransport !== \"webrtc\" ||\n !options.webrtcSupported ||\n active?.kind === \"webrtc\" ||\n retryTimer !== null\n ) {\n return;\n }\n const delay = webrtcRetryMs;\n webrtcRetryMs = Math.min(WEBRTC_RETRY_MAX_MS, webrtcRetryMs * 2);\n retryTimer = after(delay, () => {\n retryTimer = null;\n startWebRTC();\n });\n };\n\n const candidateFailed = (kind: LiveSessionTransportKind, error: LiveSessionError) => {\n const requested = transportRequest?.kind === kind;\n if (requested) {\n rejectTransportRequest(error.message);\n if (active) {\n preferredTransport = active.kind;\n }\n }\n if (active) {\n if (active.kind === \"websocket\") {\n scheduleWebRTCRetry();\n }\n return;\n }\n if (kind === \"webrtc\") {\n startWebSocket();\n return;\n }\n callbacks.onPhase(\"disconnected\");\n callbacks.onError(error.message);\n startWebSocketLater(WEBSOCKET_RETRY_MS);\n };\n\n const sendReliable = (message: Record<string, unknown>) => active?.sendReliable(message) ?? false;\n\n const sendRealtime = (message: Record<string, unknown>) => {\n realtimeCounter += 1;\n return active?.sendRealtime({ realtimeCounter, ...message }) ?? false;\n };\n\n const close = () => {\n disposed = true;\n clearRetry();\n dropCandidate();\n active?.close();\n active = null;\n rejectTransportRequest(\"live session connection closed\");\n rejectPending(\"live session connection closed\");\n callbacks.onFrame(null);\n callbacks.onStream(null);\n callbacks.onTransport(null);\n };\n\n yield* Effect.addFinalizer(() => Effect.sync(close));\n\n callbacks.onPhase(\"connecting\");\n startPreferredTransport();\n\n return {\n reconnect: Effect.sync(() => {\n clearRetry();\n dropCandidate();\n active?.close();\n active = null;\n rejectTransportRequest(\"live session transport replaced\");\n rejectPending(\"live session transport replaced\");\n callbacks.onPhase(\"connecting\");\n startPreferredTransport();\n }),\n\n selectTransport: (kind) =>\n Effect.suspend(() => {\n if (kind === \"webrtc\" && !options.webrtcSupported) {\n return Effect.fail(\n new LiveSessionError({ message: \"WebRTC presentation is unavailable\" }),\n );\n }\n preferredTransport = kind;\n clearRetry();\n if (candidate && candidate.kind !== kind) {\n dropCandidate();\n }\n rejectTransportRequest(\"presentation selection was replaced\");\n if (active?.kind === kind) {\n return Effect.void;\n }\n const deferred = Deferred.makeUnsafe<void, LiveSessionError>();\n transportRequest = { kind, deferred };\n if (candidate === null) {\n if (kind === \"webrtc\") {\n startWebRTC();\n } else {\n startWebSocket();\n }\n }\n return Deferred.await(deferred);\n }),\n\n sendReliable,\n sendRealtime,\n\n command: (type, payload = {}) =>\n Effect.suspend(() => {\n nextRequestId += 1;\n const requestId = `request-${nextRequestId}`;\n const deferred = Deferred.makeUnsafe<LiveSessionCommandResult, LiveSessionError>();\n pendingCommands.set(requestId, deferred);\n if (!sendReliable({ type, requestId, ...payload })) {\n pendingCommands.delete(requestId);\n return Effect.fail(\n new LiveSessionError({ message: \"live session transport is unavailable\" }),\n );\n }\n return Deferred.await(deferred).pipe(\n Effect.onInterrupt(() => Effect.sync(() => pendingCommands.delete(requestId))),\n );\n }),\n } satisfies LiveSessionConnection;\n});\n\nfunction setupError(cause: unknown, fallback: string) {\n return new LiveSessionError({\n message: cause instanceof Error && cause.message ? cause.message : fallback,\n });\n}\n\nclass WebSocketSessionTransport implements SessionTransport {\n readonly kind = \"websocket\" as const;\n private readonly socket: WebSocket;\n private readonly callbacks: TransportCallbacks;\n private readonly fork: Fork;\n private readonly pendingRealtime = new Map<unknown, Record<string, unknown>>();\n private pendingRasterPacket: Blob | null = null;\n private rasterDecoder: Fiber.Fiber<void> | null = null;\n private decodingRaster = false;\n private realtimeFrame: number | null = null;\n private closed = false;\n\n constructor(options: {\n baseUrl: string | undefined;\n sessionId: string;\n credentials: ApiCredentials;\n sessionToken?: string;\n callbacks: TransportCallbacks;\n fork: Fork;\n }) {\n this.callbacks = options.callbacks;\n this.fork = options.fork;\n this.socket = new WebSocket(\n sessionWebSocketURL(options.baseUrl, options.sessionId),\n sessionProtocols(options.credentials, options.sessionToken),\n );\n this.socket.binaryType = \"blob\";\n }\n\n connect() {\n this.socket.addEventListener(\"open\", () => {\n this.sendReliable(this.callbacks.hello());\n });\n this.socket.addEventListener(\"message\", (event) => {\n if (typeof event.data === \"string\") {\n const message = decodeServerMessage(event.data);\n if (Option.isSome(message)) {\n this.callbacks.message(this, message.value);\n }\n return;\n }\n if (event.data instanceof Blob) {\n // Only the newest packet matters; older ones still waiting are dropped.\n this.pendingRasterPacket = event.data;\n if (!this.decodingRaster) {\n this.decodingRaster = true;\n this.rasterDecoder = this.fork(this.decodeRasterPackets());\n }\n }\n });\n this.socket.addEventListener(\"close\", () => {\n if (!this.closed) {\n this.callbacks.failed(\n this,\n new LiveSessionError({ message: \"WebSocket session transport closed\" }),\n );\n }\n });\n this.socket.addEventListener(\"error\", () => {\n if (!this.closed) {\n this.callbacks.failed(\n this,\n new LiveSessionError({ message: \"WebSocket session transport failed\" }),\n );\n }\n });\n }\n\n sendReliable(message: Record<string, unknown>) {\n this.flushRealtime();\n return this.sendNow(message);\n }\n\n sendRealtime(message: Record<string, unknown>) {\n if (this.socket.readyState !== WebSocket.OPEN) {\n return false;\n }\n this.pendingRealtime.delete(message.type);\n this.pendingRealtime.set(message.type, message);\n if (this.realtimeFrame === null) {\n this.realtimeFrame = window.requestAnimationFrame(() => {\n this.realtimeFrame = null;\n this.flushRealtime();\n });\n }\n return true;\n }\n\n close() {\n this.closed = true;\n this.pendingRasterPacket = null;\n this.rasterDecoder?.interruptUnsafe();\n this.rasterDecoder = null;\n if (this.realtimeFrame !== null) {\n window.cancelAnimationFrame(this.realtimeFrame);\n this.realtimeFrame = null;\n }\n this.pendingRealtime.clear();\n this.socket.close();\n }\n\n // Decodes one packet at a time until none is waiting.\n private decodeRasterPackets(): Effect.Effect<void> {\n return Effect.gen({ self: this }, function* () {\n while (true) {\n const packet = this.pendingRasterPacket;\n if (packet === null || this.closed) {\n this.decodingRaster = false;\n return;\n }\n this.pendingRasterPacket = null;\n const frame = yield* decodeRasterFrame(packet);\n if (Option.isSome(frame) && !this.closed) {\n this.callbacks.frame(this, frame.value);\n }\n }\n });\n }\n\n private flushRealtime() {\n if (this.realtimeFrame !== null) {\n window.cancelAnimationFrame(this.realtimeFrame);\n this.realtimeFrame = null;\n }\n for (const message of this.pendingRealtime.values()) {\n this.sendNow(message);\n }\n this.pendingRealtime.clear();\n }\n\n private sendNow(message: Record<string, unknown>) {\n if (this.socket.readyState !== WebSocket.OPEN) {\n return false;\n }\n this.socket.send(JSON.stringify(message));\n return true;\n }\n}\n\nclass WebRTCSessionTransport implements SessionTransport {\n readonly kind = \"webrtc\" as const;\n private readonly connection: RTCPeerConnection;\n private readonly reliable: RTCDataChannel;\n private readonly realtime: RTCDataChannel;\n private readonly signal: WebSocket;\n private readonly callbacks: TransportCallbacks;\n private readonly fork: Fork;\n private readonly pendingCandidates: RTCIceCandidateInit[] = [];\n private reliableOpen = false;\n private realtimeOpen = false;\n private helloSent = false;\n private snapshotReceived = false;\n private stream: MediaStream | null = null;\n private streamReady = false;\n private closed = false;\n\n constructor(options: {\n baseUrl: string | undefined;\n sessionId: string;\n credentials: ApiCredentials;\n sessionToken?: string;\n iceServers: readonly IceServer[];\n callbacks: TransportCallbacks;\n fork: Fork;\n }) {\n this.callbacks = options.callbacks;\n this.fork = options.fork;\n this.connection = new RTCPeerConnection({\n iceServers: options.iceServers.map((server) => ({ ...server, urls: [...server.urls] })),\n });\n this.reliable = this.connection.createDataChannel(\"application\", { ordered: true });\n this.realtime = this.connection.createDataChannel(\"application-realtime\", {\n ordered: false,\n maxRetransmits: 0,\n });\n this.connection.addTransceiver(\"video\", { direction: \"recvonly\" });\n this.signal = new WebSocket(\n signalWebSocketURL(options.baseUrl, options.sessionId),\n sessionProtocols(options.credentials, options.sessionToken),\n );\n }\n\n connect() {\n this.reliable.addEventListener(\"open\", () => {\n this.reliableOpen = true;\n this.sendHello();\n });\n this.realtime.addEventListener(\"open\", () => {\n this.realtimeOpen = true;\n this.sendHello();\n });\n this.reliable.addEventListener(\"message\", (event) => this.handleApplicationMessage(event));\n this.realtime.addEventListener(\"message\", (event) => this.handleApplicationMessage(event));\n for (const channel of [this.reliable, this.realtime]) {\n channel.addEventListener(\"close\", () => this.fail(\"WebRTC session channel closed\"));\n channel.addEventListener(\"error\", () => this.fail(\"WebRTC session channel failed\"));\n }\n this.connection.addEventListener(\"track\", (event) => {\n this.stream = event.streams[0] ?? new MediaStream([event.track]);\n const ready = () => {\n if (!this.stream) {\n return;\n }\n this.streamReady = true;\n this.maybeReady();\n };\n if (event.track.muted) {\n event.track.addEventListener(\"unmute\", ready, { once: true });\n } else {\n ready();\n }\n });\n this.connection.addEventListener(\"icecandidate\", (event) => {\n if (event.candidate && this.signal.readyState === WebSocket.OPEN) {\n this.signal.send(\n JSON.stringify({\n version: 1,\n type: \"ice-candidate\",\n candidate: event.candidate.toJSON(),\n }),\n );\n }\n });\n this.connection.addEventListener(\"connectionstatechange\", () => {\n if (\n this.connection.connectionState === \"failed\" ||\n this.connection.connectionState === \"closed\"\n ) {\n this.fail(`WebRTC ${this.connection.connectionState}`);\n }\n });\n this.signal.addEventListener(\"open\", () => {\n this.fork(\n this.sendOffer().pipe(\n Effect.catchTag(\"LiveSessionError\", (error) =>\n Effect.sync(() => this.fail(error.message)),\n ),\n ),\n );\n });\n this.signal.addEventListener(\"message\", (event) => this.handleSignal(event));\n this.signal.addEventListener(\"close\", () => this.fail(\"WebRTC signaling closed\"));\n this.signal.addEventListener(\"error\", () => this.fail(\"WebRTC signaling failed\"));\n }\n\n sendReliable(message: Record<string, unknown>) {\n if (this.reliable.readyState !== \"open\") {\n return false;\n }\n this.reliable.send(JSON.stringify(message));\n return true;\n }\n\n sendRealtime(message: Record<string, unknown>) {\n if (this.realtime.readyState !== \"open\") {\n return false;\n }\n this.realtime.send(JSON.stringify(message));\n return true;\n }\n\n close() {\n this.closed = true;\n this.reliable.close();\n this.realtime.close();\n this.connection.close();\n this.signal.close();\n }\n\n mediaStream() {\n return this.stream;\n }\n\n private sendHello() {\n if (this.helloSent || !this.reliableOpen || !this.realtimeOpen) {\n return;\n }\n this.helloSent = this.sendReliable(this.callbacks.hello());\n }\n\n private handleApplicationMessage(event: MessageEvent<unknown>) {\n if (typeof event.data !== \"string\") {\n return;\n }\n const message = decodeServerMessage(event.data);\n if (Option.isNone(message)) {\n this.fail(\"WebRTC session message is invalid\");\n return;\n }\n this.callbacks.message(this, message.value);\n if (message.value.type === \"session.snapshot\") {\n this.snapshotReceived = true;\n this.maybeReady();\n }\n }\n\n private handleSignal(event: MessageEvent<unknown>) {\n const decoded =\n typeof event.data === \"string\" ? decodeSignalResponse(event.data) : Option.none();\n if (Option.isNone(decoded)) {\n this.fail(\"WebRTC signaling message is invalid\");\n return;\n }\n const signal = decoded.value;\n if (signal.type === \"error\") {\n this.fail(signal.error.message);\n return;\n }\n if (signal.type === \"answer\") {\n this.fork(\n Effect.tryPromise(() =>\n this.connection.setRemoteDescription({ type: \"answer\", sdp: signal.sdp }),\n ).pipe(\n // Candidates that arrived before the answer apply once it is set.\n Effect.andThen(\n Effect.suspend(() =>\n Effect.forEach(\n this.pendingCandidates.splice(0),\n (candidate) => Effect.tryPromise(() => this.connection.addIceCandidate(candidate)),\n { discard: true },\n ),\n ),\n ),\n Effect.catch(() => Effect.sync(() => this.fail(\"WebRTC answer is invalid\"))),\n ),\n );\n return;\n }\n if (!this.connection.remoteDescription) {\n this.pendingCandidates.push(signal.candidate);\n return;\n }\n this.fork(\n Effect.tryPromise(() => this.connection.addIceCandidate(signal.candidate)).pipe(\n Effect.catch(() => Effect.sync(() => this.fail(\"WebRTC ICE candidate is invalid\"))),\n ),\n );\n }\n\n private sendOffer(): Effect.Effect<void, LiveSessionError> {\n return Effect.gen({ self: this }, function* () {\n const negotiationFailed = (cause: unknown) => setupError(cause, \"WebRTC negotiation failed\");\n const offer = yield* Effect.tryPromise({\n try: () => this.connection.createOffer(),\n catch: negotiationFailed,\n });\n yield* Effect.tryPromise({\n try: () => this.connection.setLocalDescription(offer),\n catch: negotiationFailed,\n });\n const sdp = this.connection.localDescription?.sdp;\n if (!sdp) {\n return yield* new LiveSessionError({ message: \"WebRTC offer is unavailable\" });\n }\n this.signal.send(JSON.stringify({ version: 1, type: \"offer\", sdp }));\n });\n }\n\n private maybeReady() {\n if (this.snapshotReceived && this.stream && this.streamReady) {\n this.callbacks.ready(this);\n }\n }\n\n private fail(message: string) {\n if (!this.closed) {\n this.callbacks.failed(this, new LiveSessionError({ message }));\n }\n }\n}\n\n// A raster packet is a 4-byte header length, a JSON header, and the JPEG image. Malformed\n// or unreadable packets decode to None.\nfunction decodeRasterFrame(packet: Blob): Effect.Effect<Option.Option<LiveSessionRasterFrame>> {\n return Effect.gen(function* () {\n if (packet.size < 4) {\n return Option.none();\n }\n const prefix = yield* Effect.tryPromise(() => packet.slice(0, 4).arrayBuffer());\n const headerLength = new DataView(prefix).getUint32(0);\n if (headerLength === 0 || headerLength > packet.size - 4) {\n return Option.none();\n }\n const header = decodeRasterFrameHeader(\n yield* Effect.tryPromise(() => packet.slice(4, 4 + headerLength).text()),\n );\n return Option.map(header, (value) => ({\n targetId: value.targetId,\n data: packet.slice(4 + headerLength, packet.size, \"image/jpeg\"),\n width: value.width,\n height: value.height,\n }));\n }).pipe(Effect.orElseSucceed(() => Option.none()));\n}\n\nfunction sessionWebSocketURL(baseUrl: string | undefined, sessionId: string) {\n return webSocketURL(baseUrl, `/sessions/${encodeURIComponent(sessionId)}/session`);\n}\n\nfunction signalWebSocketURL(baseUrl: string | undefined, sessionId: string) {\n return webSocketURL(baseUrl, `/sessions/${encodeURIComponent(sessionId)}/webrtc/signal`);\n}\n\nfunction webSocketURL(baseUrl: string | undefined, path: string) {\n const url = new URL(path, baseUrl ?? window.location.href);\n url.protocol = url.protocol === \"https:\" ? \"wss:\" : \"ws:\";\n return url.toString();\n}\n\nfunction sessionProtocols(credentials: ApiCredentials, sessionToken?: string) {\n const protocols = [LIVE_SESSION_PROTOCOL];\n if (sessionToken) {\n protocols.push(`authorization.bearer.${sessionToken}`);\n } else if (credentials.kind === \"bearer\") {\n protocols.push(`authorization.bearer.${credentials.token}`);\n }\n const tenantId = resolveTenantHeader(credentials, \"tenant-scoped\");\n if (tenantId) {\n protocols.push(`x-aperture-tenant-id.${tenantId}`);\n }\n return protocols;\n}\n\nexport type { LiveSessionConnectionCallbacks, LiveSessionConnectionOptions, LiveSessionSnapshot };\n"],"mappings":"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"}
@@ -0,0 +1,13 @@
1
+ //#region \0rolldown/runtime.js
2
+ var __defProp = Object.defineProperty;
3
+ var __exportAll = (all, no_symbols) => {
4
+ let target = {};
5
+ for (var name in all) __defProp(target, name, {
6
+ get: all[name],
7
+ enumerable: true
8
+ });
9
+ if (!no_symbols) __defProp(target, Symbol.toStringTag, { value: "Module" });
10
+ return target;
11
+ };
12
+ //#endregion
13
+ export { __exportAll as t };
package/package.json ADDED
@@ -0,0 +1,41 @@
1
+ {
2
+ "name": "@aperture-browser/live-session",
3
+ "version": "0.0.0-init.0",
4
+ "description": "Framework-agnostic client for Aperture live sessions: the session protocol, WebRTC and WebSocket transports, and browser input mapping.",
5
+ "homepage": "https://github.com/tarik02/aperture#readme",
6
+ "bugs": "https://github.com/tarik02/aperture/issues",
7
+ "license": "MIT",
8
+ "repository": {
9
+ "type": "git",
10
+ "url": "git+https://github.com/tarik02/aperture.git",
11
+ "directory": "packages/live-session"
12
+ },
13
+ "files": [
14
+ "dist"
15
+ ],
16
+ "type": "module",
17
+ "sideEffects": false,
18
+ "exports": {
19
+ ".": {
20
+ "types": "./dist/index.d.ts",
21
+ "default": "./dist/index.js"
22
+ }
23
+ },
24
+ "publishConfig": {
25
+ "access": "public"
26
+ },
27
+ "dependencies": {
28
+ "@aperture-browser/api-client": "0.0.0-init.0"
29
+ },
30
+ "devDependencies": {
31
+ "effect": "4.0.0-rc.117",
32
+ "vite-plus": "0.2.4"
33
+ },
34
+ "peerDependencies": {
35
+ "effect": "^4.0.0-rc.117"
36
+ },
37
+ "scripts": {
38
+ "build": "vp pack",
39
+ "typecheck": "tsgo --noEmit"
40
+ }
41
+ }