perf(sse+tasks): индекс SSE-соединений, getTaskTree на recursive CTE, батчи N+1
Шаги 1.4 и 1.5 плана production-готовности: - SseConnectionIndex (byOrg/byUser), один heartbeat-таймер, протокол SSE не тронут - getTaskTree/getTaskParentChain: WITH RECURSIVE CTE (было 1+2N запросов) - sync initial/delta: Promise.all по формам - embedding queue/reindex: батч-предзагрузки вместо поштучных запросов - 8 новых тестов (96/96)
This commit is contained in:
@@ -4900,14 +4900,11 @@ To block task creation from task.before_create, set: ctx.result = { allow: false
|
||||
};
|
||||
};
|
||||
|
||||
// Цепочка родителей вверх по parentTaskId (с защитой от циклов)
|
||||
// Цепочка родителей вверх по parentTaskId (ближайший первым, до 10 уровней,
|
||||
// один recursive CTE вместо последовательных getTask на каждый уровень)
|
||||
const parentChain = await storage.getTaskParentChain(taskId, organizationId, 10);
|
||||
const parents: Array<Record<string, unknown>> = [];
|
||||
const seen = new Set<number>([task.id]);
|
||||
let cursor = task.parentTaskId ?? null;
|
||||
while (cursor !== null && !seen.has(cursor) && parents.length < 10) {
|
||||
seen.add(cursor);
|
||||
const parent = await storage.getTask(cursor, organizationId);
|
||||
if (!parent) break;
|
||||
for (const parent of parentChain) {
|
||||
if (isFormAllowed(parent.formId)) {
|
||||
parents.push({
|
||||
id: parent.id,
|
||||
@@ -4917,7 +4914,6 @@ To block task creation from task.before_create, set: ctx.result = { allow: false
|
||||
isCompleted: parent.isCompleted,
|
||||
});
|
||||
}
|
||||
cursor = parent.parentTaskId ?? null;
|
||||
}
|
||||
|
||||
return {
|
||||
|
||||
Reference in New Issue
Block a user