Something went wrong. Try again.
Monorepo for the nibling.run platform
Something went wrong. Try again.
123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566// The WebSocket shim tag, put into guest app documents so it runs before any app// script: as the first child of <head>, or before the first tag when there is no// <head> tag (the parser then opens head for it). Comments, doctypes and the contents// of script and style elements are skipped while looking. The document's bytes are// otherwise untouched; the scan reads them as latin1, one character per byte, so any// ASCII-compatible charset survives.import { WS_SHIM_PATH } from "../shared/vurls";
const TAG = new TextEncoder().encode(`<script src="${WS_SHIM_PATH}"></script>`);const RAW_TEXT = new Set(["script", "style"]);
/** Where the shim tag goes in `html`. */export function shimOffset(html: string): number { let firstTag = -1; let at = 0; while ((at = html.indexOf("<", at)) !== -1) { if (html.startsWith("<!--", at)) { const end = html.indexOf("-->", at + 4); if (end === -1) break; at = end + 3; continue; } const m = /^<\/?([A-Za-z][^\s/>]*)/.exec(html.slice(at, at + 64)); if (!m) { // <!doctype ...>, <?...>, or a stray "<" in text. at += 1; continue; } const close = html.indexOf(">", at); if (close === -1) break; if (firstTag === -1) firstTag = at; const name = m[1]!.toLowerCase(); const isEnd = html[at + 1] === "/"; if (!isEnd && name === "head") return close + 1; if (!isEnd && RAW_TEXT.has(name)) { const end = html.toLowerCase().indexOf(`</${name}`, close); at = end === -1 ? html.length : end; continue; } at = close + 1; } return firstTag === -1 ? html.length : firstTag;}
export function injectShim(body: Uint8Array): Uint8Array { const at = shimOffset(new TextDecoder("latin1").decode(body)); const out = new Uint8Array(body.length + TAG.length); out.set(body.subarray(0, at)); out.set(TAG, at); out.set(body.subarray(at), at + TAG.length); return out;}
/** The HTML patterns of the MIME Sniffing standard's rules for an unknown type: a body * with no content-type that starts like this is rendered as HTML. */const SNIFFED_HTML = /^[\t\n\f\r ]*<(?:!doctype html|html|head|script|iframe|h1|div|font|table|a|style|title|b|body|br|p|!--)[ >]/i;
/** Only a document runs scripts, and only an uncompressed HTML body can be edited. */export function wantsShim(mode: RequestMode, headers: Headers, body: Uint8Array): boolean { const encoding = headers.get("content-encoding"); if (mode !== "navigate" || (encoding !== null && encoding.toLowerCase() !== "identity")) return false; const type = headers.get("content-type"); if (type !== null) return /^text\/html\b/i.test(type); return SNIFFED_HTML.test(new TextDecoder("latin1").decode(body.subarray(0, 512)));}