fix: поиск по подресурсам + реальный per-call таймаут ЛЛМ

search(resourceBaseSegment): суффиксы-подресурсы перебираются по убыванию
длины (KNOWN_RESOURCE_SUBS). Иначе "_user" матчился раньше "_sub_user" и
nubes_s3_sub_user давал "s3_sub" вместо "s3" — страница ресурса не находилась.

assist(llmChat): реально применяет ASSIST_LLM_TIMEOUT_MS — таймаут ОДНОГО
вызова (покрывает и чтение тела ответа). Таймаут возвращает отдельный код
llm_timeout, отмена вызывающим (дедлайн/закрытие соединения) — по-прежнему
aborted, чтобы stage2 различал причины.

stage1: убран дублирующий AbortController (таймаут теперь только в llmChat).

orchestrator: llm_timeout -> HTTP 504.
This commit is contained in:
Repinoid
2026-10-12 07:51:48 +03:00
parent 5ab9274015
commit 12d29ee98d
4 changed files with 139 additions and 100 deletions
+19 -8
View File
@@ -190,6 +190,22 @@ function pageKind(seg) {
return "resource";
}
/**
* Суффиксы-подресурсы в именах `nubes_*`, по которым отрезается хвост до
* базового ресурса (например, `nubes_postgres_database` → `postgres`).
*
* ⚠️ Порядок перебора критичен: суффиксы идут по УБЫВАНИЮ длины, поэтому
* сортируем массив один раз при загрузке модуля. Иначе короткий `_user`
* затеняет более длинный `_sub_user`: для `nubes_s3_sub_user` (rest =
* "s3_sub_user") отрезался бы `_user`, и получалось "s3_sub" вместо "s3",
* из-за чего страница ресурса не находилась (`isResourcePage`).
*/
const KNOWN_RESOURCE_SUBS = [
"_database", "_user", "_topic", "_backup", "_snat", "_record",
"_sub_user", "_ip_allocation", "_vdc", "_kv", "_policy", "_secrets",
"_team", "_redeploy", "_group",
].sort((a, b) => b.length - a.length);
/**
* Преобразует имя ресурса nubes_<база>_<подресурс> в базовое имя страницы
* (<база>). Для `nubes_postgres_database` → `postgres`; `nubes_postgres` → `postgres`.
@@ -201,15 +217,10 @@ function resourceBaseSegment(resourceType) {
if (!resourceType || !resourceType.startsWith("nubes_")) return null;
const rest = resourceType.slice("nubes_".length);
if (!rest) return null;
// Известные подресурсы (суффиксы) — отрезаем до базового ресурса.
// Берём первую часть до суффикса-подресурса, если составное имя содержит известный подресурс.
const knownSubs = [
"_database", "_user", "_topic", "_backup", "_snat", "_record",
"_sub_user", "_ip_allocation", "_vdc", "_kv", "_policy", "_secrets",
"_team", "_redeploy", "_group",
];
// Известные суффиксы-подресурсы; перебор идёт от самого длинного к самому
// короткому (порядок задан в KNOWN_RESOURCE_SUBS, см. определение выше).
let base = rest;
for (const sub of knownSubs) {
for (const sub of KNOWN_RESOURCE_SUBS) {
if (rest.endsWith(sub)) {
base = rest.slice(0, rest.length - sub.length);
break;