// isolator/worker.ts // No module cache to ensure fresh code for every execution. const States = Object.freeze({ SUCCESS: "SUCCESS", NOT_A_FUNCTION: "NOT_A_FUNCTION", SCRIPT_ERROR: "ERROR", }); self.onmessage = async (e) => { const { code, request, environment, name } = e.data; const logs: any[] = []; const startTime = performance.now(); // Temporarily override console.log and console.error to capture logs const oldConsoleLog = console.log; const oldConsoleError = console.error; console.log = (...args) => { logs.push(args); oldConsoleLog.apply(console, args); }; console.error = (...args) => { logs.push(args); oldConsoleError.apply(console, args); }; try { // Make the environment object and response helpers available globally. (self as any).environment = environment; (self as any).FUNCTION_NAME = name; (self as any).Response = (body = "", headers = {}, status = 200) => ({ body, status, headers, }); (self as any).JsonResponse = (body = {}, headers = {}, status = 200) => (self as any).Response( JSON.stringify(body), { "Content-Type": "application/json", ...headers }, status ); (self as any).HtmlResponse = (body = "", headers = {}, status = 200) => (self as any).Response( body, { "Content-Type": "text/html", ...headers }, status ); (self as any).TextResponse = (body = "", headers = {}, status = 200) => (self as any).Response( body, { "Content-Type": "text/plain", ...headers }, status ); // Use a data URL to import the user's code as a fresh ES module on every execution. const dataUrl = `data:text/javascript;base64,${btoa( unescape(encodeURIComponent(code)) )}`; const userModule = await import(dataUrl); if (typeof userModule.default !== "function") { throw new Error( "Module does not have a default export or the export is not a function." ); } const userFn = userModule.default; const result = await userFn(request); const executionTime = performance.now() - startTime; self.postMessage({ status: States.SUCCESS, result, logs, environment: (self as any).environment, // Return the mutated environment. execution_time: executionTime, }); } catch (err) { const executionTime = performance.now() - startTime; self.postMessage({ status: States.SCRIPT_ERROR, result: { name: err.name, message: err.message, stack: err.stack, }, logs, environment, execution_time: executionTime, }); } finally { // Restore original console functions console.log = oldConsoleLog; console.error = oldConsoleError; } };