Files
Aislo/resources/tester/helper_298_3_finishdrop_loop.cjs
T
eomsangdonandClaude Opus 5.5 fcb3c994b3 fix(498-1 렌더러 멈춤): 밀린 버림 차례가 같은 기록을 되받는 finishDrop 고리 그침 — 요구 298-3
- design_pipeline_page finishDrop — lastRun 이 이미 끝난 같은 기록을 돌려주면 다시 부르지 않고 그 기록으로 마침(마이크로태스크 고리 · 렌더러 메모리 4.7 GB 뒤 죽음)
- 시험 test_298_3_finishdrop_loop(finishDrop 본문을 떼어 같은 기록 되받기 → 한 번만 · 고치기 전 51 번)

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-10-20 22:49:19 +09:00

64 lines
2.3 KiB
JavaScript

/* 298-3 노선 [저장] 뒤 렌더러 멈춤 단위검증 헬퍼 — `design_pipeline_page.ts` 의 `finishDrop` 본문을
* 그대로 떼어 트랜스파일 · 둘레 칸은 가짜. 밀린 버림 기록(dropped · 옛 차례)을 넘기고 lastRun 이 같은 기록을
* 되돌려 줄 때 finishDrop 이 몇 번 불리는지 · 끝나는지. 결과 JSON 을 stdout 으로.
*/
const fs = require("fs");
const path = require("path");
const ts = require(path.join(__dirname, "..", "..", "config", "node_modules", "typescript"));
const ROOT = path.join(__dirname, "..", "..");
const code = fs.readFileSync(
path.join(ROOT, "A00_Common", "design", "design_pipeline_page.ts"),
"utf8",
);
const begin = code.indexOf("const finishDrop = async");
const end = code.indexOf("\n };", begin) + 5;
if (begin < 0 || end < begin) throw new Error("finishDrop 못 찾음");
const body = code
.slice(begin, end)
.replace("const finishDrop = async", "const finishDropInner = async");
const harness = `
let calls = 0;
const finishDrop = (record: any): Promise<string> => {
calls += 1;
if (calls > 50) return Promise.reject(new Error("loop"));
return finishDropInner(record);
};
${body}
return { finishDrop, calls: () => calls };
`;
const js = ts
.transpileModule(`(function () {${harness}})`, {
compilerOptions: { target: ts.ScriptTarget.ES2022 },
})
.outputText.replace(/^"use strict";/, "");
const record = { outcome: "dropped", generation: 3 };
const pipe = { generation: 5, input: () => null, output: () => null };
let released = 0;
const scope = {
pipe,
dropPending: true,
lastRun: Promise.resolve(record), // 이미 끝난 같은 차례 기록
pageSaved: { canonRouteId: () => 7, adoptCanon() {} },
held: null,
options: {},
heldSectionDetail: () => null,
stationDiff: () => null,
adoptAfterDrop() {},
publisher: { shown: async () => undefined },
releaseWhenQuiet: async () => void (released += 1),
};
const names = Object.keys(scope);
const make = new Function(
"scope",
`let { ${names.join(", ")} } = scope;\nreturn ${js.trim().replace(/;$/, "")}();`,
);
const { finishDrop, calls } = make(scope);
finishDrop(record).then(
(why) => console.log(JSON.stringify({ calls: calls(), why, released, record })),
(error) => console.log(JSON.stringify({ calls: calls(), error: String(error), released })),
);