diff --git a/src/client.ts b/src/client.ts index 7c24aaf..fb7af99 100644 --- a/src/client.ts +++ b/src/client.ts @@ -1,5 +1,5 @@ -import { BareHeaders, BareTransport, maxRedirects } from './baretypes'; -import { WorkerConnection, WorkerMessage, WorkerResponse } from './connection'; +import { BareHeaders, maxRedirects } from './baretypes'; +import { WorkerConnection, WorkerMessage } from './connection'; import { WebSocketFields } from './snapshot'; const validChars = @@ -17,12 +17,6 @@ export function validProtocol(protocol: string): boolean { return true; } -// get the unhooked value -const getRealReadyState = Object.getOwnPropertyDescriptor( - WebSocket.prototype, - 'readyState' -)!.get!; - const wsProtocols = ['ws:', 'wss:']; const statusEmpty = [101, 204, 205, 304]; const statusRedirect = [301, 302, 303, 307, 308]; @@ -238,7 +232,7 @@ export class BareClient { } }; - const onclose = (code, reason) => { + const onclose = (code: number, reason: string) => { fakeReadyState = WebSocketFields.CLOSED; socket.dispatchEvent(new CloseEvent("close", { code, reason })); }; diff --git a/src/connection.ts b/src/connection.ts index efa71b9..b3fcc60 100644 --- a/src/connection.ts +++ b/src/connection.ts @@ -8,7 +8,7 @@ export type WorkerMessage = { remote: string, method: string, headers: BareHeaders, - body: ReadableStream | undefined, + body: ReadableStream | ArrayBuffer | undefined, } websocket?: { url: string, @@ -96,6 +96,25 @@ function createPort(path: string, registerHandlers: boolean): MessagePort { return worker.port; } +let browserSupportsTransferringStreamsCache: boolean | null = null; +export function browserSupportsTransferringStreams(): boolean { + if (browserSupportsTransferringStreamsCache === null) { + const chan = new MessageChannel(); + const stream = new ReadableStream(); + let res: boolean; + try { + chan.port1.postMessage(stream, [stream]); + res = true; + } catch(err) { + res = false; + } + browserSupportsTransferringStreamsCache = res; + return res; + } else { + return browserSupportsTransferringStreamsCache; + } +} + export class WorkerConnection { channel: BroadcastChannel; port: MessagePort | Promise; diff --git a/src/worker.ts b/src/worker.ts index 70ddc31..566276f 100644 --- a/src/worker.ts +++ b/src/worker.ts @@ -1,5 +1,5 @@ import { BareTransport } from "./baretypes"; -import { BroadcastMessage, WorkerMessage, WorkerResponse } from "./connection" +import { BroadcastMessage, WorkerMessage, WorkerResponse, browserSupportsTransferringStreams } from "./connection" let currentTransport: BareTransport | null = null; let currentTransportName: string = ""; @@ -51,6 +51,11 @@ function handleConnection(port: MessagePort) { null ); + if (!browserSupportsTransferringStreams() && resp.body instanceof ReadableStream) { + const conversionResp = new Response(resp.body); + resp.body = await conversionResp.arrayBuffer(); + } + if (resp.body instanceof ReadableStream || resp.body instanceof ArrayBuffer) { port.postMessage({ type: "fetch", fetch: resp }, [resp.body]); } else {