1/** Standalone Node preload written outside packaged application archives. */
2export const progressPreloadSource = String.raw`
3const modules = require("node:module");
4const { connect } = require("node:net");
5const { fstatSync } = require("node:fs");
6const { basename } = require("node:path");
7const { randomUUID } = require("node:crypto");
8
9const endpoint = /^127\.0\.0\.1:(\d+)$/.exec(process.env.T3_SCRIPT_PROGRESS_ENDPOINT ?? "");
10const token = process.env.T3_SCRIPT_PROGRESS_TOKEN;
11const key = Symbol.for("t3.script-progress.observe");
12if (endpoint && token && typeof modules.registerHooks === "function" && !globalThis[key]) {
13 const port = Number(endpoint[1]);
14 if (port > 0 && port <= 65535) {
15 try { install(port, token); } catch {}
16 }
17}
18
19function install(port, token) {
20 const producerId = randomUUID();
21 const roots = new Map();
22 const observed = new WeakSet();
23 let nextId = 0;
24 let socket;
25 let connected = false;
26 let retry;
27 let queue = [];
28 let queuedBytes = 0;
29 let exiting = false;
30 let flushed = false;
31 const limit = 1024 * 1024;
32
33 function send(record) {
34 try {
35 const line = JSON.stringify(record) + "\n";
36 if (Buffer.byteLength(line) > limit) return;
37 if (connected && socket) {
38 if (socket.writableLength + Buffer.byteLength(line) <= limit) socket.write(line);
39 else socket.destroy();
40 } else if (queuedBytes + Buffer.byteLength(line) <= limit) {
41 queue.push(line);
42 queuedBytes += Buffer.byteLength(line);
43 } else {
44 socket?.destroy();
45 }
46 } catch {}
47 }
48
49 async function read(root, state) {
50 try {
51 // The server coalesces updates; capture must not add a script-side timer.
52 // Observing an error must not consume the emitter's unhandled-error throw.
53 const source = {
54 get active() { return root.active; },
55 delay: root.delay,
56 now: root.now,
57 on(channel, callback) {
58 return channel === "error"
59 ? root.onAny((event, args) => { if (event === "error") callback(...args); })
60 : root.on(channel, callback);
61 },
62 onAny: root.onAny.bind(root),
63 };
64 const reader = state.encode(source, { throttleMs: -Infinity }).getReader();
65 state.reader = reader;
66 while (state.reader === reader) {
67 const { done, value } = await reader.read();
68 if (state.reader !== reader) break;
69 if (done) {
70 roots.delete(root);
71 break;
72 }
73 send({ type: "progress", streamId: state.id, event: value });
74 }
75 } catch {}
76 }
77
78 function open() {
79 if (exiting) return;
80 retry = undefined;
81 const connection = connect({ host: "127.0.0.1", port });
82 socket = connection;
83 connection.unref();
84 connection.on("error", () => {});
85 connection.on("connect", () => {
86 connected = true;
87 connection.write(JSON.stringify({
88 type: "hello", token, producerId, pid: process.pid,
89 label: process.argv[1] ? basename(process.argv[1]) : undefined,
90 }) + "\n");
91 for (const line of queue) connection.write(line);
92 queue = [];
93 queuedBytes = 0;
94 for (const [root, state] of roots) if (!state.reader) void read(root, state);
95 });
96 connection.on("close", () => {
97 if (socket !== connection) return;
98 socket = undefined;
99 connected = false;
100 queue = [];
101 queuedBytes = 0;
102 for (const state of roots.values()) {
103 const reader = state.reader;
104 state.reader = undefined;
105 void reader?.cancel().catch(() => {});
106 }
107 if (!exiting && roots.size) {
108 retry = setTimeout(open, 500);
109 retry.unref();
110 }
111 });
112 }
113
114 Object.defineProperty(globalThis, key, { value(Root, encode, forwardedRoot) {
115 if (typeof Root?.prototype?.start !== "function" || typeof Root.prototype.onAny !== "function" || typeof encode !== "function") return;
116 let forwarded = false;
117 const [fd, parent] = (process.env.CLOVER_PROGRESS ?? "").split(":").map(Number);
118 if (forwardedRoot && parent === process.ppid && fd > 2) {
119 try { forwarded = fstatSync(fd).isFIFO() || fstatSync(fd).isSocket(); } catch {}
120 }
121 const start = Root.prototype.start;
122 Root.prototype.start = function (...args) {
123 if (!(forwarded && this === forwardedRoot) && !observed.has(this)) {
124 observed.add(this);
125 try {
126 const state = { id: String(++nextId), encode };
127 roots.set(this, state);
128 void read(this, state);
129 const off = this.onAny((channel, args) => {
130 if (channel !== "end" && channel !== "error") return;
131 const reader = state.reader;
132 state.reader = undefined;
133 roots.delete(this);
134 try {
135 send({ type: "progress", streamId: state.id, event: [0,
136 channel === "error" ? ["error", String(args[0])] : ["end", args[0] ?? null],
137 ] });
138 } catch {}
139 queueMicrotask(() => { off(); void reader?.cancel().catch(() => {}); });
140 });
141 if (!socket && !retry) open();
142 } catch {}
143 }
144 return start.apply(this, args);
145 };
146 }});
147
148 modules.registerHooks({ load(url, context, nextLoad) {
149 const loaded = nextLoad(url, context);
150 if (!/\/progress\.(?:[cm]?js|ts)(?:\?|$)/.test(url) || !loaded.source) return loaded;
151 const source = typeof loaded.source === "string" ? loaded.source : Buffer.from(loaded.source).toString("utf8");
152 if (!/export\s+class\s+Root\b/.test(source) || !/export\s+function\s+encodeEventStream\b/.test(source)) return loaded;
153 return { ...loaded, source: source + "\n;try { globalThis[Symbol.for('t3.script-progress.observe')]?.(Root, encodeEventStream, typeof tryAttachToParent === 'function' ? global : null); } catch {}\n" };
154 }});
155
156 process.on("beforeExit", () => {
157 if (flushed || !socket) return;
158 flushed = true;
159 exiting = true;
160 clearTimeout(retry);
161 const connection = socket;
162 connection.ref();
163 const deadline = setTimeout(() => connection.destroy(), 100);
164 connection.once("close", () => clearTimeout(deadline));
165 if (connected) connection.end();
166 else connection.once("connect", () => connection.end());
167 });
168}
169`;