* Fake worker speaking the same {load-grammars → grammars-loaded} / * {parse → parse-result} protocol as the real parse-worker. `behavior` decides * per parse whether to return a result, crash (exit≠0), hang (never reply — * exercises the timeout), or wait on a promise (hold a parse in-flight to
| 28 | * wired its listeners first. |
| 29 | */ |
| 30 | class FakeWorker implements ParsePoolWorker { |
| 31 | private msgCb?: (m: unknown) => void; |
| 32 | private exitCb?: (code: number) => void; |
| 33 | alive = true; |
| 34 | constructor(private behavior: (m: ParseMsg) => Action, private onTerminate?: () => void) {} |
| 35 | on(event: string, cb: (...args: any[]) => void): void { |
| 36 | if (event === 'message') this.msgCb = cb; |
| 37 | else if (event === 'exit') this.exitCb = cb; |
| 38 | // 'error' unused by the fakes |
| 39 | } |
| 40 | private reply(id: number, result: ExtractionResult): void { |
| 41 | if (this.alive) this.msgCb?.({ type: 'parse-result', id, result }); |
| 42 | } |
| 43 | postMessage(msg: unknown): void { |
| 44 | const m = msg as { type: string } & Partial<ParseMsg>; |
| 45 | if (m.type === 'load-grammars') { |
| 46 | setTimeout(() => { if (this.alive) this.msgCb?.({ type: 'grammars-loaded' }); }, 0); |
| 47 | return; |
| 48 | } |
| 49 | if (m.type !== 'parse') return; |
| 50 | const action = this.behavior(m as ParseMsg); |
| 51 | if ('crash' in action) { |
| 52 | this.alive = false; |
| 53 | setTimeout(() => this.exitCb?.(1), 0); // simulate a WASM-OOM exit(1) |
| 54 | return; |
| 55 | } |
| 56 | if ('hang' in action) return; // never reply → timeout path |
| 57 | if ('wait' in action) { void action.wait.then((r) => this.reply(m.id!, r)); return; } |
| 58 | setTimeout(() => this.reply(m.id!, action.result), 0); |
| 59 | } |
| 60 | terminate(): Promise<number> { this.alive = false; this.onTerminate?.(); return Promise.resolve(0); } |
| 61 | } |
| 62 | |
| 63 | const task = (filePath: string, content = 'code'): ParseTask => ({ filePath, content, language: 'typescript' as Language }); |
| 64 | const result = (tag = 0): ExtractionResult => ({ nodes: [], edges: [], unresolvedReferences: [], errors: [], durationMs: tag }); |
nothing calls this directly
no outgoing calls
no test coverage detected