Files
MikrotikManager/docs/ux-ui-remaining-acceptance.md
T

290 KiB
Raw Blame History

Оставшаяся внешняя приёмка — 2026-10-12

Это актуальная матрица после 12.5.183. Исторические записи сохраняют версии и ограничения на момент выполнения; поздние проверки ниже уточняют их. Этап 12.5 открыт. Успех в двух CHR и одном backend не означает приёмку всех конфигураций, интеграций или полной регрессии.

Стенд: Debian13/Compose, PostgreSQL18.6, два CHR RouterOS7.24.5. Backend ux-warning183, frontend ux-warning183; production lab использует AUTH_REQUIRED=false. Подписанные JWT/RBAC проверялись в изолированных процессах. Все собственные объекты112 удалены, исходные13 коллекций×2 (включая logging/certificates/files/routes) проверены; пароли не менялись.

Раздел Подтверждено Осталось / условие завершения
PostgreSQL Bootstrap, backup/restore, SQL rollback, concurrency, writer drain одного экземпляра, JWT guards и unknown commit: блоки14–24 Несколько backend/worker экземпляров и координация всех writers; физическая потеря соединения отличается от введённого отказа подтверждения
Speed/uptime TCP transmit/receive/both32–33, короткий UDP34, auth failure25, transport timeout27, интерфейс after-ping28–29, snapshot/history race23–24 Busy/abort/physical WAN disconnect; HTTP receipt socket disconnect принят97; независимое доказательство multi-WAN source/path; Home→JH/JH↔Exit с асимметричными каналами ; ROS-10 POST/SQL/GET и три часовых пояса приняты96. Короткие тесты не доказывают maximum throughput
Outbox Production PG claim/dedupe/settlement/retry/JWT/browser checkpoint/a11y35–49 Настоящий Telegram API/чат, физический timeout после возможной отправки, несколько sender процессов. Нужны тестовый бот/чат и прямое разрешение на конкретное сообщение; подменённый ответ не доказывает доставку
GRE Native lifecycle, metadata, live формы/меню/URL/Ping53–57; GRE используется в OSPF/BGP/IPsec последующих блоков; native IPv6 ULA inner109; application static IPv6 lifecycle151 IPv6 outer, from-pool/EUI-64, независимые WAN, масштаб и длительное восстановление; принятие GRE не означает приёмку всех сценариев автоматического расписания
WireGuard Native handshake/data plane58, deletion60, live create/peer/disable/enable/delete62, mobile64, export/import67–74; native IPv6 ULA inner/allowedIps/handshake109; application static IPv6 lifecycle152 Клиентские ОС и произвольные конфигурации, IPv6 outer/scale, from-pool/EUI-64 и multiple-address import/export, физический lost ACK и устойчивое восстановление; .conf с placeholders — шаблон, не принятый клиентский tunnel
VXLAN Собственная пара/private Ping/catalog/URL/export75–76; bridge/FDB/port loss/recovery107; IPv6 ULA inner по IPv4 outer108 API приложения read-only: create/delete проверены native. IPv6 outer, масштаб/производительность, профильные mutation RBAC/concurrency отдельно не приняты
IPsec PSK и сертификатное шифрование77–82, active peer/online/mode-config, scoped NAT/group, partial/unknown/applied receipts, restore conflicts, JWT; full DN/специальные символы/online110; literal CN namespace guards и explicit FQDN111; certificate/PSK shared ID unknown/recovery112; multiple sessions controlled snapshots113; shared certificate rows/target guards114; preserve-certificate UI/native DELETE115; explicit deletion binding/PSK collision116; legacy export binding118; real duplicate DN sessions/Linux Ping/UI119; DN DER/ASCII tag и FQDN SAN native120; implicit unique DNS SAN/mixed IDs/API/UI121; короткий CHILD/IKE rekey/reconnect122; server pin и unbound same-CA certificate refusal123; own RSA Root/Intermediate/client chain/CRLs/IKE/reauth138; external revoked CRL new-handshake refusal/existing-session boundary137; certificate-bound malformed/signed expired CRL IKE refusal/recovery136; certificate-bound missing-CDP404/IKE refusal and recovery135; external HTTP CRL download/404/cache preservation134; isolated diagnostic buffers132; own ECDSA P-256/Ping/API export131 and final18×2 inventory; isolated same-key/CA time boundary with explicit AUTH_FAILED130; valid-renewal control timeout/clock/log observation129; original/renewed controls and time-invalid timeout observation128; CRL-issued cert/CA no-write delete guards127; own CRL-enabled valid/revoked control126; local revoked flag/CRL-disabled reconnect observation125; certificate reauth/CHILD absence boundary/UI124 Реальные duplicate certificate-derived DN sessions приняты119; arbitrary custom PKI/OIDs/policies/path-length and missing/intermediate-revoked chain; native intermediate chain accepted138; ECDSA P-256 accepted131;128/129 timeout cause still unknown,130 time boundary accepted; periodic refresh; existing IKE survives short external-revocation observation137, automatic termination not guaranteed; direct CHR-to-CHR CRL HTTP failure cause134; reauth/CHILD loss принят124; длительный rekey/переходная потеря пакетов; прочие ID типы/ADDR4/manual DN/custom PKI; native edit identical matching rules rejected; клиентские Windows/macOS/iOS/Android, прочие DN форматы/custom OIDs/IKE ID namespaces, полная PKI и policy/profile/proposal restore, физический disconnect, durable retry/multi-instance, IPv6/maximum throughput
OSPF/BFD Real Full/own routes84–85, раздельные наблюдения BFD86, effective disabled/optimizer cost/partial/RBAC87, alternate path90 и CIDR91; basic native OSPFv3/API/UI154 (harness timeout отдельно), OSPFv3/BFDv6 loss/recovery/API/UI159 BFD-only sustained route gate не гарантирован:153 подтвердил поздние Full/active при BFD Down в30s samples, UI предупреждение/recovery принято. В90 переходный Ping18/40 с55% loss: бесшовность не принята. REST timing — наблюдаемая граница, не SLA; basic BFDv6 принят159; IPv6 outer/WAN/scale/independent WAN открыты
BGP Established83, exact /32 exchange/API/UI/administrative withdrawal92, BFD primary GRE loss/alternate/recovery93; basic native IPv6 eBGP/AFI/NLRI/Ping/withdrawal/API/UI155; native IPv6 BGP/BFD scoped withdrawal/recovery160; private4-byte ASN/as4/API/UI162 Hold timer/TCP loss безBFD принят104; packet loss в переходе, разные внешние peers/WAN policy, basic BFDv6 принят160; IPv6 outer/public WAN/scale. Два логических пути используют тот же public WAN; physical redundancy не принята
Recursive routes Production PUT/change/own history restore88, disabled guards, partial/unknown/applied outcomes, live формы/контекст Автоматический rollback/retry, durable receipts и несколько экземпляров отсутствуют; PUT не является idempotent noop. Полная произвольная legacy catalog миграция не принята
Diagnostics/terminal Allowlist/native reads, Ping/trace/route/MTU/DNS, actual avg-rtt, disabled guards, JWT/live PC/mobile89; real default memory tail/log limits/API/UI133 DNS использует backend resolver; MTU — ограниченная оценка, не гарантированный максимум. Stop ожидания не доказывает остановку RouterOS команды; arbitrary CLI и physical disconnect не приняты
Portal/интеграции Локальные и isolated JWT guards; UI/API error states в границах журналов Настоящий Portal issuer/login/отзыв прав; RIPE SDK two-IP/no-fetch passed140, native IPv6 ULA flow pipeline passed145 (IPv4 transport), public IPv6 WAN/local licensed MaxMind/S3/container/certificate jobs и Gitea delivery требуют отдельных тестовых endpoints/аккаунтов. Не отправлять сообщения и не публиковать релиз без соответствующего поручения
Общая приёмка Локальная12.3.83; UI1244/context221/compiled984 parity139; профильные build/E2E/live проверки последующих блоков Traffic initial live mock-id gate passed141; IPv6 special ranges/cache passed142; unknown RIPE coordinates passed143; IPv6 synthetic UDP/worker/SQL passed144; native CHR ULA/IPFIX/API/UI passed145; ICMPv6/IPv6 endpoint labels passed146; HTTP DTO validation passed147; scoped flow catalog/serverId guards passed148; strict monthly calendar passed149; Sessions labels passed150; application GRE static IPv6 lifecycle151 passed; WireGuard static IPv6 lifecycle152 и disabled SQL/API gates passed; OSPF/BFD boundary/warning153 passed; OSPFv3 routes154 accepted in recorded bounds; BGP IPv6 basic155 passed; bigint ID/SQL guards156 passed; общая UI1260/context221/backend24 regression157 passed; IPv6 BFD correlation158 profile/deployed passed; native OSPFv3/BFDv6 boundary/recovery159 passed; BGP IPv6/BFD withdrawal/recovery160 passed; selected BGP/alert unknown guards161 replay/profiles/deployed passed (SQL stability skipped); private4-byte ASN162 native/API/UI passed; duplicate BGP alert keys163 replay/profiles/deployed passed; nullable selected BGP164 replay/profiles/API/UI passed; collector165 parallel/current guards/read-only PG passed; positive partial/error SQL166/full24 with PG passed (optional network SQL not repeated); GRE/BGP freshness167/SQL8 passed; other source audit168 выявил identity/disabled/freshness gaps; локальный server/traffic identity guard169 passed без SQL/deploy, source/per-probe/freshness170/ownSQL16/compiled1008/deployed passed; source diagnostics171/42E2E/ownSQL metadata/live2 passed; monitoring history172/ownSQL26/compiled1020/deployed passed; Ping known/error173/ownHTTP-SQL8/85uniqueE2E/native4/4/deployed passed; traffic confidence174 baseline reproduced/local guard passed; owned SQL9/9358ms/deploy175/1024compiled/live smoke passed; legacy history/provenance open; compound RTT176 local/native replay2 passed, SQL10/deploy177/1024compiled/live smoke passed; history178/legacy provenance/current TTL/manual truth/SQL9+14/35unique E2E/native GET/deployed passed; live179 complete/disable-config/bounded fallback/ownSQL10/nativeSSE2/liveUI2 passed; volume180 exact/unit marker/ownSQL6/18E2E/API/liveUI/deployed passed; binding status181 native/ownSQL9/8E2E/deployed passed; peer atomicity182 ownSQL3/native/API/UI passed; peer failure warning183 ownSQL2/4E2E/deployed passed; history coverage184 next; последующие изменения проверять отдельно; scoped axe не означает полную WCAG сертификацию

Доказательства и точные ограничения: полная история этапа12, внешний протокол, BGP93, паспорт стенда. Невыполненные пункты не являются все блокерами данного лабораторного сценария: для выпуска необходимо явно определить требуемые конфигурации и принять их либо согласовать ограничение.

Следующая последовательность

  1. 12.5.95 завершён: source/context/compiled audit, production source drift не выявлен; нормализация и исключения явно указаны.
  2. 12.5.96 timezone завершён: 6 live UI cases. 97 HTTP receipt disconnect принят: протокол. 98 сообщение неизвестного native результата исправлено/развёрнуто. 99 main/context завершён с точной записью одного failure/delta;100 transport и101 accessibility исправлены/развёрнуты.102 malformed PATCH исправлен/принят.103 packet rows/public/GRE приняты в границах коротких samples; initial loss/root cause остаётся открытым.104 hold/TCP loss/recovery принят.105 source/runtime/evidence сверка passed.106 read-only readiness: auth disabled/Portal localhost/bot and chat unconfigured.107 — native bridge/FDB/loss/recovery принят.108 — IPv6 inner VXLAN принят, initial0/3 и1/3 остаются в протоколе;109 — native GRE/WireGuard IPv6 inner принят; readers /ip/address не показывают native IPv6 interface addresses.110 — полный native DN/online исправлен и принят;111 — literal CN guards/real explicit FQDN accepted;112 — certificate/PSK alias ambiguity marked unknown/recovery accepted;113 — repeated native ID groups исправлены на controlled snapshots; 114 — multiple refs/target guards/native conflict приняты в описанных границах. 115 — UI сохранения сертификата/native DELETE принят; 116 — name-based guessing удалён/live PSK collision принят;117 — main1243/1failed+delta1/context221/source runtime приняты в точных границах; 118 — legacy export binding/native409/explicit200 принят;119 — real certificate-derived DN/Linux sessions приняты; следующий120 — manual ID interop/encoding. Реальные интеграции требуют тестовых доступов и отдельного разрешения на сообщение.
  3. Заключительный профильный контроль: после последнего исправления собрать только затронутую часть, проверить её live и обновить матрицу. Общую регрессию выполнить один раз на согласованном runtime.
  4. Внешние зависимости: Telegram/Portal/client OS/multi-WAN/scale проходят отдельную приёмку при наличии нужных аккаунтов, устройств и разрешений. Лабораторный результат двух CHR не закрывает их автоматически.

Каждый блок: конкретный результат → профильные проверки → независимая сверка cleanup → датированная запись → локальный коммит без push. Не повторять уже принятые сценарии без изменения исходников или нового выявленного риска.

12.5.113 — IPsec: несколько сессий одного клиента без ложного офлайн (2026-10-10)

Исправлен mapper: ранее повторяющиеся established active-peers.id удалялись из индекса целиком, и даже единственный соответствующий клиент выглядел офлайн. Теперь индекс сохраняет группу сессий. Единственный клиент с совпадающим ID получает online=true; activeAddress/activeSince выдаются только при одной established сессии. При нескольких сессиях reader не выбирает произвольный lease/uptime. Claims считаются на группу: если её разделяют разные catalog clients, у них sessionAmbiguous и нет подтверждённого online/адреса, как в112. Начальные/завершающиеся сессии не подтверждают online.

Изменены backend/src/services/ipsec-live.ts, ipsec-state.test.ts и tests/e2e/ipsec-data.spec.ts. Контракт и существующие компоненты ReUI не менялись: таблица уже показывает «онлайн» без адреса. Проверены certificate/PSK, перестановка native rows, конфликт aliases, переход несколько→одна→нет established сессий. State108/108; все8 профильных скриптов, backend build, ESLint прошли. E2E16 unique passed33.6s: два новых сценария1280/320 и прежняя профильная регрессия IPsec.

На стенд собран/развёрнут только backend ux-sessions113/version1.0.0-test.sessions113. Source base cb6ec09/context build-alias112 плюс один явный override; source и compiled ipsec-live.js SHA256 совпали с локальными байтами. Label sessions113 не является Git SHA. Frontend ux-alias112-version/version1.0.0-test.alias112 сохранён, backend/PG healthy; у frontend нет healthcheck, подтверждены HTTP/browser. Rollback .env сохранён privately как pre-sessions113.env, прежний образ оставлен.

Оба CHR прошли реальный fetchIpsecState, aggregate GET /api/ipsec вернул200 без failures. В собранном reader проверены контролируемые snapshots с повторяющимися ID и aliases на базе прочитанных состояний; это НЕ создание нескольких реальных IKE подключений. Каталог live пустой: browser smoke1280/320 проверил API, пустое состояние, отсутствие ошибки и overflow; pageerrors0/APIwrites0. Первый browser запуск получил ECONNREFUSED: прежний localhost туннель отсутствовал; восстановлен согласованный SSH forward3000/8000, повтор passed. RouterOS writes0, acceptance DBwrites0, тестовых сетевых объектов не создавалось; пароли прежние.

Протокол: ipsec-multiple-sessions. Следующий114 — один сертификат с несколькими identity refs: текущий last-reference-wins ещё не исправлен, нужно проверить представление строк и выбор target для мутаций. Одновременные реальные подключения с одним ID, внешние интеграции, client OS, полнаяPKI и итоговая общая регрессия остаются отдельной приёмкой.

Референс Схема
ReUI Filtering2 ID → группа established → один клиент «онлайн» / разные клиенты «Не определено»
ReUI Stats12 Несколько сессий → один подтверждённый клиент → сводка без двойного счёта

12.5.114 — IPsec: общий сертификат, разные identity и безопасный target (2026-10-10)

Устранён last-reference-wins: mapper хранит все ссылки на remote-certificate и выдаёт отдельную строку для каждой identity. У каждой строки свой identity:, имя, peer, Remote ID, mode-config/static IP. Сертификат без ссылок сохраняет cert:. Общая observed сессия не присваивается двум строкам: sessionAmbiguous и «Не определено»; независимые explicit ID проверены отдельно. Перестановка native identity rows не меняет состав/поля каталога.

Resolver помечает запрос по certificate target как неоднозначный при нескольких refs, поэтому PATCH/DELETE не выбирают первую identity. DELETE identity с removeCertificate=true проверяет другие identity/peer refs до первого удаления и возвращает409. Явный removeCertificate=false допускает удаление выбранной identity с сохранением сертификата; локальный HTTP тест подтверждает один delete/историю и отсутствие других writes. Интерфейс пока не предлагает этот отдельный вариант — следующий115 должен сделать его понятным. Прямой endpoint принудительного удаления сертификатов не менялся.

Изменены backend services/ipsec-live.ts, routes/ipsec.ts, state/mutation tests и UI HTTP fixture. Контракт и компоненты ReUI/base-nova не менялись; существующая таблица принимает отдельные DTO rows. State114/114, все8 профильных скриптов, backend build и scoped ESLint passed. E2E18 unique/35.9s: две новые проверки общего сертификата1280/320 плюс профильная регрессия.

Before на backend113: native established с адресом198.18.114.250, две certificate identities, но каталог сохранил только вторую и присвоил ей адрес; первая отсутствовала. After на ux-refs114 обе строки присутствуют и unknown без активного адреса, конфигурационные250/251 сохраняются. Certificate PATCH/DELETE и identity DELETE с общим сертификатом вернули409. PATCH выбранной identity при одинаковых match-by=certificate условиях вернул502 с native400 «a matching identity already exists»; обе identity остались неизменными. Это ограничение RouterOS, успешное редактирование одновременно существующих идентичных match rules НЕ принято. После удаления собственного дубля исходная identity восстановила online/250; её API PATCH имени и возврат исходного имени дали200, native readback совпал. Два успешных PATCH вызывают запись истории с dedupe; число вставленных revisions отдельно не заявляется.

Live browser4/4 без HTTP mocks: dark/light1280/320, обе реальные строки, unknown alert/сводка, decoy offline, reload, overflow0, pageerrors0/APIwrites0. Desktop light и mobile dark снимки просмотрены. Первичные helper ошибки сохранены: syntax до вызовов; DELETE с Content-Type без тела дал400 до guard; затем native matching conflict потребовал правильного критерия приёмки. Каждый запуск с сетевыми объектами завершил cleanup13 коллекций×2; предварительные отказы не выданы за passed.

Backend только: ux-refs114/version1.0.0-test.refs114, base60b2e09/context build-sessions113 плюс два overrides; source и compiled bytehashes совпали. Frontend ux-alias112-version/version1.0.0-test.alias112 сохранён. Backend/PG healthy; frontend подтверждён браузером, собственного healthcheck нет. Rollback .env pre-refs114.env сохранён privately, старый образ оставлен. Собственные certificates/keys/imports/peers/identities/mode-config/profile/proposal/groups/templates/files удалены; исходные13 коллекций×2 совпали, default/public/metadata/195.195.195.195/32/logging сохранены. Оба CHR доступны; пароли прежние.

Протокол: shared certificate, live UI. Следующий115 — UI для удаления только выбранной identity с сохранением общего сертификата; затем согласовать оставшиеся native/внешние ограничения и итоговую регрессию. Множественные реальные сессии одного ID, клиентские ОС, полнаяPKI, интеграции и multi-WAN не закрыты этим блоком.

Референс Схема
ReUI Filtering2 Сертификат → все identity → отдельные строки/настройки → выбор по identity ID
ReUI Sheet8 Выбранная identity → проверка ссылок → API409 без записи либо подтверждённая операция

12.5.115 — IPsec: удалить identity и сохранить общий сертификат через UI (2026-10-10)

В существующий AlertDialog добавлен Checkbox «Удалить также клиентский сертификат» только для certificate identity с явным identity:. По умолчанию выбран для единственной привязки; при других rows того же certName на том же serverId выключен/disabled. Сертификаты с одинаковым именем на другом сервере не считаются общими. Подтверждение объясняет сохранение сертификата и остальных identity; запрос передаёт removeCertificate=false. При API ошибке диалог/выбор/данные сохраняются, блокировки повторного нажатия прежние. Для cert-only row без identity нет ложной возможности «удалить клиента, сохранив единственный объект».

Изменены app/(main)/ipsec/page.tsx и tests/e2e/ipsec-delete.spec.ts. ReUI/base-nova, установленный AlertDialog и Checkbox переиспользованы; vendor/theme не менялись. Scoped ESLint и source TypeScript passed; production frontend build passed. Приняты26 unique E2E: первая профильная серия22 passed/4 failed из-за проверки getByRole фона при открытом модальном диалоге; corrected includeHidden проверка сохранности DOM rows дала4/4 rerun9.8s. Это26 уникальных, не30 сценариев.

Frontend ux-keepcert115/version1.0.0-test.keepcert115 развёрнут; backend ux-refs114/version1.0.0-test.refs114 сохранён. Source base58f5c48/context build-alias112-front плюс один page override, bytehash совпал. Label keepcert115 — метка этапа, неGitSHA; compiled frontend reproducibility не заявлена. Backend/PG healthy, frontend HTTP/browser passed, healthcheck у frontend отсутствует. Private rollback pre-keepcert115.env и прежний образ сохранены.

На собственном signed-certificate IKE fixture проверены4 live диалога (dark/light1280/320) без mocks; первые3 отменены, в light320 выполнен ровно один DELETE identity с removeCertificate=false. Native readback подтвердил отсутствие выбранной identity и сохранение точного certificate ID и другой identity. Исходный клиент восстановил online/198.18.115.250, unknown alert исчез. Последующие PATCH имени/возврат200 подтвердили восстановление. Чужой для приложения mode-config API не удалял: helper очистил только собственный fixture объект. История вызывается API с dedupe; точное число вставленных revisions не заявляется.

Собственные native объекты и private exports/imports очищены, исходные13 коллекций×2 совпали; маршруты/default/logging сохранены. Оба CHR/SSH доступны, пароли прежние. Screens4, просмотрен light320. Протоколы: native/deployment, live UI.

Следующий116: default user DELETE ещё угадывает имя сертификата для identity без remote-certificate; проверить/исключить случай PSK + отдельный cert с совпавшим именем. После последнего исправления — единая общая регрессия. Внешние Portal/Telegram/client OS/multi-WAN/scale и множественные native IKE sessions остаются в матрице.

Референс Схема
ReUI Sheet8 Выбранная identity → прямой объём удаления → сохранить общий сертификат → подтверждённый API результат

12.5.116 — IPsec: не удалять сертификат, угаданный по имени PSK (2026-10-10)

Устранена подтверждённая ошибка default DELETE: при пустом remote-certificate managed display name преобразовывалось в ipsec-user-, и несвязанный сертификат мог удаляться вместе с PSK identity. Теперь имя клиента не является доказательством связи: certificate deletion/preflight используют только явный remote-certificate либо выбранный cert target. Прямая одиночная certificate привязка по-прежнему допускает удаление; shared refs блокируются до записи как114. PSK диалог объясняет сохранение сертификатов; описания mode-config уточняют, что удаляются только неиспользуемые объекты приложения.

Изменены routes/ipsec.ts, mutation test, IPsec page и delete E2E. Все8 backend scripts, state114, backend build/source TypeScript/scoped ESLint passed. HTTP тест подтвердил PSK name collision: один identity DELETE, removeCertificate0; positive explicit binding: identity+certificate writes2. E2E28 unique passed39.6s, включая PSK описание/сохранение отдельной строки1280/320 и профильную регрессию. Vendor/ReUI/base-nova не менялись.

Before на backend114: создана собственная PSK identity с managed name, совпадающим со slug собственного unused signed decoy certificate. DELETE200 удалил оба объекта, хотя remote-certificate пуст. After на bound116: четыре live PSK диалога (dark/light1280/320), один DELETE через light320 UI, PSK удалён, тот же native ID/имя несвязанного сертификата сохранены. Browser не использовал mocks; APIwrites1, pageerrors0. Исходная certificate IKE сессия/online/198.18.116.250 сохранялись. Это не тест новой PSK сессии/throughput. Просмотрен light320 screenshot.

Обе части собраны последовательно и развёрнуты как ux-bound116/version1.0.0-test.bound116. Base d52c48e/context backend build-refs114, frontend build-keepcert115-front; по одному override для route/page, два source bytehash и compiled backend route bytehash совпали. Frontend compiled reproducibility не заявлена, label bound116 неGitSHA. Private rollback pre-bound116.env и прежние образы оставлены. Backend/PG healthy; frontend browser/HTTP подтверждён, healthcheck отсутствует. На VM25GB после сборок3.6GB свободно/86% занято; ресурсов достаточно для текущих проверок, production performance не оценивалась.

Оба native запуска очистили собственные fixtures, baseline13 коллекций×2 совпал; сохранены logging/default/public/metadata/195.195.195.195/32. Пароли прежние, оба CHR/SSH доступны. API DELETE вызывает history recording с dedupe; число новых revisions отдельно не заявляется. Протоколы: binding, live UI.

Следующий117 уже запущен: единая основная UI-регрессия1244 сценария на текущем frontend source, затем контекстный набор и сверка source/build/runtime. Внешние аккаунты/Portal/Telegram/client OS/scale/multi-WAN и одновременные native IKE sessions остаются в матрице.

Референс Схема
ReUI Sheet8 Выбранная identity → явная certificate связь → preflight → удаление выбранных объектов / сохранение несвязанных

12.5.117 — общая UI-регрессия и сверка действующего source/runtime (2026-10-10)

Основной набор1244:1243 passed/1 failed за28.8m; контекстный221/221 за7.2m. Failed large-backups.spec.ts измерял кнопки сразу после изменения1440→320 viewport: размер43.796875px во время CSS-transition, после двух animation frames ровно44×44, границы viewport/pinned соблюдены. Исправлен только тест: expect.poll ждёт прежние44px/координаты без снижения порога. Scoped rerun1/1 за10.2s, полноценный поиск/refresh/error/page/file/focus/grid axe сценарий завершился. Итог1465 unique accepted (1243+1+221); основной первоначальный exit1/failure сохранён,1244 fresh whole-main pass НЕ заявляется. Production UI менять/пересобирать не требовалось, scoped ESLint passed.

Source audit базируется на057b530:905 tracked application/config inputs, frontend515 raw matched + preprocessing package + отсутствующий clean-context .dockerignore; backend405 raw matched + подготовленный root package + четыре test-source differences. Содержимое frontend package проверено: только исключён backend workspace; backend package: scripts omitted, dependencies/devDependencies empty, остальные поля совпадают. Production source drift0; различия ipsec-state/ipsec-mutation/recursive-routes/speed-test tests явно исключены из этого утверждения. Контексты не содержат non-example .env inputs. Git label bound116 — метка, неSHA.

Все984 emitted production backend/contracts outputs, построенные по текущим tracked non-test TS paths, совпали с actual backend container после CRLF→LF. Старые вложенные local dist/backend/src outputs не включались: они не текущие outputs и отсутствуют в контейнере. Это normalized equivalence, не обещание byte identity; отдельная frontend binary reproducibility не доказана. Runtime source contexts build-bound116/build-bound116-front, обе версии1.0.0-test.bound116; backend/PG healthy, frontend HTTP/browser принят116, собственного healthcheck нет.

Read-only stand: оба enabled CHR reachable/RouterOS7.24.5 stable;27 коллекций×2 не содержат собственных prefixes (критерии/пути сохранены в JSON), own speed runs/probes0, servers2/migrations9. Это scoped namespace scanner, не full export и не универсальное определение ownership; native session caches не удалялись. Проверка не меняла RouterOS/пароли. Отдельный118-before fixture после этого подтвердил legacy export bug и очистился по13 коллекциям×2; archive/passphrase остались в памяти и не попали в Git.

Автоматически переснятые120 ранее чистых PNG сохранены в ignored tmp/regression117-generated-screens и убраны из diff; восемь исходных dirty GRE/VXLAN снимков восстановлены из сохранённой копии с проверенными исходными размерами. В этот блок включён только relevant large-backups-320 screenshot; unrelated skills/AGENTS не коммитились. Протокол: regression/source/runtime.

Следующий118 — удалить name inference из legacy POST /ipsec/users/:serverId/:rosId/cert, отказать PSK до export и проверить прямую certificate binding. Before200 с архивом отдельного своего сертификата уже воспроизведён, не принят как верное поведение. UI fixtures не заменяют native/Portal/Telegram/client OS/multi-WAN/scale приёмку.12.5 остаётся открыт.

Референс Схема
ReUI Filtering2 Viewport → окончание анимации → прежний touch target44px → keyboard/file/axe

12.5.118 — IPsec: legacy экспорт только по явной certificate привязке (2026-10-10)

Исправлен POST /ipsec/users/:serverId/:rosId/cert: managed display name больше не преобразуется в clientCertName как fallback. PSK либо отсутствие remote-certificate возвращают409 до вызова exporter, без contentB64/passphrase. Для отдельного сертификата остаётся явный export-by-name endpoint. Direct certificate binding поддерживается после смены display label: имя сертификата/ключ не меняются, bundle.user соответствует актуальной подписи.

Изменены routes/ipsec.ts и mutation test. Все8 backend scripts/state114, backend build и scoped ESLint passed. HTTP test подтвердил PSK409/exportCalls0, positive200/exportedName ровно explicit ref при другом display label. Первый positive mock упал502 из-за отсутствующего getCertificates у заглушки; fixture дополнен и повтор принят. Последняя перестановка независимых HTTP кейсов проверена focused script повторно. UI/source не менялись, full1244/context221 не повторялись после локального изменения одного backend endpoint; границы117 сохранены.

Native before на backend116: создана своя PSK identity без remote-certificate с именем, совпадающим со slug собственного unused signed decoy cert. Legacy POST200 вернул его P12 archive. After на118: этот запрос409 без archive/passphrase. Для primary certificate identity временно установлен другой managed display label; POST200 вернул archive её прямого remote-certificate, исходный comment восстановлен. Архив/passphrase/instructions использовались только в памяти, не записывались в report/Git. Existing certificate IKE session/CN/FQDN/catalog оставались корректны; это не новая PSK session или клиентская OS приёмка.

Backend ux-export118/version1.0.0-test.export118 собран из build-bound116/base9da5e55 с одним route override; source/compiled route bytehash совпал. Frontend ux-bound116/version1.0.0-test.bound116 сохранён. Backend/PG healthy; rollback .env pre-export118.env и прежний образ оставлены, label export118 неGitSHA. Оба native запуска очистили собственные certificates/imports/peers/identity/groups/templates/mode-config/profile/proposal/files, baseline13×2 совпал. Native certificate IDs сохранялись до собственного cleanup; logging/default/public/metadata/195.195.195.195/32 сохранены, оба CHR/SSH доступны, пароли прежние. Протокол: export binding.

Следующий119 — закрыть controlled-only границу113: несколько реальных established IKE sessions с одним ID и одним certificate principal. Подготовка отдельного official Debian/strongSwan image начата; клиенты будут в собственных Docker namespaces, private credentials временные/свои, host network и приложение не перенастраиваются. До native подтверждения этот пункт остаётся открытым. Конфигурация сверена с strongSwan, каталогом credentials и RouterOS. Внешние Portal/Telegram/Windows/macOS/mobile/multi-WAN/scale остаются отдельно.

Референс Схема
ReUI Sheet8 Выбранный клиент → явная certificate binding → PKI export либо409 без архива

12.5.119 — две реальные IKE-сессии одного certificate principal (2026-10-10)

Контролируемая граница113 дополнена реальными сессиями: два Docker Linux клиента, official Debian trixie/strongSwan6.0.1-6+deb13u7, собственные namespace/bridge, NET_ADMIN только внутри clients. Один свой RSA2048 клиентский сертификат/ключ, свой CA и явно закреплённый server certificate. IKE/ESP AES256/SHA256/MODP2048, unique=never; чужие сетевые объекты/host networking приложения не перенастраивались. Docker создал и затем удалил собственную временную bridge/NAT сеть.

В принятой конфигурации local ID получен непосредственно из сертификата. RouterOS подтвердил две established с одинаковым ID CN=<имя>-client и разными198.18.119.249/248. Каждый клиент выполнил Ping3/3 до собственного encrypted endpoint198.18.119.1. Это short data-plane proof, не throughput/rekey/SLA. API: clientsTotal1/clientsOnline1, activeAddress/activeSince/sessionAmbiguous отсутствуют. Два live UI1280/320 без mocks: один зелёный «онлайн», VIP не присвоен произвольно, unknown alert отсутствует; writes0/pageerrors0. Mobile screenshot просмотрен. Application source не менялся, backend118/frontend116 сохранены.

Первый cleanup остановился: helper ошибочно ожидал comment у cert, который SDK/RouterOS не сохранил. До повторения scoped recovery проверил имя/CN/CA references/native IDs, удалил только свои объекты/credential files; Docker cleanup уже был завершён. Последующие retries сохранили baseline16×2. Первые FQDN/ADDR4, ручной DN и pinned server+ручной DN получили AUTH_FAILED; RouterOS сообщил identity not found/peer ID does not match certificate. Certificate-derived ID с тем же ключом/CA/server pin прошёл. Точная причина различий encoding не доказана; эти варианты не переименованы в success и остаются следующей120 приёмкой.

Final cleanup: labelled clients/network удалены после owner проверки, свои native logging/peer/identity/policy/group/profile/proposal/mode-config/pool/bridge/address/certificates удалены по ID;16 исходных коллекций×2 совпали, default/public/metadata/195.195.195.195/32 сохранены. Private P12/pass/PEM/config files удалены, пустые свои directories закрыты без recursive delete. Архивы/ключи не попали в Git. Оба CHR доступны, пароли прежние. Инструментальный image сохранён для повторения; приложение не пересобиралось. Протоколы: native/отказы/cleanup, live UI.

References: strongSwan configuration, credentials, RouterOS. Два контейнера используют один public WAN/NAT, не являются независимыми площадками и не закрывают Windows/macOS/iOS/Android. Следующий120 — ID interop/encoding; остальные внешние зависимости сохранены в матрице.12.5 открыт.

Референс Схема
ReUI Filtering2 Две подтверждённые сессии → один клиент онлайн → без произвольно выбранного VIP

12.5.120 — кодирование DN и FQDN SAN в реальном IKE (2026-10-11)

На том же strongSwan6.0.1-6+deb13u7 последовательно проверены шесть вариантов с собственными CA/server/client certs, server certificate pin, RSA/AES256/SHA256/MODP2048. Certificate-derived DN, явный asn1dn с точными DER-байтами, FQDN из DNS SAN и FQDN с явным RouterOS remote-id установили tunnel и дали Ping3/3 каждый. Ручной текстовый DN и точный DER с единственным изменением тега CN 0x0c→0x13 отклонены AUTH_FAILED. Сертификат содержит UTF8String; парсер strongSwan6.0.1 выбирает PrintableString для этого ASCII CN. Это доказанная граница данной пары версий, не утверждение обо всех DN/PKI.

Обнаружено: FQDN SAN без явно заданного remote-id успешно аутентифицируется, но catalog API показывает offline. С remote-id=fqdn:… online=true. Первый helper остановился на ошибочном ожидании online; finally полностью очистил стенд. Уточнённый сценарий сохранил этот дефект отдельным результатом и завершил шесть вариантов. Он требует исправления в121, а не считается успешной приёмкой отображения. Ранее119 отказ FQDN включал requested IDr; новая конфигурация закрепляет точный server cert и не запрашивает IDr. Проверка сертификатов не отключалась.

Все свои containers/network/credentials и native objects удалены после проверки ownership. Baseline16 коллекций×2 совпал; оба CHR доступны, пароли и исходная конфигурация сохранены. Application source/runtime не менялись, UI заново не тестировался. Протокол. Следующий121 — SAN matching с защитой неоднозначности и нескольких ID одного principal. Windows/macOS/mobile, независимые WAN, scale/rekey и интеграции остаются открыты.

References: Identity parsing6.0, парсер6.0.1.

Референс Схема
ReUI Filtering2 Native established → точный ID/сертификат → подтверждённый online; неоднозначность → неизвестно

12.5.121 — подтверждённый онлайн по DNS SAN и нескольким IKE ID (2026-10-11)

Исправлен обнаруженный120 дефект: RouterOS принимает FQDN SAN, но API сопоставлял только DN/CN/явный remote-id. Теперь точный DNS SAN учитывается при прямой привязке сертификата к identity и отсутствующем/auto remote-id. SAN должен быть уникален среди всех native certificates; DNS wildcard/IP/email/чужие namespaces и конфликты DN/CN не угадываются. Явный иной remote-id не подменяется SAN. Общие claims проверяются по каждой native session, поэтому пересечение с PSK или другой identity остаётся sessionAmbiguous, без присвоения её адреса.

Все наблюдаемые DN/CN/explicit ID/SAN сессии одного principal объединяются: online подтверждён, но при нескольких сессиях не выбираются произвольные VIP/uptime. Добавлены13 state scenarios: unique/duplicate SAN, explicit/auto, DN+SAN с перестановкой, PSK collision, неподдерживаемые SAN, CN shadow и отсутствие привязки. Прошли127 state checks и8 профильных scripts, backend production build и scoped ESLint. Общая регрессия117 не повторялась; DTO/frontend/vendor не менялись.

Backend ux-san121/version1.0.0-test.san121 собран из контекста118 с одним source override. Локальный и серверный SHA256 source/compiled ipsec-live совпали. Frontend116 сохранён; backup pre-san121.env/предыдущий image оставлены. Backend healthy. Первый native helper остановился на regex старого диапазона VIP; finally восстановил baseline, затем regex исправлен. Повторение: один certificate-derived DN и один FQDN SAN одного cert одновременно established, Ping3/3 каждый. Catalog online1, activeAddress/activeSince отсутствуют. Два live UI1280/320 без mocks/write/pageerrors, mobile screenshot просмотрен.

Все свои Docker clients/network/credentials/native configs удалены после ownership preflight; baseline16 коллекций×2 совпал, default/public/metadata/195.195.195.195/32 сохранены. Оба CHR доступны, пароли прежние. Native/build/проверки, live UI. Следующий122 — IKE/CHILD rekey/reconnect; клиентские ОС/длительные нагрузки/физические WAN/integrations остаются открыты.

Референс Схема
ReUI Filtering2 Native DN+SAN → один клиент online → несколько сессий без случайного VIP

12.5.122 — реальный rekey CHILD/IKE и повторное подключение (2026-10-11)

На собственном Linux strongSwan→CHR certificate tunnel приняты пять состояний: initial, CHILD rekey, IKE rekey, terminated, reconnected. CHILD rekey подтверждён новой парой native ESP SPI после ухода старых SA; IKE rekey — новым strongSwan IKE unique ID после ухода прежнего. В четырёх connected фазах native established1/API online и Ping3/3 с первой попытки; после terminate established0/API offline без activeAddress/uptime. Повторное подключение вернуло online/Ping. RSA/private CA/exact server certificate pin/AES256/SHA256/MODP2048 сохранены.

Первый прогон принял обе смены ключей/офлайн, но reconnect Ping failed. Сценарий не сохранил достаточно данных для доказательства причины. Повторение использовало именно выданный native VIP, записало все client addresses и ограниченные Ping attempts; каждая рабочая фаза прошла с первого Ping3/3. Это не превращает первый отказ в успех и не доказывает мгновенное/бесшовное восстановление. Оба протокола сохранены. Длительное обновление, packet loss в переходе, reauth и физический WAN/SLA ещё не приняты.

Application source/image не менялись, общая регрессия и UI повторно не запускались. Все собственные Docker clients/network, private P12/PEM/pass/config и native configs/certs/logging удалены с ownership preflight. Baseline16×2 совпал, оба CHR доступны/пароли прежние. Native installed-sa сохранялись только по whitelist public SPI/state/адресов, ключи не записывались. Протокол с первоначальным отказом. Следующий123 — неправильный server pin и непривязанный клиентский certificate.

Reference: strongSwan rekey6.0.

Референс Схема
ReUI Filtering2 Новые SA → подтверждённый online → terminate/offline → reconnect/online

12.5.123 — server pin и привязка клиентского сертификата (2026-10-11)

Три реальные Linux strongSwan→CHR попытки без ослабления проверки сертификатов. Контрольный клиент с private CA/точным server pin/привязанным remote-certificate установил туннель и дал Ping3/3. Замена server pin на другой собственный certificate привела к отказу на клиенте. Второй RSA client certificate, подписанный тем же CA, но не указанный в remote-certificate identity, отвергнут RouterOS. Общий доверенный CA не подменяет точную native привязку. Отказы проверялись как ожидаемые, а не success tunnel.

После каждой попытки native established0 и catalog online0; неподключённые клиенты не получили active session. Все собственные Docker clients/network/private credentials и native objects удалены;16 исходных коллекций×2 совпали, пароли/default/public/metadata/195.195.195.195/32 сохранены. Оба CHR доступны. Source/runtime не менялись, профильная общая регрессия и UI не повторялись. Протокол.

Это ограниченная certificate authentication приёмка, не полная PKI: revocation/expiry, прочие client OS/custom OIDs/ID namespaces остаются открыты. Следующий124 — полноценный reauth и наблюдаемая граница IKE online при отсутствии CHILD SA.

Референс Схема
ReUI Filtering2 Сертификат и привязка подтверждены → online; ошибка pin/привязки → отказ без ложного online

12.5.124 — reauth и честная граница IKE онлайн (2026-10-11)

Реальный strongSwan certificate reauth завершился новой IKE SA и уходом старой; после initial/reauth/CHILD restore Ping3/3 каждый с первой попытки. При terminate только CHILD SA RouterOS сохранил established IKE1, installed-sa0; API продолжал online=true, Ping2/2 потерян. После нового CHILD SA Ping восстановился. Это подтверждает семантику текущего online: установленная IKE-сессия, не измерение передачи данных.

На странице добавлено краткое пояснение «Онлайн означает установленную IKE-сессию. Передачу данных проверяйте Ping». ReUI/Frame/base-nova и существующие компоненты сохранены. Production frontend build/typecheck и scoped ESLint прошли; source hash страницы совпал с Docker context. Frontend ux-ike124/version1.0.0-test.ike124 развёрнут, backend ux-san121 сохранён. Backup pre-ike124.env/прежний image оставлены. Два live UI1280/320 без writes/pageerrors/overflow: дождались API receipt и стабильного положения текста, screenshot mobile просмотрен. Empty catalog UI проверяет пояснение; активные DN/SAN строки уже приняты121.

Native objects/private credentials/Docker clients/network очищены с ownership preflight, baseline16×2 совпал. Оба CHR доступны, пароли/default/public/metadata/195.195.195.195/32 сохранены. Полная регрессия117 не повторялась для этой текстовой правки. Native/build, браузер. Длительный reauth/rekey, transition loss, физические WAN и клиентские ОС остаются открыты; следующий125 — отзыв/CRL.

Референс Схема
ReUI Stats12 IKE online → пояснение значения → отдельная проверка Ping

12.5.125 — фактическая граница локального отзыва сертификата (2026-10-11)

Контрольный собственный certificate tunnel установился/Ping3/3. Первая попытка использовала неверный /certificate/revoke и получила400 no such command; finally очистил fixtures. По официальному CLI reference уточнена /certificate/issued-revoke. Повторение подтвердило native revoked=true у собственного leaf certificate. Уже установленная IKE-сессия осталась established. После terminate повторное подключение тем же отозванным certificate также установилось. Ожидание отказа не прошло; это сохранённое наблюдение, не успешная приёмка revocation blocking.

После cleanup чтение certificate/settings подтвердило на обоих CHR crl-use=false/crl-download=false; certificates0/crls0. Глобальные settings в этом блоке не изменялись. Документация описывает CRL проверку отдельной настройкой, поэтому native revoked flag не считается доказательством блокировки при нынешней конфигурации. Application source/API не менялись; вывод об API online после reconnect не делается — helper остановился раньше его чтения.

Все свои configs/certificates/logging/private credentials/Docker clients/network удалены. Baseline17 коллекций×2, включая certificate/crl, совпал; default/public/metadata/195.195.195.195/32 и пароли сохранены. Протокол наблюдения и непройденное ожидание. Следующий126 — контроль валидного клиента и отказ отозванного при собственной CRL цепочке/временном crl-use, с обязательным возвратом исходных settings. Полная CRL/expiry/PKI приёмка остаётся открытой.

References: issued-revoke, CRL settings.

Референс Схема
ReUI List9 Метка revoked → отдельная CRL policy → реальная попытка соединения → подтверждённый результат

12.5.126 — CRL-enabled отзыв и проверенная очистка цепочки (2026-10-11)

Создана собственная CA/серверная/клиентская цепочка с CRL URL. До control IKE временно включены crl-use/crl-download на CHR1, после проверки certificates0/CRLs0 baseline. Валидный клиент установился/Ping3/3. После issued-revoke подтверждён revoked=true; действующая IKE могла остаться established. После явного terminate новый IKE тем же cert отвергнут AUTH_FAILED, native established0/API offline. Это закрывает отличие от125 для данной local CA конфигурации, не полную PKI и не мгновенный разрыв существующих SA.

Все certificate/settings возвращены к точной исходной записи. Initial sign потребовал точный .id — добавлен по ответу REST. Первый cleanup остановился на удалении issued server leaf: RouterOS требует revoke для сертификата CA с CRL. Settings/Docker/network/configs к этому моменту уже восстановлены/удалены. Recovery проверил ровно три собственных имени/CN/issuer, отсутствие своих configs, исходные settings и удалил точный собственный CA ID с каскадом только этих проверенных детей. CRL/private files очищены. Повторение использовало preflight всех дочерних cert IDs/ссылок перед own CA cascade и прошло целиком; baseline17 коллекций×2, private credentials/Docker/settings restored.

Наблюдение показывает риск API удаления: identity может быть удалена до native отказа удаления CRL-issued certificate. Следующий127 —409 до любых writes для защищённого leaf и CA с issued children; сохранение cert при identity-only остаётся доступным. Production source/runtime в126 не менялись. Оба CHR доступны, пароли/default/public/metadata/195.195.195.195/32 сохранены. Все результаты/отказ cleanup/recovery.

Reference: Certificates/CRL. Expiry, внешняя CRL загрузка/timeout, intermediate/custom PKI, клиентские ОС и долговременные нагрузки остаются открыты.

Референс Схема
ReUI List9 CA/CRL policy → валидный клиент → отзыв → reconnect отказ → возврат исходных settings

12.5.127 — удаление CRL-issued сертификатов без частичных изменений (2026-10-11)

Исправлена выявленная126 последовательность: перед удалением identity API проверяет явно привязанный cert/issuer. Локально issued либо revoked certificate CA с crl=true получает409 до любых writes. Пользователь может удалить только identity с removeCertificate=false. В /ipsec/certs дополнительно запрещено отдельное удаление CA с дочерними certs: RouterOS каскадно удаляет цепочку, поэтому force=true это ограничение не обходит. Автоматический отзыв/удаление чужой цепочки не добавлялся. Imported non-issued/non-revoked leaf сохраняет прежний сценарий удаления.

Добавлены13 профильных HTTP cases с нулевыми writes/history при отказе, сохранением cert при identity-only, обеими issued/revoked формами native metadata, CA force guard и положительным imported случаем. Прошли8 IPsec scripts (state127), backend production build/scoped ESLint. Backend ux-crl127/version1.0.0-test.crl127 собран из121 с одним route override; локальные и серверные source/compiled SHA256 совпали. Frontend ux-ike124 сохранён, backup pre-crl127.env/прежний image оставлены. DTO/vendor не менялись.

Native собственная CRL chain: семь409 (user/cert targets, direct leaf/CA с/безforce и revoked leaf) сохранили certs; до identity-only identity также оставалась. Identity-only200 удалил выбранную identity, сохранил все3 certs. Первый control остановился на Ping3/3 без достаточной диагностики; cleanup прошёл, отказ сохранён. Повторение проверяло выданный native VIP и записывало bounded Ping attempts, затем завершило API-сценарии. Мгновенная связность/SLA не заявляется.

Settings восстановлены точно, own CA cascade после проверки всех детей/ссылок очистил только собственную цепочку; baseline17×2/Docker/private credentials restored. Оба CHR доступны, пароли/default/public/metadata/195.195.195.195/32 сохранены. UI и общая регрессия117 повторно не запускались: guards/backend-only, сохранение modal при API error уже принято предыдущими UI блоками. Протокол. Следующий128 — expired/not-yet-valid certs без изменения часов.

Референс Схема
ReUI Sheet8 Проверка cert/CA →409 без изменений → выбор сохранить cert → подтверждённое identity-only удаление

12.5.128 — сроки сертификатов и неподтверждённая причина отказа (2026-10-11)

На OpenSSL3.5.7 созданы собственные same-key/same-CA сертификаты с явно заданными датами. Часы VM/CHR не менялись. Действующий original cert и перевыпущенный valid cert установили IKE/Ping3/3 каждый. Для renewed/invalid сертификатов временная собственная identity проверяла доверенный CA (remote-certificate=none/match-by=remote-id/auto), сохраняя pubkey auth/crypto и точный server certificate pin. Положительный renewed control доказывает работоспособность этой конфигурации с новым certificate DER.

Expired и not-yet-valid certificate не установили сессию за30s: IKE_INIT отвечал, затем IKE_AUTH retransmits, без явного AUTH_FAILED. Native established0/API online0. Это наблюдение тайм-аута, а не доказанный RouterOS expiry отказ. Журнал прочитан после cleanup, audit boundary уже не сохранился; точная причина остаётся открытой. Следующий129 должен захватить scoped auth logs сразу в каждой фазе.

Первый подход пытался импортировать expired cert: новых native rows оказалось0, точная причина импорта не записана. Cleanup остановился на принадлежности файла/ID. Scoped recovery проверил собственный namespace/CN/issuer/возраст, удалил только свои configs/certificate chain и точное имя созданного CRT (flash directory не удалялся), private files/CA key. Повторение не импортировало invalid certificates, держало их только в собственном client filesystem; cleanup baseline17×2/Docker/credentials passed. Оба CHR доступны/пароли/default/public/metadata/195.195.195.195/32 сохранены.

Протокол и все ограничения. Полный первоначальный Ping failure127 дополнительно перенесён в репозиторий. Source/runtime не менялись, UI/общая регрессия не повторялись. Expiry reason и внешняя CRL/PKI приёмка не закрыты.

Reference: OpenSSL x509 dates.

Референс Схема
ReUI List9 Valid control → encoded dates → native establishment/API → тайм-аут без выдуманной причины

12.5.129 — непройденный положительный контроль и изоляция диагностики (2026-10-11)

Повторение с чтением журнала во время фаз остановилось на valid-renewal control: original cert/Ping3/3 прошли, действующий новый cert получил IKE_AUTH timeout. Expired/future случаи не запускались. Поэтому предыдущие128 тайм-ауты не считаются доказанной expiry причиной. Phase authLogs оказались пусты; точная транспортная/сертификатная причина пока не определена.

Readonly clock проверка: VM20:13:44Z, CHR1 23:13:44/+03:00 (Moscow), CHR2 22:13:44/+02:00 (Warsaw), в пределах точности секунд совпали. Часы и timezone не менялись. Default memory:1000 entries/stop-on-full=false; CHR1 журнал содержит273 сообщения namespace129. Гипотеза о повторном использовании container IP/UDP tuple не выдаётся за установленную причину. Следующий130 использует отдельный netns/IP на вариант и собственный memory logging action с чтением только своего буфера; default logs не очищаются.

Final cleanup baseline17 коллекций×2/Docker/private files (включая собственный CA key) passed. Оба CHR доступны, passwords/default/public/metadata/195.195.195.195/32 сохранены. Source/runtime не менялись, UI/регрессия не повторялись. Failure/control/clocks/log metadata.12.5 и time-validity diagnosis открыты.

Референс Схема
ReUI List9 Положительный контроль не прошёл → не принимать отрицательные случаи → изолировать транспорт/журнал

12.5.130 — изолированная проверка сроков и исправление остатка cleanup (2026-10-11)

Каждый renewed/expired/future вариант получил отдельный Docker client namespace/IP (.3/.4/.5); прежние контейнеры удерживали адреса до общего cleanup. Original и renewed valid client установили IKE/Ping3/3. Expired и not-yet-valid client получили явный AUTHENTICATION_FAILED от CHR, native established0/API online0. Own key/CA/server pin/pubkey auth/crypto сохранены, часы не менялись. Это принимает local same-key/CA time-boundary после положительного renewed control; точная причина прежних128/129 тайм-аутов не доказана.

Созданы и затем удалены собственные memory action/rule без очистки штатного memory. Collector GET buffer query сохранил также исторические сообщения, поэтому строгая атрибуция этих логов не считается принятой; proof отрицательных случаев — прямой IKE AUTH_FAILED и состояние API/native. Полный диагностический buffer selector требует отдельной проверки через print query.

Обнаружено дополнительно: recovery128 удалял объекты по name/comment и пропустил logging rule, имеющее только prefix. Оно входило в последующие baseline128/129/130; их равенство не доказывало отсутствие этого остатка. Проверено точное имя namespace из recovery128, единственная rule с этим prefix, topics и action=memory; удалён только её native ID. Все остальные logging rows остались точно прежними, default журнал не очищался. Артефакты128/129 дополнены исправлением, исторические ограничения сохранены.

Итоговое повторение18 коллекций×2 прошло; после него отдельно удалён доказанный остаток128. Own custom logging action/clients/network/private files/CA key очищены, certificates/CRLs0, оба CHR доступны/пароли/default/public/metadata/195.195.195.195/32 сохранены. Source/runtime/UI не менялись. Протокол и correction. Следующий131 — ECDSA P-256 chain/Ping/экспорт. Full intermediate/custom PKI/external CRL/OS/scale остаются открыты.

Референс Схема
ReUI List9 Раздельные клиенты → valid control → explicit AUTH_FAILED → API offline → полная ownership очистка

12.5.131 — ECDSA P-256 и итоговая очистка блока IPsec (2026-10-11)

Создана собственная ECDSA P-256 CA/server/client chain (prime256v1), без изменения existing certificates/passwords. strongSwan6.0.1 установил certificate-authenticated IKE/ESP tunnel с точным server certificate pin/private CA и AES256/SHA256/MODP2048; Ping3/3. Public client key проверен Node X509: ec/prime256v1. API online1 и конкретный VIP этой единственной сессии. Экспорт client cert через /api/ipsec/certs/1/export вернул200/archive; архив и passphrase не сохранены в evidence/Git.

Own logging/peer/identity/policy/group/profile/proposal/mode-config/pool/bridge/address/certificates/private files/Docker client/network удалены по ownership preflight; baseline16×2 совпал. Дополнительная итоговая readonly inventory18 коллекций на каждом CHR проверила все namespaces120–131: residue0, established0, crl-use/download=false, private directories0. Labelled Docker acceptance containers/networks0; backend ux-crl127 и PostgreSQL healthy, frontend ux-ike124 running/HTTP+UI уже подтверждены124. Source/runtime/UI в131 не менялись, тесты и регрессия не повторялись. Оба CHR доступны, пароли/default/public/metadata/195.195.195.195/32/flash directory сохранены.

За эту серию исправлены implicit DNS SAN online121, смысл подписи IKE online124 и no-write CRL certificate/CA deletion guards127. Native interop/rekey/reauth/authentication/CRL/time validity/ECDSA приняты только в описанных границах. Все initial failures/recovery сохранены; тайм-ауты128/129 не переименованы в success и не используются как proof expiry. ECDSA/экспорт/final inventory.

Следующий132 — проверить scoped logger через POST print query (GET buffer collector130 содержит исторические сообщения), затем external CRL download/failure и оставшуюся матрицу. Windows/macOS/mobile, intermediate/custom PKI, независимые WAN/scale/долговременные нагрузки/реальные интеграции ещё не приняты. Этап12.5 открыт; новые native проверки начинать только с доступным бюджетом для cleanup и сохранения.

Референс Схема
ReUI Filtering2 EC cert/CA → native IKE/Ping → API online/VIP → подтверждённый экспорт → ownership cleanup

12.5.132 — изоляция диагностических буферов RouterOS (2026-10-11)

На обоих CHR RouterOS7.24.5 созданы по два собственных RAM action/rule с разными prefix. Один script/info marker попал в оба буфера. POST /log/print с .query=[buffer=ownAction] и .proplist вернул только нужный prefix: один маркер, foreignRows0. Контроль другого буфера вернул другой prefix; несуществующий буфер —0 строк. Обычный POST параметр buffer отклонён400; это ожидаемый отрицательный контроль. В проекции поле buffer отсутствует, поэтому изоляция подтверждена независимыми маркерами/контролями, а не выдуманным значением поля.

GET /log?buffer=ownAction тоже изолирует корректно. Повторное чтение helper130 показало, что после initial scoped read его collector обращался к общему GET /log. Поэтому предыдущая формулировка о ненадёжности GET buffer уточнена: дефект был в диагностическом сборщике. Исторические записи130 остаются смешанными и не становятся доказательством конкретной причины отказа сертификата.

Все четыре собственных logger/action на каждом CHR удалены по exact-ID/name/prefix/action/topics preflight. Полные существующие logging/action rows до/после совпали на обоих устройствах; default buffer не очищался. Пароли и VPN-конфигурация не менялись. Протокол и точный selector. Документация: REST query, раздельные memory buffers.

Source/runtime/UI не менялись; build и регрессия не повторялись. Следующий133 — оставшиеся реальные сценарии и проверка расхождений API; external CRL distribution failures, другие ОС и независимые WAN остаются открыты.12.5 не завершён.

12.5.133 — реальные журналы в REST-терминале (2026-10-11)

Диагностика132 выявила продуктовый баг getLogs: GET /log?limit=N использовал limit как REST property filter. На обоих CHR default memory содержал1000 строк, но SDK возвращал0, а API log print limit=3 —200/(no log entries). Исправлен SDK: чтение default memory с проекцией полей, последние N строк в native chronological order, максимум200. Невалидный limit отклоняется до опроса. Это лимит вывода: native buffer читается целиком перед slice; лимит сетевой передачи не обещается.

Проверены реальные API limits3/50/500→3/50/200 на каждом CHR, own marker виден, latest native IDs совпадают; limit0→400. Live терминал1280/320 получил по3 реальные строки, очистил поле команды после успеха и не имеет document overflow. Уточнена исходная подпись: «REST: каждая команда — отдельный запрос. Результат появится после ответа API.»; постоянная фраза о непроверенном соединении больше не противоречит успешному результату. ReUI Frame/Button/Input и base-nova сохраняются, vendor/layout не менялись.

Профильный HTTP SDK test (tail/default50/cap200/short/empty/invalid limits/401) passed, включён в npm test:exec. HTTP route/empty-versus-error и signed JWT/RBAC passed; backend build passed; source-only TypeScript и frontend production build passed. Scoped ESLint страницы/тестов passed; SDK lint имеет две исходные prefer-const ошибки125/899, проверка с отключением только этой rule passed. Обычный root tsc захватил ignored historical tmp и failed; существующий source-only config passed. Initial SDK test sandbox EACCES исправлен разрешённым loopback запуском. Первый UI assertion сравнивал newline string с отдельными div и failed; исправлен только способ проверки, final2/2 passed. Эти initial failures не скрыты и не прибавлены к уникальным сценариям.

Развёрнуты production backend/frontend ux-log133; backend/PostgreSQL healthy, frontend running/live UI. SDK source и compiled output SHA256 совпали с Docker; source страницы совпал с build context. Сохранены private rollback env и предыдущие образы. Только script/info markers добавлены в default logs; журнал не очищался, новых конфигурационных/VPN fixtures нет, оба CHR доступны, пароли не менялись. До/после и проверки, live UI.

Следующий134 — external CRL distribution/failure и оставшаяся матрица. Полная итоговая регрессия после последнего product изменения ещё требуется;12.5 открыт.

Референс Схема
ReUI App Shell12 Устройство → log print limit=N → default memory tail → ответ API → реальные строки

12.5.134 — внешняя загрузка CRL и отказ HTTP endpoint (2026-10-11)

Первый CHR выпустил собственные CA/client certificates с CDP; второй импортировал только public PEM, private-keys-imported0. Публичный DER CRL успешно разобран OpenSSL. Временный HTTP endpoint на Debian161.104.46.222:18084 отдавал только точный CRL path с Content-Length/Connection close. Фактические downloader GET от104.165.244.7 зафиксированы; dynamic CRL для CA и client в итоговом snapshot оба invalid=false/expired=false/revoked0.

Для независимого static CRL URL с отсутствующим path сервер вернул404 фактическому downloader. Строка осталась invalid=true/cert=none; ранее загруженные валидные CA/client CRL сохранились. Это принятие HTTP download/404/cache preservation, а не доказательство IKE refusal для сертификата с недоступным собственным CDP. Новый VPN tunnel здесь не создавался: проверяется инфраструктура распространения CRL. Отказ IKE, истёкший/повреждённый CRL, часовой refresh и немедленное завершение existing IKE остаются открыты.

Initial attempts сохранены полностью.1: manual download400/in progress и cleanup preflight failed, поскольку RouterOS потребил публичные файлы после импорта; exact scoped recovery убрал own chain/files/cache, остальные файлы сохранены.2: direct CHR-to-CHR CRL не загрузился за20s, cleanup10×2 passed.3: receiver /tool/fetch к direct CHR URL получил remote disconnected while in HTTP exchange, хотя Debian GET200; точная причина неизвестна, настройки HTTP/Firewall не менялись.4: временный endpoint дал valid CRL control, но повторный manual download во время automatic job вернул400/in progress; cleanup passed.5: busy receipt учтён отдельно, ожидается actual downloader request/status; valid+404/cache control и cleanup passed. Эти отказы не переименованы в success; direct distribution между CHR не принята.

CRL-use/download второго CHR восстановлены точным сравнением исходного settings object. Own logger/action, issuer chain, imported certificates, exports/uploads и CRL cache удалены после exact ownership preflight. Набор IDs10 коллекций на каждом CHR совпал с baseline итогового запуска; endpoint closed, порт18084 больше не слушается, Compose one-off завершён. Default buffer не очищался; flash directory/default/public/metadata/195.195.195.195/32 сохранены; пароли не менялись. Backend/PG healthy, frontend ux-log133 running; source/runtime/UI не менялись, build и регрессия не повторялись. Все попытки и итоговый протокол.

Следующий135 — certificate-bound missing/expired/malformed CRL и IKE enforcement с новым успешным контролем.12.5 открыт.

Референс Схема
ReUI List9 Own CA → public certificate/CDP → HTTP200 CRL → valid cache → own404 → invalid row → scoped cleanup

12.5.135 — недоступный CRL привязанного сертификата и реальный IKE (2026-10-11)

Создан собственный certificate-authenticated tunnel на CHR2; client CA/certificate выпущены CHR1 и импортированы в responder только публично. Собственный responder CA/server key создан native на CHR2. Linux strongSwan использовал собственный client key/private CA и точный public server certificate pin. CRL-use/download=yes; distinct Linux containers/addresses сохранены для трёх фаз.

  1. Валидный external CRL для CA/client загружен: IKE/ESP established, Ping3/3, API online=true.
  2. Тот же certificate CDP endpoint отвечает404; own CRL cache сброшен только после проверки ownership всех сертификатов/URL, invalid caches подтверждены. Native RouterOS ответил AUTHENTICATION_FAILED в обоих запусках; scoped log первого запуска — «failed to validate path: CRL not found» для собственного client certificate. Established0/API online=false. Это явный PKI отказ, не inference по timeout.
  3. Endpoint снова отдаёт signed valid CRL, оба cache valid; новый Linux container: IKE/Ping3/3/API online=true.

Первый запуск прошёл1–2, но recovered control получил IKE_INIT timeout без ответа и не был принят как восстановление. Его полный протокол сохранён, exact transport cause неизвестен. Повторный полный запуск прошёл три фазы; возможный bounded transport retry записывается отдельно, не увеличивает число уникальных сценариев. Оба запуска и итог.

CRL settings восстановлены точным сравнением. Own endpoint/logger/CA/certificates/private exports/credentials/Linux clients/network/IPsec identity/peer/policy/group/profile/proposal/mode-config/pool/bridge/address удалены по ownership checks.18 наборов IDs на каждом CHR совпали с baseline; private files removed, Docker cleanup, порт18084 закрыт. Existing/default/public/metadata/195.195.195.195/32/flash directory и пароли сохранены. Crypto dumps в evidence не включены, сохранены только выбранные auth/CRL сообщения.

Source/runtime/UI не менялись; действующий backend/frontend ux-log133. Следующий136 — повреждённый и подписанный истёкший CRL. Общая UI-регрессия после133 запущена отдельным процессом, её результат пока не заявляется. Немедленное завершение существующего IKE при отзыве, другие ОС и SLA ещё не приняты;12.5 открыт.

12.5.136 — повреждённый и подписанный истёкший CRL в IKE (2026-10-11)

В собственном external-CA tunnel проверены четыре payload на одном certificate-bound CDP: valid DER → HTTP200 malformed text → signed expired DER → original valid DER. Между фазами own cache сбрасывался после certificate/URL ownership preflight, CRL-use/download=yes. Private CA key использован только в0700/0600 временных файлах для подписания CRL, затем удалён. OpenSSL проверил подпись expired DER точным собственным CA; lastUpdate=now−2h, nextUpdate=now−1h. Часы CHR/Debian не менялись.

Оба positive controls установили IKE/ESP, Ping3/3 и API online=true. Malformed payload дал invalid=true caches, AUTHENTICATION_FAILED/established0/API offline. Signed expired payload был распознан RouterOS как invalid=false/expired=true, но новое IKE тоже получило явный AUTHENTICATION_FAILED/established0/API offline. Это четыре уникальные фазы без retry в итоговом запуске; отказ не выводится из сетевого timeout. Per-phase log сохраняет выбранную auth metadata; список expired может содержать earlier malformed reason и не выдаётся за отдельный точный текст причины expiry.

Own certificates/CA/exports/imports/private credentials/Linux containers/network/endpoint/loggers/tunnel config/pool/bridge/address удалены.18 наборов IDs×2 совпали с baseline, CRL settings restored exact, endpoint closed/порт18084 не слушается. Default/public/metadata/195.195.195.195/32/flash directory и пароли сохранены. Четыре фазы, подпись и cleanup; OpenSSL CRL date options.

Source/runtime/UI не менялись, действуют backend/frontend ux-log133. Следующий137 — external revocation при existing IKE и новый handshake. Уже запущенная общая UI-регрессия после133 продолжается; её итог будет отдельным последующим блоком, без объявления успеха заранее. Другие ОС/SLA/часовой refresh/immediate active-session revocation остаются открыты;12.5 открыт.

12.5.137 — внешний отзыв сертификата и существующая IKE-сессия (2026-10-11)

Собственный external-CA tunnel подтвердил IKE/Ping3/3. Затем CHR1 отозвал собственный client certificate. Свежий CRL содержит его точный serial, подпись проверена собственным public CA; CHR2 загрузил CA/client cache valid с revoked count1. Новый Linux client получил AUTHENTICATION_FAILED; scoped RouterOS log — «revoked by CRL cert is revoked by crl».

Уже установленная IKE-сессия в коротком наблюдении сохранилась и продолжила Ping3/3. API online=true корректно отражал именно эту старую сессию, а не успех нового handshake. После явного terminate только собственного старого IKE API стал offline; ещё один новый revoked client также получил AUTHENTICATION_FAILED/established0/API offline. Поэтому отзыв/обновление CRL не выдаётся за гарантированное немедленное завершение уже установленного туннеля. Подпись/serial, старый IKE, два отказа и cleanup.

Own logger/certificate chains/exports/imports/private credentials/Linux containers/network/tunnel config/pool/bridge/address/HTTP endpoint удалены.18 наборов IDs×2 restored, CRL settings object восстановлен точно, port18084 closed. Default/public/metadata/195.195.195.195/32/flash и пароли сохранены. Source/runtime/UI не менялись; действуют backend/frontend ux-log133. Ключи и crypto dumps в evidence не сохранялись.

Следующий138 — intermediate CA certificate chain. Общая UI-регрессия после133 продолжается и будет принята только по итоговому протоколу. Другие ОС, долгие нагрузки, periodic refresh и немедленное завершение existing sessions ещё не приняты как гарантии;12.5 открыт.

12.5.138 — промежуточный CA и повторная аутентификация (2026-10-11)

CHR1 выпустил собственную RSA2048 chain Root CA → Intermediate CA → client. Root/intermediate имеют CA BasicConstraints, leaf — CA=false; обе подписи проверены Node X509, полная цепочка/сроки/constraints прошли OpenSSL verify. CHR2 импортировал три public certificates и загрузил три valid/nonexpired CRL cache через два собственных CDP path. Отдельные native responder CA/server key созданы на CHR2.

Linux strongSwan с собственной client private key, explicit public Root/intermediate trust и точным server certificate pin установил IKE/ESP: Ping3/3/API online=true/конкретный VIP. Reauth завершился успешно, IKE id изменился1→2; новый IKE/ESP снова Ping3/3/API online/VIP. Профиль не менял auth algorithms/правила существующих сетевых операций. Полная цепочка, CRL, IKE/reauth и cleanup.

Own issuer chain удалена только после доказательства ownership всех descendants/отсутствия references. Own responder/imports/exports/private credentials/Docker client/network/endpoint/loggers/cache/tunnel objects/pool/bridge/address удалены;18 наборов IDs×2 restored, CRL settings restored exact, порт18084 закрыт. Default/public/metadata/195.195.195.195/32/flash directory и пароли сохранены. Source/runtime/UI не менялись; backend/frontend ux-log133.

Принята именно описанная native RSA chain и один Linux client. Arbitrary custom OIDs/policies/path length/missing chain/intermediate revocation/прочие ОС и полная production PKI не приняты. Следующий139 — дождаться итогов текущей общей UI-регрессии, выполнить context/source series и сохранить точный итог с сохранением исходных evidence/screens.12.5 открыт.

12.5.139 — общая регрессия, сверка Docker и реальный RIPE (2026-10-11)

После последнего продуктового изменения133 выполнена полная main UI-серия:1244/1244 passed, затем последовательно context/source/backend switch:221/221 passed. Итого1465 уникальных сценариев, оба exit0, без retries/delta rerun. Это production UI code с HTTP mocks/изолированными источниками, а не1465 живых RouterOS операций. Source не менялся во время обеих серий; production build/live UI133 и native135–138 остаются отдельными доказательствами.

С текущих tracked non-test backend/contracts source inputs построен manifest984 emitted outputs. Все984 совпали с actual Docker backend ux-log133 после CRLF→LF; missing0/different0. Старые вложенные local dist/backend/src outputs исключены. Создан input manifest906 файлов, но equality всех raw inputs/воспроизводимость frontend binary этим не заявляются. Нового build не требовалось: runtime source не менялся.

Реальный production RIPE service в отдельном процессе, без чтения/записи рабочего кеша, обогатил194.226.121.150 и104.165.244.7: network-info/maxmind-geo-lite/as-overview200, prefix/ASN/holder/country/coordinates получены. Это provider metadata, не гарантия физического положения хоста и не complete NetFlow pipeline. Дополнительный no-fetch контроль с198.18.139.1 failed: benchmark IPv4 ошибочно отправлен upstream. Private192.168/loopback контроль не вызвал запросов; public cache hits проверяются отдельно в следующем блоке. Этот отказ сохранён, весь RIPE test не объявлен success. Регрессия, compiled hashes и partial RIPE.

Перед регрессией сохранены586 existing evidence files.125 автоматически изменённых файлов восстановлены; все исходные SHA256 совпали, включая восемь pre-existing dirty GRE/VXLAN PNG. Новые135–138 evidence не затёрты. Подробные временные logs/snapshots в ignored tmp; побочные generated screenshots не включены в коммит. Source/runtime не менялись; backend/frontend ux-log133. Следующий140 — исправление фильтра специальных IPv4 согласно IANA, профильные backend/flow проверки, build/deploy и повторный live RIPE.12.5 открыт.

12.5.140 — специальные IPv4, RIPE и изолированная SQL-приёмка (2026-10-11)

Исправлен isNonPublicIp: benchmark198.18/15, TEST-NET ranges, reserved240/4 и non-global IETF assignments исключены из внешнего RIPE lookup. Глобальные PCP/TURN anycast192.0.0.9/10 сохранены eligible. Фиксированные CIDR masks вычисляются один раз; hot flow predicate больше не разбирает строки CIDR/адреса для каждого range. IPFIX tuples, NAT, network config и DB schema не менялись.31 boundary/exception checks и stale public-cache bypass/no-fetch тесты passed; IANA.

Local test:traffic-flow (20 scripts) exit0, но шесть SQL modules включали PG skips — не объявлены pass. Все шесть затем проверены against production candidate в четырёх собственных temporary PostgreSQL DBs. Parent создаёт exact own DB, child проверяет current_database до test import, DATABASE_PATH/GEOIP_DIR вынесены в ephemeral container; original DB/legacy SQLite не использовались fixtures. Все четыре DB удалены с owner/prefix check, включая failed runs.

Initial failures сохранены и исправлены в tests: analytics зависел от чужого hardcoded server7 (FK); теперь создаётся own server, все SQL scoped, finally cleanup. Map-hops использовал TEST-NET как вымышленные публичные сервисы; fixtures получили eligible synthetic IPv4, assertions не ослаблены. Statistics не создавал historical server_snapshots partition; теперь создаёт exact fixed-date partition. Ingest/analytics/map-hops/purge/facts-rebuild/statistics SQL modules passed across bounded runs; прошедшие modules без необходимости не повторялись. Mock upstream failure fixture перенесён с TEST-NET на eligible address и явно подтверждает реальный вызов stub.

Changed-file ESLint, backend production build, RIPE/IP profile tests passed. Реальный production RIPE service снова обогатил два публичных IP; повторный public cache hit и special/private controls дают0 дополнительных requests. Действует backend ux-ripe140/frontend ux-log133; backend/PG healthy. Все984 emitted outputs совпали с candidate Docker, actual deployed IP service SHA256 совпал; private rollback env/old image сохранены. Полные попытки/проверки/границы.

Readonly live traffic/statistics smoke320: rendering200/no overflow/pageerror0. При этом traffic отправил initial requests /api/traffic/servers/srv1 и /interfaces, оба400/id is required; это existing mock-id hydration/catalog gate defect, не часть IPv4 fix и не скрытый success. Smoke. Следующий141 — gate live fetch до подтверждённого numeric server id/catalog. IPv6 special ranges — отдельно. Full UI1465 accepted139 до backend-only140; backend/SQL/live delta проверены отдельно, frontend не менялся.12.5 открыт.

12.5.141 — подтверждённый каталог перед запросами трафика (2026-10-11)

Исправлен обнаруженный140 initial live defect: details/interfaces requests отправлялись с demo ID srv1 до загрузки реального каталога и получали400. Теперь details, interfaces и SSE ждут positive safe numeric ID, присутствующий в подтверждённом каталоге текущего backend. Смена источника данных лишает старый каталог права запускать запросы; смена периода не сбрасывает выбранный интерфейс. Demo-режим и backend API не менялись.

17 профильных E2E passed: два новых сценария удерживают запрос каталога и проверяют отсутствие любых individual requests до подтверждения, затем успех numeric ID или503 без запросов к серверу; остальные проверяют историю/ошибки/гонки периода/интерфейсов и SSE. Changed-file ESLint и source-only TypeScript passed; production Docker frontend build passed. Runtime frontend ux-traffic141, backend ux-ripe140 сохранён. Private rollback env и предыдущий образ оставлены.

Readonly live /traffic1440 и320: каталог и numeric interfaces200, initial srv1/400 отсутствуют, pageerror0, horizontal overflow нет. Протокол. Это приёмка начальной загрузки с реальным текущим каталогом, а не полной цепочки NetFlow ingestion/throughput. Сетевые объекты и пароли не менялись. Следующий отдельный блок — IPv6 special registry guard; оставшаяся внешняя приёмка перечислена в матрице.12.5 открыт.

12.5.142 — специальные IPv6 и рабочий кеш RIPE (2026-10-11)

Исправлены две причины недостоверного обогащения IPv6: неполная проверка служебных адресов и отсутствие IPv6-поиска в RIPE-кеше. Теперь документальные/benchmark/discard/dummy/SRv6/local/multicast адреса и некорректные записи не запрашивают RIPE, даже при старом seeded metadata. Более конкретные глобальные назначения внутри2001::/23 сохранены; Teredo/6to4 со статусом N/A не объявлены non-global. Правила сверены с IANA, eligibility не гарантирует маршрутизацию.

Добавлены validated128-bit parser, /48 buckets и отдельные широкие IPv6-префиксы. Lookup выбирает самый точный свежий CIDR, учитывает замену/просрочку/инвалидацию. Отрицательный кеш использует /128 и не затрагивает соседний адрес. Expanded и compressed записи дают одинаковый результат; IPv4-mapped hex/dotted/expanded формы нормализуются к одной IPv4 host identity. Host /128 удаляется перед RIPE resource request. Тест с3000 unrelated /48 подтверждает, что lookup не сканирует их все. Фиксированные special CIDR вычисляются один раз.

Changed-file ESLint, backend production build и IP/RIPE profile tests прошли локально и в candidate. Потребители classification/destination/GeoIP passed. Первый local aggregate остановился на GeoIP из-за ограниченного доступа к temporary files; разрешённый отдельный rerun passed, причина и неуспешный запуск не скрыты. Шесть PG skips локального запуска не считаются успешными: все шесть SQL-модулей затем прошли одним запуском в собственной temporary DB, удалённой с owner check. Working DB и legacy SQLite не использовались fixtures.

Первый Docker запуск указал отсутствующий Dockerfile.backend; исправлен путь backend/Dockerfile, build passed. Все984 emitted production outputs candidate совпали с local build. Реальный RIPE API дал6 HTTP200 для Google и Cloudflare IPv6; cached sibling/expanded address и special/invalid controls дали0 новых requests. Service process отдельный, persistence выключена. Backend ux-ipv6142 развёрнут, /health и Docker health healthy; frontend ux-traffic141 сохранён. Live /traffic1440/320 passed без srv1/400/pageerror/overflow. Rollback env/image сохранены, сетевые настройки и пароли не менялись.

SQL/live RIPE и границы, browser smoke. Это не доказывает IPv6 WAN connectivity или полный exporter→ingest→SQL→UI pipeline. При live RIPE выявлены координаты0/0 для Cloudflare; следующий143 — проверить, не подменяются ли отсутствующие значения нулями. Далее — IPv6 flow pipeline.12.5 открыт.

12.5.143 — неизвестные координаты RIPE без ложной точки на карте (2026-10-11)

При real RIPE IPv6 acceptance142 Cloudflare получил координаты0/0 после ответа upstream с country=? и latitude/longitude=0. Эти данные не подтверждают положение узла. Исправлен pickGeo: принимается только полная пара finite numeric coordinates в диапазонах±90/±180; empty strings, boolean, numeric strings, missing/partial/out-of-range coordinates дают null pair. Unknown-country0/0 также даёт null. Действительный ноль на экваторе/меридиане и явно заданный known-country0/0 сохраняются. ASN country fallback не превращает неизвестную точку в подтверждённые координаты.

16 новых end-to-end service cases в RIPE profile прошли локально и в production candidate. ESLint, backend build,984 compiled outputs comparison passed. Три затронутых SQL-потребителя (analytics, map-hops, facts-rebuild) прошли в собственной temporary PostgreSQL DB; она удалена с owner check, working DB не использовалась fixtures. Real RIPE снова дал6 HTTP200 для Google/Cloudflare IPv6. Upstream unknown-country0/0 сохранён в протоколе вместе с service lat/lng=null, ASN/country retained. Cache controls не сделали новых queries.

Backend ux-geo143 развёрнут, health healthy, frontend ux-traffic141 сохранён; read-only traffic PC/mobile smoke выполнен отдельно. Rollback env/image сохранены. Полный протокол, browser smoke, RIPE API.

Unknown0/0 policy основана на наблюдённом live ответе, а не на заявлении о поведении всех providers. Старые persisted entries с уже потерянной raw provenance не переписываются: исправлены новые fetches, прошлый cache живёт по прежнему TTL. Изменений schema/UI/theme или настроек CHR нет, пароли не менялись. Полная физическая точность геолокации и licensed GeoLite2 file acceptance не заявляются. Следующий144 — реальный IPv6 IPFIX UDP→collector worker→SQL в изолированной БД.12.5 открыт.

12.5.144 — IPv6 IPFIX через UDP, production worker и PostgreSQL (2026-10-11)

Новый controlled dual-stack IPFIX fixture воспроизвёл реальный parser defect: zero IPv4 placeholders заменяли уже прочитанный IPv6 или блокировали последующее IPv6 field. Исправлены source/destination поля в обоих порядках: usable IPv4 сохраняет прежний приоритет, zero IPv4 не подменяет usable IPv6. Expanded unspecified IPv6 теперь распознаётся так же, как ::, включая NAT fallback. Новая проверка добавлена в test:traffic-flow; parser assertions исполняются всегда, UDP/SQL часть требует exact own MMAPP_OWN_TEST_DB/current_database before migrations, иначе явно skip.

21 local traffic-flow scripts exit0; existing6 PG modules и UDP own-DB часть имели явные skips и не объявляются pass. Changed-file ESLint и backend production build passed. Candidate984 emitted outputs matched. Затем в own temporary PostgreSQL DB запущен настоящий production collector worker с UDP loopback socket: отправлены template и data datagrams, приняты6 IPv6 flows с forward/reverse public peers и documentation/benchmark/multicast controls. Проверены каждый src/dst, bytes/packets; raw/minute сохраняют все25200B/42 packets. Hour/day Internet facts по существующим правилам включают только три public flows:7200B/12 packets. Worker dropped0/error0, graceful shutdown acknowledged; SQL totals проверены после flush.

Две initial fixture failures сохранены: в первом запросе использовались неверные SQL column names src_ip/dst_ip (actual src/dst); во втором ожидалось равенство all traffic и Internet facts, что противоречит существующим правилам. Исправлены только ожидания/запрос теста, assertions каждого адреса/объёма не ослаблены, production aggregation/filter/schema не менялись. Third attempt passed. Все3 own temporary DBs удалены с owner check; working DB и legacy SQLite fixtures не использовались.

Backend ux-ipfix144 развёрнут, health healthy; frontend ux-traffic141 сохранён. Live traffic1440/320 passed без initial srv1/400, page errors/overflow. Rollback env/image оставлены. Все попытки и границы, browser smoke.

Это real UDP/worker/SQL path с синтетическим exporter через IPv4 loopback transport, не native RouterOS IPv6 export/outer transport и не maximum throughput. CHR configuration/passwords не менялись. Следующий145 — проверить возможность native RouterOS IPv6 exporter и populated API/UI на собственных objects/DB.12.5 открыт.

12.5.145 — настоящий RouterOS IPv6 IPFIX и заполненный интерфейс (2026-10-11)

Оба CHR доступны с прежними credentials, RouterOS7.24.5. Исходно Traffic Flow disabled/targets empty. Созданы собственные GRE-пара с allow-fast-path=false и fd00:145:1::1/2/64, advertise=no. CHR1 временно экспортирует IPFIX только своего GRE, с short timeouts/one owned target. Native Ping прошёл5/5 в обе стороны; CPU/input-output path и IPv6 support сверены с официальным Traffic Flow manual, версия manual7.26, фактическая проверка7.24.5.

На Debian запущен отдельный application/production collector worker в own temporary PostgreSQL DB. Скопирована конфигурация только CHR1 без публикации credentials; worker слушает UDP48145, HTTP API доступен только через localhost18145/SSH. Native RouterOS sender, не synthetic fixture, передал IPv6 IPFIX records: production API содержит реальные ULA source/destination и positive bytes/packets. Deployed frontend ux-traffic141 проверен через явный relay реальных ответов отдельного backend: Sessions DOM содержит IPv6, PC1440/mobile320 API200/pageerror0/no document overflow. Screenshots сохраняют frame/current scroll position, не все строки одновременно. Initial UI attempts искали адрес на Applications summary и ошибочно выбирали button вместо actual tab; исправлено только обращение к существующей вкладке.

Тест не использовал main DB для seeded fixtures; обычный background polling главного приложения оставался активным, поэтому абсолютное отсутствие background writes не заявляется. IPsec/WireGuard keys, пароли, исходные public/default/metadata routes не менялись. Native objects/GRE/IPv6 inputs принадлежат одному unique tag.

Автоматическая очистка восстановила Traffic Flow и удалила objects CHR1, но GET собственного GRE по ID на CHR2 вернул401. Child drain прошёл, own DB удалена. Read-only resource и полный каталог обоих CHR снова доступны с теми же credentials; причина одиночного GET401 не установлена, пароль не менялся. Recovery по свежему полному каталогу проверил exact comment/name/local-remote/address и отсутствие IDs в baseline; удалены только два оставшихся objects CHR2 обычным DELETE. Все12 collection projections×2 и Traffic Flow/IPFIX fields/IPv6 settings совпали с исходными. Initial failure и recovery сохранены, не заменены гладким success.

Own container удалён после проверки exact container ID; UDP48145/HTTP18145 и отдельный SSH tunnel закрыты, основной стенд backend ux-ipfix144/frontend ux-traffic141 healthy. Начальный неверный host port81245 был отвергнут до запуска/изменений, исправлен18145. Native/API/cleanup receipt, UI receipt, PC screenshot, mobile screenshot.

Доказан IPv6 ULA inner/native IPFIX поверх IPv4 GRE/export transport, не public IPv6 WAN/outer или throughput/произвольные clients. На live UI ICMPv6 подписан numeric58, IPv6 endpoints с портом требуют однозначного bracket format; следующий146 — улучшить эти подписи, сохранив ReUI/Frame/base-nova.12.5 открыт.

12.5.146 — понятные подписи ICMPv6 и адресов IPv6 с портами (2026-10-11)

После native145 устранены две неоднозначные подписи. protoName/applicationName protocol58 теперь ICMPv6 вместо numeric58 или58/—. Existing ICMP, TCP/UDP, unknown numeric fallback сохранены. В существующей ReUI Sessions table IPv6 с портом выводится [IP]:port, включая packet-tuple tooltip; IPv4:port и IPv6 без порта не изменились. Frame/base-nova/vendor компоненты и порядок колонок сохранены.

Parser/interface/classifier profiles прошли локально и в production candidate; последние выполнены без подключения к working PostgreSQL. Changed-file ESLint, source-only TypeScript, backend/frontend production Docker builds и984 emitted backend output comparison passed. Existing28 flow E2E прошли первым запуском. Два новых1440/320 tests сначала получили неверный fixture (sessions вместо conversationsList), что выявило отсутствие HTTP DTO guard; corrected fixture повторён отдельно,2 passed. Проверены visible IPv6 TCP/UDP endpoints, tooltip, portless ICMPv6, IPv4 compatibility и отсутствие document overflow. Итого30 принятых сценариев across attempts; первый failure не скрыт и прошедшие28 не повторялись.

Backend/frontend ux-labels146 развёрнуты; backend/PG healthy, deployed traffic PC/mobile loading passed. Label/check receipt, readonly smoke. Это live rendering/catalog smoke после label delta, а не повтор populated native145. Raw protocol integer сохранён в DB; talker/analytics response отображает его через новый protoName, schema/migration не требовались. Rollback env/images оставлены, device settings/passwords не менялись.

Следующий147 — применить существующие contract schemas к HTTP analytics/monthly, как уже сделано для SSE/settings, чтобы malformed200 response давал existing error/retry state без ложных нулей или page crash.12.5 открыт.

12.5.147 — подтверждённые HTTP данные аналитики и месяца (2026-10-11)

HTTP analytics/monthly раньше принимались как typed JSON без runtime schema check: malformed200 с отсутствующей conversationsList мог упасть при render. Теперь reused existing contract schemas и flowConfirmed error state, как в SSE/settings. Неверные required fields и negative RX/TX series отклоняются; monthly.month обязан совпадать с requested month. Existing Alert/Повторить аналитику показывает понятную ошибку, retry сохраняет server/range/month. Никаких false zero defaults для отсутствующих обязательных данных.

Необязательные overlay/wire measurements могут быть неизвестны отдельно от основных счётчиков. Invalid optional numbers (missing/null/string/negative/nonfinite) нормализуются в undefined, UI сохраняет Нет данных; legitimate numeric0 и valid core остаются. Это сохраняет partial-data UX и прежнюю проверку, вместо объявления всего DTO недоступным. Contract schemas/backend response shapes не менялись.

34 профильных E2E приняты across attempts:31 passed в первом запуске; strict optional metric rejection и два monthly fixtures без server catalog дали3 failures. Исправлены partial metric handling и fixtures, повторены только эти3, все passed. Covered incomplete analytics/monthly, negative series, different month, no pageerror/no false speed, retry with identical scope, existing flow races/SSE/metrics/month/table and IPv6 labels. ESLint/source-only TypeScript/frontend Docker build passed. Receipt.

Frontend ux-http147 развёрнут, backend ux-labels146 сохранён. Настоящие analytics/monthly HTTP200 текущего backend прошли схемы; month2026-10 совпал с запросом. Live PC/mobile smoke. Это contract compatibility/read-only smoke с текущими lab data, не новый populated WAN test. Rollback image/env сохранены, device/password changes нет.

Следующий148 — не запускать scoped flow HTTP/SSE до подтверждённого выбранного элемента каталога и не превращать malformed serverId в aggregate request.12.5 открыт.

12.5.148 — подтверждённый срез потоков без агрегатной подмены (2026-10-11)

Исправлено продолжение initial srv1 defect для flow mode. Scoped analytics/SSE теперь ждут выбранный элемент current provider/range/scope catalog. Server ID обязан быть positive safe numeric и присутствовать в exporters/monthly catalog, user ID — в confirmed clients. Catalog pending/error не запускает запрос для guessed/old selection; analytics loading не висит после catalog failure. Monthly history сохраняет supported non-exporting/disabled catalog entries, device polling не добавлено.

Backend больше не извлекает numeric prefix из1suffix и не превращает srv1/invalid/unsafe IDs в omitted filter/all-servers aggregate. Возвращается400 Некорректный идентификатор сервера. Missing/empty optional filter сохраняет aggregate semantics. Query validation выполняется до acquisition MAX4 SSE slots, поэтому malformed requests не съедают live quota.

21 invalid query cases (7 IDs×analytics/monthly/live) прошли source/candidate; full4 slots остались доступны. Новый тест сначала импортировал несуществующий non-scoped package; исправлен на existing @fastify/type-provider-zod без установки dependencies, проверки затем passed. Backend test включён в обычную traffic-flow series.36 E2E одним запуском passed: delayed/error catalog без any scoped request, затем only confirmed id1; existing flow/SSE/races/month/DTO/IPv6 labels. ESLint/source-only types/both production builds и984 emitted backend outputs comparison passed.

Backend/frontend ux-scope148 развёрнуты, health healthy. Real API9 malformed cases400 и2 valid scoped cases200; receipt, PC/mobile readonly smoke. No native changes/password changes/schema/theme changes; rollback env/images сохранены. Populated native145 не повторялся без необходимости.

Следующий149 — строгий month input и calendar bounds: invalid month не должен подменяться текущим или выдаваться за подтверждённый zero report.12.5 открыт.

12.5.149 — календарный месяц без тихой подмены и ложных нулей (2026-10-11)

Supplied malformed month раньше подменялся current UTC month на route; impossible month мог вернуться из service как zero report. Теперь непустой параметр передаётся для strict YYYY-MM/month1..12/year!=0000 validation, invalid получает400 Некорректный месяц отчёта до SQL. Missing/empty optional month сохраняет прежний current UTC default. Runtime non-string тоже отклоняется.

Calendar bounds больше не используют Date.UTC дляyear1..99 (он превращает их в1901..1999) и не режут extended ISO date at year10000. Integer year/month arithmetic даёт exact next-month day1, average bps используют Gregorian month length/leap rule. Source tests проверяют нормальный month/year rollover,1/99/9999, invalid input rejection before SQL. Normalized labels/DB schema не менялись.

В candidate Docker5 SQL intervals прошли в own temporary PostgreSQL DB:0001 January,0099 December,1900 February28days,2000 February29days,9999 December/end10000. In-month1200B retained, next-month12000B excluded, average country bps matches exact month length. Fixture DDL выполняется только после exact own DB/current_database check, DB удалена с owner check; working DB/legacy SQLite не использовались fixtures. Both month and scoped-query tests добавлены в normal traffic-flow series. ESLint/backend build/984 output comparison и6 frontend scoped/context tests passed; frontend не пересобирался.

Backend ux-month149 развёрнут, frontend ux-scope148 сохранён, health healthy. Real API6 invalid months400 иcorrect2026-10→200/same month; initial smoke helper Fetch.status method typo исправлен только в harness, сохранён как setup error. Full SQL/live receipt, PC/mobile smoke. Device/password changes нет, rollback retained. Это не расширяет UI на future month selection.

Следующий небольшой150 — понятные подписи Sessions columns вместо App/Proto/Iface/JH/EN, сохраняя ReUI grid/Frame/base-nova/data semantics.12.5 открыт.

12.5.150 — понятные названия колонок сессий (2026-10-11)

Существующая ReUI Sessions grid получила ясные подписи вместо внутренних сокращений:

Было Стало
JH Экспортёр
EN Выходной узел
App Приложение
Proto Протокол
Iface Интерфейс
Напр. Направление
Download / Upload (tooltip) Получение / Отправка

Column IDs, accessors, sorting/filtering, row values, direction meanings, grid layout/Frame/base-nova/vendor не менялись. Экспортёр описывает serverName корректнее, чем JH: данные могут поступать с разных типов устройств. IPv6 bracket/ICMPv6 labels146 сохранены.

Existing viewport1440/320 cases passed: endpoint/tooltip/IPv4/ICMPv6 behaviour иno document overflow. ESLint passed. Первый types check совпал с Next dev записью generated routes.d.ts и прочитал незавершённый файл; после окончания E2E/webserver TypeScript повторён последовательно и passed без изменения source. Production frontend build passed. Frontend ux-sessions150 развёрнут, backend ux-month149/PG healthy; receipt, readonly PC/mobile smoke. Rollback image/env сохранены. Network/password/device/schema changes нет; populated native145 не повторялся для copy-only delta.

Окно завершает coherent группу IPv6/NetFlow142–150. Следующий151 — application GRE IPv6 address lifecycle. Native inner proof109/145 уже есть, но gre-live читает только /ip/address, а entity-snapshots create/restore/delete всегда используют IPv4 resource. Нельзя просто объединить IPv6 catalog без family-safe write/delete paths: одинаковые ROS IDs в разных namespaces и dynamic link-local требуют отдельной обработки. План151: static IPv6 catalog, family-aware paths, create/update/restore/delete+legacy snapshot compatibility, запрет неоднозначной смены primary при multiple addresses, profile/native own tunnel cleanup иUI metadata. Сначала проверить лимит; не выпускать partial family migration.12.5 открыт, public IPv6 WAN/outer и внешние integrations остаются в матрице.

12.5.151 — управление статическими IPv6-адресами GRE (2026-10-11)

GRE читает IPv4 и IPv6 адреса; динамические адреса исключены из управления. Ошибка любого address catalog или неверный формат ответа останавливает чтение/запись, неполный ответ не становится пустым снимком. Выбранный выключенный сервер также исключён из опроса.

Create/PATCH/restore/delete выбирают /ip/address или /ipv6/address по проверенному CIDR; одинаковый RouterOS ID в разных семействах безопасен. Новые снимки содержат все статические адреса, disabled/advertise/comment/no-dad. PATCH меняет только целевой GRE, сохраняет дополнительные адреса; очистка поля передаёт явную пустую строку. Восстановление старой ревизии при нескольких текущих адресах возвращает409 до записи. Неоднозначные ID/name и переименование также409. Expanded/compressed IPv6 сравниваются по одному ключу. Применение from-pool/EUI-64 остановлено с объяснением: их выделение не принимается за обычный literal static address.

Существующие ReUI/Frame/base-nova сохранены, добавлена подсказка IPv4/IPv6 с префиксом. Проверки: config-sync4 scripts (включая14 invalid POST/PATCH до DB/REST), gre-comment и selected-context tests; backend/source-only types/ESLint;15 GRE E2E; backend/frontend production builds;984 emitted outputs совпали. Первый E2E запуск не стартовал из-за sandbox Windows/SWC canonicalize access; разрешённый повтор прошёл.

Настоящие production Fastify handlers + выделенная PG база + оба CHR:18 API requests включая создание IPv6 пары, PATCH IPv6, сохранение дополнительных IPv4/disabled IPv6, history restore многoадресного снимка, legacy409 и ID/name409, смену IPv6→IPv4, очистку, восстановление и DELETE. Ping3/3 в обе стороны после running=true и address invalid=false. Первоначальный короткий Ping получил0 вместо ожидаемых3 и остановил первый сценарий; причина не доказана. Его результат и очистка сохранены отдельно, повтор не скрывает начальный отказ. Это короткий dataplane, не доказательство бесшовности/throughput.

Оба запуска: собственные объекты удалены,8 static collections×2 совпали с baseline, отдельные базы удалены. Пароли не менялись, public/default routes не трогались. Native parent читает исходные enabled server credentials; background polling главного приложения продолжался, отсутствие всех background SQL writes не заявляется. Runtime backend/frontend ux-gre151 healthy, live read-only PC/mobile catalog/form smoke прошёл после cleanup; native mutation принята через изолированную базу, deployed browser mutation не выполнялась.

Протоколы: native/cleanup, API/history, первый запуск, compiled parity, live UI.

Границы: IPv6 ULA inner по IPv4 GRE outer; IPv6 outer/public WAN, scale, длительное восстановление и from-pool/EUI-64 не приняты. Полная регрессия после139 не повторялась: выполнен профиль изменённых областей. Следующий152 — WireGuard IPv6 lifecycle;12.5 остаётся открытым.

12.5.152 — IPv6 lifecycle WireGuard и общий допуск выключенных серверов (2026-10-11)

WireGuard читает оба address catalogs; ошибки/не-массивы не превращаются в пустые данные. Catalog показывает активный статический адрес, новые snapshots сохраняют все статические адреса с disabled/advertise/comment/no-dad. Dynamic link-local исключён из управления. Create и PATCH address, history restore и delete выбирают семейство по CIDR; дополнительные адреса сохранены, legacy snapshot с несколькими текущими адресами409. Общий адресный planner переиспользован GRE/WireGuard; constructor alias GreRestoreConflict совместим. PATCH не переименовывает одновременно интерфейс и адрес.

Import подтверждает receipts в /ip/address и /ipv6/address раздельно, normalized IPv6 identities принимаются, automatic link-local не считается чужим static child. Lost/unconfirmed receipt не разрешает удаление по одному имени; rollback не удаляет IPv4 с совпавшим IPv6 ID. IPv6 RSC export использует /ipv6 address add +advertise=no, parser распознаёт IPv6 address line. Multiple/special address import и export явно отклоняются вместо тихой потери данных. Это single-address literal import/export, не произвольный RouterOS configuration codec. Существующий ReUI create sheet получил подсказку IPv4/IPv6; структура/Frame/base-nova сохранены.

При native приёмке обнаружено: getEnabledServerById ранее проверял только ID. Теперь общий getter допускает только enabled=true и полный корректный DB ID; WireGuard selected catalog также исключает disabled. Это влияет на использующих getter GRE/WireGuard/firewall/containers/traffic/overlay. Постоянный opt-in test network-disabled-server.test.ts делает33 API/SQL cases: три типа Home Router/Jump Host/Exit Node ×11 calls, factory любого ROS client запрещена, contacts=0, enabled positive control проходит.8 malformed IDs проверяются до SQL, включая unsafe/выход за integer DB range. Без MMAPP_OWN_TEST_DB SQL часть честно skipped; в собственном PG стенде выполнена и база удалена.

Проверки:56 node:test cases import/rollback/revision/delete, service/config/HTTP scripts, GRE config-sync и14 invalid GRE requests, containers/live-maps profiles;10 E2E (WireGuard IPv6/error-retained input PC/mobile, tables/menus и GRE smoke после общего planner), source types/ESLint; обе production сборки,984 emitted outputs совпали с окончательным backend.

Native изолированная PG + production handlers + оба CHR:29 API cases, native handshake0s и Ping3/3 в обе стороны после IPv6 invalid=false; create/PATCH/IPv6→IPv4/clear, multiple-address history restore, legacy409, export multiple409, RSC/conf single IPv6 export и реальный import/delete, disabled GET empty/PATCH404 с forbidden factory. После каждого запуска9 static collections×2 совпали, собственные интерфейсы/peers/адреса и PG базы удалены. Native source/cleanup не меняли пароли/public/default routes. Background polling главного приложения продолжался; отсутствие всех background SQL writes не заявляется.

Первый сценарий остановился из-за ошибки теста: ожидал200 от POST peer, фактический корректный201. После исправления сценарий прошёл весь native lifecycle, но завершающий disabled PATCH вернул500 из-за реального дефекта общего getter. Оба отрицательных протокола сохранены; getter исправлен,33 isolated API/SQL cases и полный native сценарий на финальном образе прошли. Frontend повторно не собирался из-за backend-only gate delta.

Runtime backend/frontend ux-wg152 healthy; deployed live read-only catalog/create-sheet на1440/320 passed после cleanup. Browser mutations покрыты controlled E2E, реальные RouterOS mutations — production handlers в выделенной базе. IPv6 ULA inner по IPv4 WireGuard outer, не IPv6 public WAN/client OS/throughput/scale/lost ACK physical acceptance. From-pool/EUI-64/multiple-address import/export остаются явными ограничениями; full regression после139 не повторялась.

Протоколы: native/cleanup, API/history/import/export, 33 SQL/API gates, до исправления getter, compiled, live UI.

Следующий153 — sustained OSPF/BFD-only gate и recovery на собственных GRE;12.5 остаётся открытым.

12.5.153 — граница OSPF/BFD и предупреждение конфликта состояний (2026-10-11)

В существующей OSPF странице ReUI/Frame/base-nova добавлено предупреждение последнего опроса: OSPF Full при наблюдаемом BFD Down/AdminDown. Correlation требует точный server/interface/neighbor IP, explicit active/useBfd=true, одну direct multihop=false BFD session и свежие данные; чужое устройство/интерфейс/peer, duplicate sessions, unknown/multihop/inactive/non-BFD template не создают вывод. Native Full/route states и правила RouterOS не меняются. Переход Проверить BFD сохраняет server/node context и атомарно снимает search, чтобы найденная сессия была видна. Референс остаётся существующий ReUI Data Grid/Frame, новые vendor components не устанавливались.

На обоих CHR собственные GRE198.18.153.0/30 и OSPFv2 loopbacks198.18.253.1/32↔2/32, hello1s/dead20s, BFD200ms×3. Два own firewall правила на CHR2 блокировали только UDP3784 input/output на own GRE с exact private src/dst. Protocol89/ICMP не блокировались; OSPF Hello отдельным packet capture не измерялся.51 native rounds около30s: BFD Down наблюдался, в поздних samples после20s оба OSPF neighbors Full и own route active. Это подтверждает отсутствие гарантированного постоянного route gate при BFD-only ACL loss; непрерывность каждого пакета/мгновенного состояния не заявляется. Data plane initial/fault/recovery Ping3/3×2. После удаления fault — BFD Up/Full/active, затем собственные firewall/OSPF/BFD/IP/bridge/GRE objects удалены.10 static collections×2 совпали с baseline; filter/BFD config order также сравнивался. Default/public routes и пароли сохранены.

UI native positive проверена в source Next dev3133 с настоящим backend8000, без JSON mocks и browser mutations:1440/320 показывают alert+native Full; переход ведёт к реальному Down, сохраняет server и очищает q. Скриншоты 1440, 320; мобильный экран визуально проверен.3 unit cases,9 controlled E2E с recovery/foreign/non-BFD/unknown и previous data-cache scenarios, source types/ESLint passed. Read-only deployed PC/mobile smoke после cleanup подтвердил отсутствие ложного alert.

Frontend production build прошёл с окончательным source context; frontend ux-ospf153 развёрнут, backend ux-wg152/PG healthy. Первоначальная SCP сессия истекла в ожидании пароля; первый frontend candidate был собран без delta и не развёртывался. Context пересинхронизирован/хеш проверен, финальная сборка повторена и принята. Backend code/build не менялись, broad regression не повторялась. Только собственный завершённый container6a521d… удалён после exact-ID/state check; background main polling продолжался, собственная SQL база не создавалась.

Правила конфигурации сверены с MikroTik BFD. Протоколы: native51 samples/recovery/cleanup, real source UI, deployed smoke.

Границы: sustained BFD-only gate не гарантирован на RouterOS7.24.5; программа показывает реально наблюдаемый конфликт и не навязывает новые network rules. IPv6/scale/independent WAN/continuous packet loss/SLA не приняты этим блоком. Следующий154 — OSPFv3 IPv6 routes; существующий catalog читает только /ip/route, требуется family-safe /ipv6/route.12.5 открыт.

12.5.154 — IPv6 маршруты OSPFv3 в API и интерфейсе (2026-10-11)

Каталог и selected/all OSPF reads получают /ip/route и /ipv6/route. Обе коллекции обязательны: ошибка/не-массив не становятся успешным пустым ответом. IPv6 rows имеют namespace ipv6: для native ID: одинаковые IPv4/IPv6 IDs не конфликтуют. IPv4 IDs сохранены, операция только чтения. Gateway parser предпочитает фактический nonblank immediate-gw, затем configured gateway; это сохраняет наблюдаемый интерфейс после %. Существующие ReUI tables/Frame/base-nova не менялись.

Backend build, config-sync, live-maps profiles (dual family ID collision, IPv6 read failure/malformed payload, link-local gateway/via, existing disabled/partial/unknown),9 OSPF data/cache/BFD E2E и984 compiled parity passed. Backend ux-ospf154 развёрнут с rollback copy; frontend ux-ospf153 сохранён, PG/backend healthy. Native проверка выполнена после profile/parity deployment на disposable lab; frontend/backend неподтверждённый candidate не публиковался.

На обоих CHR собственный GRE IPv4 outer, IPv6 link fd00:154:1::1/64↔2/64, loopbacks fd00:154:ff::1/128↔2/128, OSPFv3 router IDs198.18.254.1↔2. Interface templates принадлежат только own GRE/loopback, originate-default=never, use-bfd=no; public/default paths не менялись. Native neighbors Full и own learned IPv6 route active, Ping3/3×2. Catalog/selected API содержат ровно соответствующие remote loopbacks с ipv6: ID и actual link-local nextHop +own GRE via.4 production UI cases: оба устройства на1440/320, IPv6 prefix/family row ID/gateway/interface присутствуют в DOM, document overflow/page errors0. На mobile отдельные columns могут находиться в горизонтальном table scroll; все columns одновременно viewport-visible не заявляются.

Координационный harness ожидал ui.done180s и завершился exit1 до позднего сигнала. Исходный passed=false/timeout сохранён: не переписан на успех и не скрыт повтором. Это не API/OSPF/Ping отказ: соответствующие assertions и4 независимых реальные UI cases прошли. finally удалил own OSPF/GRE/bridge/IPv6 objects,13 static collections×2 совпали с baseline, включая IPv4/IPv6 routes/filter/ND. Background main polling продолжался; собственная SQL fixture база не создавалась. Пароли сохранены, оба CHR доступны. Остановленный own container удаляется только по точному ID/state, не по широкому filter.

Протоколы: native и timeout/cleanup, 4 real UI, compiled984. Конфигурация сверена с официальным OSPF.

Границы: IPv6 ULA inner по IPv4 GRE outer, single area/single path, BFDv6 выключен, IPv6 public WAN/outer, scale/interop/throughput/physical redundancy не приняты. Full orchestration script success не заявляется; production behavior/profile и независимые native/UI/cleanup proofs отделены от timeout. Следующий155 — BGP IPv6 session/NLRI;12.5 открыт.

12.5.155 — IPv6 BGP session и обмен NLRI (2026-10-11)

Без изменения production source/dependencies/build: на двух CHR созданы собственные GRE с IPv6 link fd00:155:1::1/64↔2/64, loopbacks fd00:155:ff::1/128↔2/128, private AS64555↔64556, afi=ipv6. Output.network использует own /ipv6/firewall/address-list. Input/output filters принимают только точный own/remote /128, default-originate=never и network-blackhole=no. Native sessions Established, каждый узел получил ровно1 собственный remote IPv6 prefix; initial/recovery Ping3/3 в обе стороны.

Catalog и selected API подтвердили Established и IPv6 peerIp. Administrative disable одной own connection снял own active IPv6 route на другом узле, первое наблюдение144ms после PATCH — не hold-timer/SLA. Enable вернул sessions/routes/Ping. Read-only production UI1440/320 показал обе IPv6 сессии/Established в DOM, document overflow/page errors0; горизонтально скрытые mobile columns не выдаются за одновременно видимые. Live UI, native/withdrawal/recovery.

Первый harness проверял отсутствующее поле remoteAddress, тогда как public API контракт использует peerIp. Он остановился после успешных native route/Ping assertions;11 baseline collections×2 восстановлены. Failure сохранён отдельно. Исправлен только ignored test helper; полный второй сценарий exit0. Own BGP/filter/address-list/IPv6/bridge/GRE objects удалены,11 static collections×2 совпали, filter order также сохранён. Обе завершённые собственные container identities проверены и удалены; пароли/public/default routes не менялись. Background main polling продолжался, SQL fixture база не создавалась.

Конфигурация сверена с официальным BGP connection/AFI и IPv6 address lists. Границы: IPv6 BGP transport/NLRI внутри GRE по IPv4 public outer, два собственных peers/single path. Это не IPv6 public WAN/outer, independent WAN, external peer interoperability, BFDv6, continuous packet loss/maximum throughput/scale acceptance. ReUI/Frame/base-nova и runtime backend ux-ospf154/frontend ux-ospf153 сохранены.

Следующий156 — общая UI/context regression после151–154, один проход с сохранением исходных изображений;12.5 открыт.

12.5.156 — bigint идентификаторы серверов и начало общей регрессии (2026-10-11)

Audit actual schema обнаружил, что servers.id и references — PG bigint с Drizzle mode:number. В152 ошибочно введён верхний предел2147483647; это не диапазон данной DB схемы. Ограничение удалено, общая parseDbServerId требует positive safe integer и полную decimal строку. IDs2147483648 и Number.MAX_SAFE_INTEGER сохраняются точно;9007199254740992/3 и прочие unsafe/malformed не округляются в другой сервер. Историческая запись152 отражает прежнюю ошибочную границу; этот блок её исправляет.

Permanent server-id.test.ts проверяет25 valid/invalid forms без SQL. Dedicated PG test сохранил33 API checks disabled Home/Jump/Exit с forbidden ROS factory/contacts0, enabled control и2 реальные positive bigint rows. Guards MMAPP_OWN_TEST_DB152/156/current_database выполнены до bootstrap; собственная база удалена. Локальные config-sync/live-maps profiles и production backend build passed;984 emitted files совпали. Backend ux-id156 развёрнут, frontend ux-ospf153 сохранён. Native devices не изменялись этим блоком.

Протоколы: SQL/33 guards/2 bigint controls, compiled984. ReUI/Frame/base-nova/контракты UI сохранены, frontend build без source delta не повторялся.

Однократная общая UI regression запущена:1260 main cases.348 текущих tracked screen files, включая8 preexisting user-dirty GRE/VXLAN изображений, сохранены с SHA256 в ignored tmp/regression156-originals. На checkpoint774 cases ошибок не наблюдалось; это не завершённая приёмка всего прогона. Source screenshots могут временно меняться тестами и должны быть восстановлены исходными bytes после main/context. В157 дождаться основного процесса, выполнить221 context cases одним sequential server session, восстановить348 файлов, выполнить types/checks и записать точные exits/failures. Не выдавать running/skipped за pass.12.5 открыт.

12.5.157 — общая регрессия после IPv6 и bigint исправлений (2026-10-12)

Однократный основной прогон завершён: 1260 UI-сценариев прошли, exit0. Затем в отдельной последовательной frontend-сессии прошли 221 проверка контекста, exit0; всего 1481 сценарий, без сложения повторных профильных прогонов. Полная команда backend test завершилась exit0: все 24 профиля, входящие в эту команду, прошли. Это не число отдельных assertions. Первоначальный sandbox-запуск остановился в probes.cancel из-за EACCES на локальном HTTP listener; исходный лог сохранён, полный повтор с разрешённым доступом прошёл. Проверки собственной PostgreSQL базы и bigint rows относятся к156, этим общим прогоном повторно не заявляются.

Source TypeScript прошёл после остановки тестового Next dev. Все348 tracked изображения восстановлены из сохранённых перед прогоном текущих bytes, каждое сверено по SHA256; сохранены в том числе8 пользовательских GRE/VXLAN изменений. Сгенерированные тестами изображения не заменяют согласованные референсы. Production source не менялся, образы ux-id156/ux-ospf153 повторно не собирались и не развёртывались. RouterOS конфигурация и пароли этим блоком не изменялись.

Протокол: регрессия157. Это локальная контролируемая регрессия интерфейса/контекста/backend, а не повтор native сценариев или приёмка внешних сервисов, клиентских ОС, масштаба и физических WAN. Исторический timeout orchestration154 остаётся в исходном протоколе. Этап12.5 открыт; следующий158 — проверка эквивалентных IPv6 адресов в сопоставлении OSPF/BFD.

12.5.158 — корректное сопоставление IPv6 OSPF и BFD (2026-10-12)

Строковое сравнение не связывало эквивалентные IPv6 адреса: например FE80:0000:0000:0000:0000:0000:0000:0002 и fe80::2. Теперь IPv6 приводится к канонической записи, optional zone должна совпадать с наблюдаемым интерфейсом. Hostnames, malformed IPv4/IPv6, пустая/чужая/повторная zone не создают совпадение. Stale duplicate с тем же точным device/interface/peer не исключается до проверки уникальности: наличие такой неоднозначности подавляет предупреждение. Single stale session также не доказывает конфликт. Это только корреляция наблюдений; состояния RouterOS и правила сети не менялись.

5 unit tests,11 E2E, source TypeScript и ESLint прошли. E2E включает IPv4/IPv6 на1440/320, предупреждение/переход к BFD с сохранением устройства и очисткой поиска, recovery/foreign/not-used/unknown; остальные7 проверяют состояния данных OSPF. Полную1481 UI/context регрессию157 повторно не запускали: она принята на предыдущем source, эта delta проверена отдельно.

Переданный production source SHA256 совпал локально/на сервере. Frontend production build exit0; ux-bfd158 развёрнут с сохранённой private rollback env, backend ux-id156/PG сохранены. Немедленный curl после старта получил000 до готовности frontend; последующие две browser проверки1440/320 получили200, реальные catalog/server API200, page errors/overflow0 и отсутствие ложного предупреждения после очистки native fixtures. Позитивная native BFDv6 сессия этим блоком не заявляется. Пароли и RouterOS конфигурация не менялись; прежний закрытый SSH-туннель localhost3000/8000 восстановлен.

Протоколы: профильные проверки и сборка, реальный развёрнутый интерфейс. Установленные ReUI/Frame/base-nova переиспользованы без изменения primitives.

Референс Схема доработки
ReUI Data Grid Filtering2 Устройство → точный IPv6 peer/интерфейс → достоверное предупреждение → соответствующая BFD сессия

Следующий159 — native OSPFv3/BFDv6 на собственной GRE паре, short loss/recovery и независимая сверка cleanup. Официальный BFD manual описывает IPv4/IPv6 и use-bfd, но текущая страница версии7.26 не заменяет эксперимент на стенде7.24.5. Sustained route gate, scale/IPv6 public WAN/outer и физическая резервность остаются непроверенными;12.5 открыт.

12.5.159 — native OSPFv3 и BFDv6 с потерей и восстановлением (2026-10-12)

Два CHR7.24.5, собственные GRE с IPv4 outer, ULA fd00:159:1::1/64↔2 и loopbacks fd00:159:ff::1/128↔2/128. OSPFv3 single area/private router IDs, originate-default=never; BFD разрешён только на собственном GRE для fe80::/10,200ms×3, use-bfd=yes только own template. Начальные состояния: BFD Up, OSPF Full, собственный удалённый IPv6 маршрут active; Ping3/3 в обе стороны. Catalog и selected API подтвердили own маршруты/ipv6:IDs/link-local nextHop/via.

Два собственных /ipv6/firewall/filter правила блокировали только UDP3784 input/output на CHR2, exact own GRE и соответствующие link-local src/dst /128. OSPF89/ICMPv6 не блокировались; отдельный packet capture Hello не выполнялся.44 samples за25s показали BFD Down и поздние OSPF Full/own route active после20s. Это наблюдаемая граница, не доказательство постоянного route gate/непрерывной доставки/SLA. На production frontend ux-bfd158 с реальным backend ux-id156 два readonly UI случая1440/320 показали предупреждение, IPv6 BFD Down и переход с сохранением server context; page errors/overflow0. ПК, телефон; mobile просмотрен, скрытые горизонтально table columns не считаются одновременно видимыми.

После снятия own UDP fault: BFD Up/Full/route active и recovery Ping3/3×2. Затем own rules/templates/area/instance/BFD config/IPv6/bridge/GRE удалены;13 static collections×2 сравнивались по выбранным конфигурационным полям, dynamic rows/volatile counters исключены. Порядок IPv4/IPv6 filters и BFD configuration сохранён. Это не побайтное сравнение полного runtime export. Helper exit0; container удалён после сравнения exact full ID с own cidfile и состояния exited0. Собственная SQL fixture база не создавалась, helper только читал server config из main DB, background polling продолжался. Пароли/public/default routes не менялись; оба CHR доступны при cleanup.

Протоколы: native44/recovery/cleanup, 2 реальные UI. Source/dependencies/build не менялись после158, повторная общая регрессия не требовалась. Официальный BFD использован как справка; фактический результат относится к установленной7.24.5, не текущей версии страницы7.26.

Принят basic native IPv6 BFD в OSPFv3, scoped loss/recovery/API/UI; IPv6 public outer/WAN, scale, физическая резервность/interop/continuous loss остаются открыты. Следующий160 — BGP IPv6+BFD own pair;12.5 открыт.

12.5.160 — IPv6 BGP с BFD: снятие маршрута и восстановление (2026-10-12)

На двух CHR7.24.5 собственная GRE пара по IPv4 outer, ULA fd00:160:1::1↔2/64 и loopbacks fd00:160:ff::1↔2/128, private AS64555/64556. BGP afi=ipv6/use-bfd=yes; BFD разрешён только own GRE/ULA subnet200ms×3. Input/output routing filters принимают только точные own/remote /128, default-originate=never, network-blackhole=no. Initial BFD Up/Established/ровно1 own remote NLRI и Ping3/3×2, catalog/selected sessions API подтверждены.2 real UI1440/320 показали IPv6 peers/Established, no overflow/page errors; собственные native мутации выполнялись helper, browser только читал.

На CHR2 два own IPv6 filter rules блокировали только UDP3784 input/output, exact own GRE/ULA src/dst /128. TCP179/ICMPv6/публичные пути не блокировались.44 samples за25s подтвердили BFD Down и отсутствие обоих own active IPv6 routes; первое такое REST наблюдение636ms после установки fault, это не SLA/packet capture/continuous packet loss. Во время перехода native established flag некоторое время ещё присутствовал на одном узле; промежуточные состояния сохранены полностью. Fault catalog показал Unknown для обеих session rows с отсутствующим установленным FSM state, не догадку Idle/Down. UI во время самого fault отдельным сценарием не проверялся.

Удаление own fault вернуло BFD Up/Established/NLRI и Ping3/3×2. Все созданные connection/instance/filter/address-list/BFD/IPv6/bridge/GRE удалены;12 static collections×2 совпали по выбранным конфигурационным полям (dynamic/volatile исключены), routing/IPv6 filter/BFD configuration order сохранён. Helper exit0, container удалён по exact full ID из cidfile только после exited0. Основная DB только читалась helper; background polling продолжался, отдельная SQL база не создавалась. Пароли и default/public routes не менялись; оба CHR доступны при cleanup.

Протоколы: native44/withdrawal/recovery/cleanup, 2 live UI, ПК, телефон. Source/dependencies/build не менялись; runtime ux-id156/ux-bfd158 сохранён, без повторной общей регрессии.

Basic single-path BGP IPv6/BFD withdrawal/recovery принят, не IPv6 public WAN/outer/scale/interop/physical redundancy/бесшовность. BFD с BGP — справочный документ; результат фактически проверен на7.24.5. Следующий161 — audit legacy selected BGP/alert parser: общий catalog сохраняет Unknown, но старый detectState угадывает Active из uptime и Idle при отсутствующем native FSM.12.5 открыт.

12.5.161 — неизвестные состояния BGP без ложных оповещений (2026-10-12)

Общий legacy/selected parser больше не угадывает Active из uptime и Idle при отсутствии native FSM. Established=true сохраняет подтверждённое Established; остальные известные FSM распознаются точным match, malformed/future-prefix/blank/missing сохраняют Unknown. Catalog и selected state согласованы; legacy числовые counters/timers этим блоком не мигрировались. BGP alert evaluation рассматривает только известные FSM: Unknown/blank/future state не подтверждают проблему и не становятся подтверждённым previous down при recovery.

Из collector выделена чистая корреляция BGP signals: newest current Unknown остаётся Unknown, previous baseline ищет ближайшее известное состояние среди сохранённых runs. Так Idle→Unknown→Established подтверждает recovery на основе последнего известного Idle; Established→Unknown→Established не создаёт ложный recovery; Unknown current не создаёт event. История ограничена существующими8 прочитанными collector runs, неизвестный период не становится новым фактом. Legacy peer keys serverName:peerName сохранены; миграция неоднозначных одинаковых имён этим блоком не заявляется.

Live-maps parser/profile прошёл; alert-engine groups/evaluate прошли, SQL confirm-stability тест пропущен из-за отсутствующего локального PG подключения/EACCES, не записан как pass. Outbox/alerts HTTP/JWT profile прошёл на controlled sender interfaces, реальные сообщения не отправлялись. На скомпилированном коде replay92 сохранённых настоящих RouterOS rows из160:19 Established/73 Unknown, selected/catalog states совпали;73 unknown problem и73 unknown previous recovery проверки не создали event. Это воспроизведение native payloads, не новый live mutation/SQL/outbox-delivery тест.

Backend build прошёл, окончательный Docker кандидат ux-bgp161b совпал с локальными988 emitted non-test файлами (новый module добавил4 outputs). Первоначальный ux-bgp161/984 был развёрнут до обнаружения last-known gap; финальный161b пересобран и развёрнут после исправления baseline, обе версии/rollback env сохранены. Backend/PG healthy, frontend ux-bfd158 сохранён;3 readonly real GET catalog/selected и2 browser1440/320 passed/no errors/overflow после cleanup. Positive missing-FSM rows доказаны replay, пустой live catalog не выдан за native inactive proof. Общая регрессия157 относится к прежнему source; эта delta проверена профильными сценариями.

Протоколы: compiled988, native payload replay, deployed API/UI. RouterOS конфигурация/пароли этим блоком не менялись, новые native fixtures не создавались, ReUI/Frame/base-nova UI primitives сохранены.

Следующий162 — native private4-byte ASN в IPv6 BGP и отображение длинных AS на1440/320; прежний BFD fault повторять без новой delta не требуется.12.5 открыт.

12.5.162 — четырёхбайтовые ASN в IPv6 BGP и интерфейсе (2026-10-12)

Два CHR7.24.5, own IPv4 outer GRE/IPv6 ULA fd00:162:1::1↔2/64 и loopbacks fd00:162:ff::1↔2/128. Private AS4200000162↔4200000163 взяты из диапазона IANA4200000000–4294967294, reserved4294967295 не использован. Input/output filters принимают только exact own/remote /128, afi=ipv6, default-originate=never и network-blackhole=no. Native Established и negotiated as4, local/remote AS сохранили исходные10-значные числа вместо AS_TRANS; catalog совпал, capabilities содержит4-byte-AS. Каждый узел получил ровно один own remote IPv6 NLRI, initial Ping3/3×2.

Readonly production UI1440/320 показал обе IPv6 сессии/Established и точные remote ASN в DOM, no errors/document overflow. Mobile проверен визуально; AS columns могут требовать горизонтального table scroll, одновременная viewport visibility всех columns не заявляется. Administrative disable одной own BGP connection снял own remote IPv6 route на другом узле, первое наблюдение135ms после PATCH, не hold timer/BFD/SLA/continuous loss. Enable вернул Established/NLRI и Ping3/3×2. BFD fault160 без source delta не повторялся.

Own connections/instances/routing filters/address-list/IPv6/bridge/GRE удалены,11 static collections×2 совпали по выбранным конфигурационным полям, filter order сохранён. Helper exit0; container удалён после exact-ID/state check. Main DB только читалась helper, background polling продолжался; пароли/public/default paths не менялись, оба CHR доступны при cleanup. Source/dependencies/build после161 не менялись, runtime ux-bgp161b/ux-bfd158 сохранён.

Протоколы: native/as4/withdrawal/recovery/cleanup, 2 live UI, ПК, телефон. Live UI162 использует отдельный файл bgp-ipv6-162-live-ui, протокол160 сохранён отдельно.

Границы: private four-byte ASN между двумя RouterOS, single-path IPv6 внутри IPv4 GRE, не interop со сторонними peers, IPv6 public outer/WAN, scale/physical redundancy. Следующий163 — проверка duplicate legacy alert keys serverName:peerName: два разных устройства с одинаковыми именами не должны создавать ложные state transitions внутри одного snapshot.12.5 открыт.

12.5.163 — неоднозначные ключи BGP-оповещений (2026-10-12)

Два CHR в native162 имели одинаковые legacy alert keys CHR:peerName. Раньше второй peer внутри того же snapshot мог стать previous state первого. Collector теперь сначала группирует строки одного run: повторный key становится current Unknown, а ambiguous history не используется для поиска previous known state через разные identities. Даже одинаковые states не доказывают уникальное соответствие configured target конкретному peer. Distinct keys и last-known переходы161 сохранены; stable server/peer ID target migration не выполнена. Для legacy ambiguous targets события подавляются консервативно.

Unit assertions проверили duplicate same/different/unknown states и исторический barrier. Compiled replay46 real native160 snapshot pairs подтвердил одинаковые ключи,46 Unknown/46 suppressed problem/46 suppressed recovery. Это сохранённые RouterOS payloads, не новая native mutation. Alert groups/evaluate и controlled outbox/HTTP/JWT profiles прошли; SQL stability снова skipped из-за отсутствующего PG подключения и не считается pass. Backend build/988 emitted parity passed, ux-bgp163 развёрнут с rollback env; backend/PG healthy, frontend ux-bfd158 сохранён.3 readonly catalog/selected GET и2 live UI1440/320 passed/no errors/overflow после fixture cleanup. Образы/сборка отражают эту delta, полная1481 UI/context regression157 повторно не запускалась.

Протоколы: replay46, compiled988, deployed API/UI. ReUI/Frame/base-nova UI primitives сохранены; RouterOS/пароли/объекты не менялись, сообщения не отправлялись.

Следующий164 — strict nullable selected BGP counters/AS/timers: legacy selected API ещё подменяет отсутствующие значения default numbers и UPDATE messages количеством prefixes.12.5 открыт.

12.5.164 — достоверные числа BGP во всех маршрутах чтения (2026-10-12)

Selected/all BGP parser и тип BgpSessionRead теперь используют nullable remote/local AS, timers, RX/TX prefixes и message counters. Отсутствующее/invalid/unsafe значение не становится0/90/30 или типом eBGP. Prefix RX читается только из prefix-count; UPDATE messages не являются количеством префиксов, TX prefixes остаётся null без доказательства. Наблюдаемый0 сохраняется0, известные ASN до32-bit сохраняются точно. Catalog переиспользует общий parser, добавляя AFI; миллисекунды в timers переведены в дробные секунды, overflow duration остаётся unknown.

Это намеренное изменение старого selected/all API numeric contract: clients должны обрабатывать null, историческое legacy-preserved утверждение ранних блоков больше не описывает эту версию. Все repository type consumers прошли backend build; основной BGP UI уже использовал nullable catalog. Collector keys/state и правила163 сохранены, новые numeric defaults не добавлялись.

Live-maps profile и controlled alert/outbox HTTP/JWT прошли,15 BGP data/freshness/link E2E passed. Compiled replay96 реальных rows из160/162:146 missing counters сохранены null,104 observed zero сохранены0,4 four-byte ASN rows точны; selected/catalog fields совпали с native values. Это replay, не новый live native lifecycle. Backend production build/988 emitted parity passed; ux-bgp164 развёрнут с rollback env, backend/PG healthy, frontend ux-bfd158 сохранён.3 readonly GET и2 real UI1440/320 passed/no errors/overflow после cleanup. Positive nullable rows доказаны replay и unit/HTTP profiles, empty live catalog не считается positive missing-field доказательством. Broad regression157 не повторялась без необходимости.

Протоколы: native replay96, compiled988, deployed API/UI. ReUI/Frame/base-nova primitives/RouterOS конфигурация/пароли сохранены, новые fixtures/сообщения не создавались.

Следующий165 — общий GRE/BGP collector: await внутри Promise.allSettled сериализует независимые reads и не сохраняет успешный BGP при раннем GRE throw; текущие BGP signals также не должны восстанавливать отсутствующий в newest snapshot peer из старого run.12.5 открыт.

12.5.165 — независимый сбор GRE/BGP и актуальные сигналы оповещений (2026-10-12)

Убраны await внутри Promise.allSettled: независимые GRE/BGP reads действительно запускаются параллельно. Promise boundary сохраняет sync и async ошибки отдельно; успешная группа не теряется при отказе другой. Dependency seam проверяет production collector без SQL/RouterOS. Busy guard не запускает повторных запросов, после отказа collecting сбрасывается. Permanent collector/history tests включены в test:alert-engine.

GRE/BGP reader берёт8 newest completed runs со status ok/error, включая null result_json: более новый отказ не скрывается фильтром успешных прогонов. Invalid/version-mismatched/null/malformed payload становится barrier с пустыми current collections и явным fatalError. Valid partial snapshot сохраняет успешную группу. Current peer/tunnel keys берутся только из newest run; прошлые строки используются только как previous state существующего текущего объекта. Удалённые/непрочитанные объекты не воскресают как current. GRE duplicate labels/history barrier также исключают cross-peer transitions; BGP163 guards сохранены. Остальные collector families, age disabled jobs и stable-ID legacy target migration этим блоком не закрыты.

Unit cases проверили concurrent start до GRE completion, busy/no second fetch, scoped sync/async failures, recovery/empty, failed/null/malformed history, successful partial BGP, deleted peers и GRE alias ambiguity. Alert/outbox HTTP/JWT profiles passed; SQL confirm-stability skipped без PG подключения и не записан как pass. Backend build/996 emitted parity passed. Actual production PG SELECT выполнен compiled candidate через default_transaction_read_only=on:8 history rows, newest BGP0/current BGP0/GRE0, old owned peers0; bootstrap/writes/RouterOS/messages отсутствовали. В этих real latest rows не доказан positive error/partial fixture — отдельный seeded SQL сценарий запланирован166.

ux-collector165 развёрнут с rollback env, backend/PG healthy, frontend ux-bfd158 сохранён;3 readonly GET и2 live UI1440/320 passed/no errors/overflow. Source frontend/primitives ReUI/Frame/base-nova не менялись; широкая UI regression157 не повторялась. Пароли/RouterOS config сохранены, fixtures не создавались этим блоком.

Протоколы: compiled996, real readonly PG, deployed API/UI. Следующий166 — own isolated PG с positive error/partial fixtures и полная backend regression при доступном PG, затем проверка удаления собственной DB/containers.12.5 открыт.

12.5.166 — полная backend-регрессия с доступным PostgreSQL (2026-10-12)

Общий npm --prefix backend test теперь запускает прежние24 профиля последовательно через cross-platform Node runner, устанавливая NODE_ENV=test без shell environment assignment. Pool использует штатный allowExitOnIdle только в test: завершённый SQL файл не ждёт30s idle socket. Production/development сохраняют обычный lifecycle; active queries не подменяются early exit. Permanent pool test проверяет оба режима без SQL подключения. Исходный список сохранён в test:all; прямой test:all — legacy chain без test-mode wrapper.

В отдельном Docker test image Node22/dev dependencies/PG18 tools создана собственная mm_accept_166_1791779292730. До bootstrap проверены уникальность, current_database и пустая public schema. Все SQL-тесты получили URL этой базы; основные server credentials не клонировались в тестовую DB, URL/env/полный лог остаются в private0600 вне Git. Все24 профиля завершились exit0 за286958ms (4m47s), PostgreSQL-unavailable skip отсутствовал. SQL confirm-stability тест, ранее skipped локально, выполнился и passed. Это измерение одного прогона, не процент ускорения без сопоставимого baseline.

Permanent owned SQL test перед DDL проверяет explicit MMAPP_OWN_SQL_DB/166 name/current_database.6 реальных scheduler_runs rows: old success, newest error с успешным BGP/failed GRE, SQL NULL result, malformed JSON string, successful empty и duplicate labels/keys. Actual reader/builder сохранили valid partial BGP, не восстановили старые/удалённые peers, не выдали malformed/null за success и подавили ambiguity. Собственные test rows удалены. Optional network-disabled SQL fixture152/156 без специального MMAPP_OWN_TEST_DB остался skipped;33 disabled/bigint guards156 не считаются повторно принятыми здесь.

Database owner проверен, только собственная DB удалена WITH FORCE после завершения child tests; main server id/host/name/username/password/type/enabled/country/site до/после совпали (в публичном отчёте только boolean, без значений). Own full-test container удалён после exact cidfile/state exited0 check. Main background polling продолжался, RouterOS сценарии не повторялись, реальные сообщения не отправлялись. Другие multi-instance/physical disconnect/real integrations границы прежние.

Backend production build и996 emitted parity passed; отдельный NODE_ENV=production readonly actual PG probe подтвердил allowExitOnIdle=false. ux-pg166 развёрнут с rollback env, backend/PG healthy, frontend ux-bfd158 сохранён;3 readonly GET/2 live UI1440/320 passed/no errors/overflow. Frontend source/ReUI/Frame/base-nova не менялись, UI/context regression157 не повторяли после backend-only delta.

Протоколы: full24/own SQL/cleanup, compiled996, production pool/read-only PG, deployed API/UI. Следующий167 — freshness/disabled collector-job audit; newest completed snapshot сам по себе не доказывает свежесть после остановки collector.12.5 открыт.

12.5.167 — устаревшие GRE/BGP снимки не подтверждают новые оповещения (2026-10-12)

Audit scheduler показал, что GRE/BGP сейчас всегда enabled, отдельного UI switch для него нет; interval30s фиксирован. Выдуманный disabled-job guard не добавлен. После остановки процесса/сборщика latest completed row может оставаться старым: reader теперь проверяет newest finished_at и producer sampledAt. Окно freshness —3 периода (90s), future clock tolerance —1 период (30s), привязанные к одной константе с scheduler timing/metadata. Старый, слишком будущий, invalid/nonstring sampledAt даёт unavailable/stale barrier и не порождает GRE/BGP current events. Прежние rows остаются last-known history при наличии свежего current; ambiguity guards163/165 сохранены. Это явно выбранная прикладная граница для30s collector, не RouterOS SLA или физическое обнаружение отказа.

Unit clock injection проверяет stale/future completion и sample, malformed/nonstring date,90s boundary; local alert/scheduler profiles/build passed. Local PG branches skipped, затем отдельный Node22/PG18.6 owned профиль test:alert-engine выполнился exit0 за31154ms:8 SQL rows (6 error/partial/NULL/malformed/empty/duplicate +stale/future sample) и actual confirm-stability passed, PostgreSQL-unavailable skip0. Полные24 profiles166 без необходимости не повторялись. Guarded integration test по-прежнему использует166 namespace; создана новая собственная mm_accept_166_1791781079670, прежняя166 база не переиспользована. Own rows/DB/container удалены; main server static fields до/после совпали. Приватный лог/env не попали в Git.

Backend production build/1000 emitted parity passed, ux-fresh167 развёрнут с rollback env, backend/PG healthy, frontend ux-bfd158 сохранён.3 readonly catalog/selected GET и2 live UI1440/320 passed/no errors/overflow. Source frontend/ReUI/Frame/base-nova и RouterOS правила/пароли не менялись, native tunnels не создавались, сообщения не отправлялись. Running containers после cleanup только3 основных сервиса. Свежесть других collector families/отключаемых jobs и stable-ID target migration этим блоком не закрыты.

Протоколы: owned SQL8/cleanup, compiled1000, deployed API/UI. Следующий168 — audit остальных alert source families: stale/disabled config не должны создавать current facts.12.5 остаётся открытым в матрице внешних ограничений.

12.5.168 — карта оставшихся источников оповещений (2026-10-12)

Выполнен source audit и чтение метаданных production PG с default_transaction_read_only=on. Source/database settings не менялись, default-seeding getters не вызывались, bootstrap/RouterOS/messages отсутствовали. Реальные текущие настройки: resources enabled/15s, traffic enabled/30s, REST disabled/120s, active Ping probes0. Builder в момент audit выдавал1 server signal (max age3.197s), traffic1 (max age18.24s), probes0. Это возраст наблюдаемого снимка, не controlled stale fixture. Одновременно обнаружена1 группа одинаковых имён у enabled servers: оба CHR называются одинаково,2 devices сворачиваются в1 name-based signal. Audit не исправляет это поведение.

Source findings: non-GRE/BGP reader выбирает только status=ok; resource/REST/traffic/probe reducers восстанавливают ключи из старых runs; evaluation не проверяет sampledAt age; builder не применяет текущие enabled flags источников. Resource reducer превращает всякое не-online значение в offline; одинаковые имена могут смешать current и previous разных устройств. Это подтверждённые свойства кода, но runtime disabled/stale/malformed fixture пока не выполнен. Не считать найденные проблемы устранёнными только по этому документу.

Источник Интервал / особенность Требование к следующему блоку
Resources Настраиваемый intervalSec, на стенде15s; default300s Effective resourcesEnabled; уникальная identity/current known state; возраст по своему периоду
REST availability Отдельные enabled/intervalSec; сейчас выключен Выключенные/старые REST данные не переопределяют свежий resource result и не подтверждают recovery
Ping probeIntervalSec и individual uptime_probes.intervalSec; snapshot содержит только due probes Фильтр enabled probes/source servers; latest observed row каждого probe и его собственный TTL, не latest-run-only
Traffic Настраиваемый enabled/intervalSec; сейчас30s Отсутствие/старое/disabled не превращается в zero/low traffic; identity не смешивает одинаковые имена

Период GRE/BGP30s/границу90s167 нельзя механически распространить на resources default5min или Ping с индивидуальным расписанием. Для169 сначала определить effective config каждого family и per-probe timing, затем coherent current states/previous known history без cross-device aliases. Проверить own PG: disabled source с retained history, stale/future times, newer error/null, empty/deleted object, duplicate labels, частичный due-probe batch и controlled recovery. Локальные unit/profile tests + scoped SQL; production build только backend после окончательной delta. Полную UI/context regression повторять лишь при frontend foundation change, остальные native протоколы не переснимать без новой причины.

Схема доработки:

flowchart LR
  A["Текущий источник и устройство"] --> B["Enabled и уникальная identity"]
  B --> C["Последнее наблюдение и свой интервал"]
  C --> D{"Свежий известный факт?"}
  D -->|да| E["Условие правила и last-known history"]
  D -->|нет| F["Нет подтверждения события"]
  E --> G["Outbox после подтверждения"]

Протокол: readonly audit168. Source/build/runtime не менялись после167, новые тесты и исправления не заявляются. Следующий169 — выполнить этот единый блок, сохранить profile/owned SQL результаты и локальный коммит без push. Реальные Telegram/Portal/внешние accounts, client OS/physical WAN/multi-instance остаются отдельными условиями12.5.

12.5.169 — идентификация устройств в сигналах оповещений (2026-10-12)

По поручению пользователя выполнить небольшой объём при оставшихся7% лимита. Исходный единый объём169 ограничен самостоятельной локальной частью; полная приёмка источников не заявляется. Добавлен server-signal-identity.ts, builder читает только id/name/host/enabled из текущего servers. До name-based timeline и traffic reducer каждая строка resource/REST/traffic сопоставляется с текущим активным устройством по ID, имени и адресу. Сигналы отключённых/удалённых устройств, старого имени/адреса и повторяющегося ID внутри одного run исключаются. Если несколько enabled устройств имеют одинаковое имя после trim/lowercase, их сигналы не выдаются: существующие правила адресуют цель по имени и не позволяют безопасно выбрать конкретное устройство. Имена/настройки самих CHR не менялись. На текущем стенде оба CHR имеют одинаковое имя; после будущего развёртывания такие цели будут подавлены до явного устранения неоднозначности или миграции правил на ID. Это консервативное отсутствие подтверждённого события, не offline и не нулевой traffic.

Новый постоянный тест добавлен в test:alert-engine: уникальная цель; отключённая/удалённая; два одноимённых устройства и перестановка каталога; отключение дубликата; изменение имени/адреса; другой ID; повторные строки; строковый безопасный PG ID и небезопасный ID; неизменность входа. Прошли доступные проверки alert-engine (identity/groups/evaluate-rule/collector/history), backend production build и ESLint трёх изменённых TS файлов. GRE/BGP SQL пропущен без явно выделенной own DB; confirm-stability SQL пропущен из-за PostgreSQL connect EACCES127.0.0.1:5432. Это не положительная SQL-приёмка. Полная UI/context regression не запускалась: frontend не менялся.

Ограничения сохранены явно: only-ok history всё ещё может поднимать старый факт, disabled flags самих jobs и sampledAt age не применяются; resource unknown и traffic отсутствующее значение требуют отдельного исправления; probe identity/enabled/individual interval остаются в170. Duplicate row guard не заменяет latest-current/error barrier. SQL/live fixtures и source/runtime parity для169 отсутствуют; удалённый backend/frontend не развёртывались, RouterOS writes/messages0, новые сетевые объекты не создавались. Доступность серверов в этом локальном блоке не перепроверялась. Runtime остаётся ux-fresh167/ux-bfd158; изменений169 в браузере пока нет.

Протокол: локальная проверка169. Следующий170 — source enabled/freshness/current known guards, per-probe timing и identity с owned SQL positive/negative fixtures, затем coherent backend build/deploy/live и локальный коммит без push. Этап12.5 остаётся открытым.

12.5.170 — достоверность серверных, пробных и трафиковых сигналов (2026-10-12)

Завершён оставшийся объём169 в одном coherent backend блоке. Новый collector-source-signals отделяет чтение от чистого построения фактов. Builder читает текущие настройки и identity без seeding getters и без credentials: resourcesEnabled/pingEnabled имеют тот же fallback на legacy enabled, что scheduler; REST/traffic используют собственные enabled. Выбираются последние завершённые ok/error runs, включая NULL/error JSON, вместо only-ok history. Текущие server/traffic keys берутся только из newest run: empty/error/malformed/unknown не восстанавливают старую цель. Частичная ошибочная коллекция сохраняет известные строки других устройств. ServerID/name/host/enabled/duplicate guards169 сохранены; пустое имя может использовать host, как collector. producer sample и completion проверяются по3 effective periods, future tolerance1 period; минимумы5s resources/traffic и10s REST повторяют scheduler. Resource неизвестное значение не становится offline; Traffic требует ok=true и конечные неотрицательные RX/TX, отсутствующее/ошибка не становится0. Подтверждённый нулевой трафик остаётся0.

Ping сопоставляется с текущим probeId/name/target/sourceServerId/interface/source label, enabled probe и enabled source. Повторные цели/строки исключаются; более новое unknown/null/fatal/error observation не подменяется старым. Valid due-only batch может не содержать медленную пробу: её latest observed row сохраняется в пределах своего TTL. Effective probe period учитывает individual interval и глобальный tick, default минимум5s; future tolerance привязана к глобальному tick. Чтение охватывает3 максимальных настроенных probe periods, с защитным пределом4096 rows (при очень большом масштабе возможен консервативный пропуск, масштаб этим блоком не принят). Сэмплы до server/probe updatedAt не подтверждают новую конфигурацию. Server timelines прекращают recovery history на unknown/invalid/ambiguous barrier; свежие resource/REST подтверждения объединяются без выдуманного cross-source recovery. Выбирается реальное собственное history успешного источника.

Постоянные чистые тесты проверяют config/identity/time/empty/error/partial/unknown/numeric boundaries, медленные due probes, изменения конфигурации, recovery и настоящий evaluateRule путь с положительным и отрицательным control (server offline, loss и RX low). Локальные alert-engine и scheduler profiles прошли, backend build и ESLint прошли. Локальный PostgreSQL недоступен, SQL branches там skipped; положительная SQL-приёмка выполнена отдельно на Node22/PostgreSQL18.6: test:alert-engine за18622ms,16 новых SQL cases (включая31 Ping batches, больше прежнего лимита24),8 GRE/BGP SQL rows и actual confirm-stability passed без PG skips.

Автоматическая проверка отклонила копирование всех production env в persistent файл; этот способ не использован. Для SQL созданы собственная база mm_accept_166_1791791913287 и отдельная LOGIN роль без SUPERUSER/CREATEDB/CREATEROLE/BYPASSRLS, пароль сгенерирован временно и не публиковался. URL/роль ограничены own DB; main credentials/JWT не копировались. Тестовые строки/контейнер, база и роль удалены и отсутствие проверено. Main SQL fixtures/RouterOS/messages отсутствуют; обычные фоновые сборщики main не останавливались. Полная24-profile/UI1260/context221 regression157/166 без новой причины не повторялась.

Production backend собран инкрементально на прежней базе ux-fresh167 с прежними зависимостями: backend dependency hash совпал.433 source inputs и1008 emitted files совпали поSHA256 с LF normalization, запущенный imageId совпал с проверенным образом. Развёрнут ux-sources170/version1.0.0-test.sources170, backend/PG healthy; frontend ux-bfd158 прежний. В.env изменён только BACKEND_IMAGE_TAG, для rollback сохранён прежний tag ux-fresh167, копия всего secret env не создавалась. После cleanup только3 основных running containers.

Readonly production PG builder подтвердил1 группу одинаковых enabled labels и0 server/traffic/probe signals. Ноль проб соответствует отсутствию configured probes, server/traffic подавлены из-за неоднозначности двух CHR с одним именем; это не отказ устройств и не доказательство положительных измерений (они проверены в owned SQL). Имена/пароли не менялись.4 read-only API checks включают оба selected CHR BGP endpoints и catalog без failures;6 UI cases /alerts,/servers,/uptime при1440/320 passed, pageerrors/API writes/overflow0. Первые локальные network calls получили sandbox EACCES, повтор с разрешённым network доступом passed; UI helper сначала ожидал отсутствующий в существующей странице h1, исправлен на фактический main без изменения frontend. Это scoped smoke, не новая полная accessibility сертификация.

Протоколы: SQL16/cleanup, source433, compiled1008, readonly production, runtime, API/UI.

Следующий171 — понятная диагностика неоднозначных/отключённых целей оповещений: silent suppression безопасен для engine, но пользователь должен понимать причину отсутствия события. Миграция name-based rules на stable ID, scale/multi-instance/physical WAN/внешние Telegram/Portal/client OS остаются отдельными условиями12.5. Локальный коммит без push.

12.5.171 — понятные причины недоступности целей оповещений (2026-10-12)

При conservative suppression170 пользователь должен понимать, почему событие не подтверждается. Добавлен чистый collectAlertTargetIssues и optional public meta.targetIssues: kind server/traffic/probe, подпись и причина ambiguous/disabled-object/disabled-source. Диагностика строится из текущих настроек внутри того же repeatable read/read only transaction, что основной overview; getters defaults не создают. Учитываются dedicated source switches, enabled REST как разрешённый availability source по конфигурации, enabled устройства/пробы, duplicate labels и fallback имени на host. Это диагностика конфигурации; она не заявляет свежесть измерений, online устройств или фактическую доставку Telegram. Поля credentials не выбираются и не публикуются. Engine правила, target representation и права не изменены.

На /alerts добавлен существующий ReUI/shadcn Alert warning в base-nova/Frame композиции без изменения vendor files/theme. Строки доступности и трафика одной цели объединены; причина и дальнейшее действие читаются вместе. Длинный список раскрывается native details/summary клавиатурой, большой список изначально свёрнут; длинные подписи переносятся на телефоне. Ссылки ведут к серверам, пробам и сбору данных. При устранении причины warning исчезает после подтверждённого обновления; legacy API без optional поля не подменяется догадкой. Имена двух CHR и targets действующих правил автоматически не переписывались.

Эталон Доработка Проверка
Существующие Alert и Frame проекта Подпись → причина → понятный переход → обновление ПК1440, телефон320

Локально прошли12 скриптов test:alerts-telegram (unit/transaction/config/queue/HTTP/JWT), application-source TypeScript, backend build и ESLint. Полный root tsc сначала захватил ignored tmp с давними test/build artifacts и выдал их ошибки; source check с исключением tmp/backend/packages прошёл, contracts/backend проверены собственной сборкой. Root tsconfig не менялся.42 unique E2E:22 readers/targets/pickers/rules/new diagnostics за44.7s;19 history/outbox/Telegram за30.6s;1 новый keyboard/long-label mobile за6.2s. Реальная отправка Telegram отсутствовала: HTTP пути подменены тестовыми receipts. Последняя проверка хронологии старым check-progress168 ожидала прежний header168; сам сохранённый historical slice имел12 dated blocks/35 существующих evidence links. Это устаревшее ожидание helper, не удаление журнала; актуальная сверка обновлена отдельно.

Owned Node22/PostgreSQL18.6 profile passed19540ms:16 source SQL cases плюс проверки actual getAlertsMeta (known empty, disabled-source reasons, ambiguous server/traffic kinds),8 GRE/BGP SQL rows и actual stability;PG unavailable skips0. Временная own DB/ограниченная роль mm_accept_166_1791794042576 и test container удалены. Main fixtures/RouterOS writes/messages0. Обе production сборки прошли; source434 backend+518 frontend inputs и1012 emitted backend/contracts files совпали SHA256 (text CRLF→LF, binary unchanged). Полную UI1260/context221/backend24 regression без новой причины не повторяли.

Развёртывание staged: frontend ux-targets171/version1.0.0-test.targets171 сначала принял реальный прежний API ux-sources170 без targetIssues; затем обновлён backend ux-targets171. На старом cached frontend строгий прежний DTO не знает additive поле: после обновления backend следует перезагрузить страницу для получения совместимого frontend. Менялись только image tags в existing.env; rollback tags сохранены отдельно без копирования secret env. Backend/PG healthy; frontend running/HTTP/browser подтверждён, отдельного healthcheck нет. Запущенные imageIds совпадают с проверенными образами; после cleanup3 основных running containers.

2 real UI1440/320 показали настоящий CHR warning:1 сгруппированная подпись,2 affected kinds, ссылка /servers, overflow/pageerrors/API writes0. Scoped axe нового блока WCAG2A/AA violations0, full WCAG certification не заявляется. Снимки просмотрены; исходные пользовательские GRE/VXLAN images сохранены без staging/revert. Настройки/имена/пароли CHR и исходные правила не менялись.

Протоколы: SQL/cleanup, source, compiled, interop, runtime, live UI.

Следующий172 — отдельная обнаруженная ветка: синтезированный monitoring history в alerts-service читает raw latest samples, пока не применяет enabled/freshness/current-error guards170 и требует проверки реального PG timestamp→public string на positive sample. Source finding не является уже выполненным исправлением или доказанной runtime ошибкой. Stable-ID target migration, отсутствующие цели удалённых правил, physical WAN/scale/multi-instance и реальные Telegram/Portal/client OS остаются отдельными условиями12.5. Локальный коммит без push.

12.5.172 — подтверждённые текущие проблемы в журнале мониторинга (2026-10-12)

Внешнее воспроизведение выполнено на compiled ux-targets171 с own PostgreSQL/ограниченной ролью. Прежний overview принимал положительный raw sample и корректно выдавал timestamp string: гипотеза Date/schema failure НЕ подтвердилась. Первая baseline попытка ожидала ошибку и завершилась assertion failure; её результат сохранён, own fixture/DB/role очищены. Уточнённый baseline прошёл: один и тот же live offline оставался после disabled server, disabled resources source и замены sampledAt на часовой давности. Это положительное независимое подтверждение реального disabled/freshness дефекта прежней ветки, не вывод только из кода.

Raw uptime_resource_samples/uptime_probe_samples больше не используются как самостоятельное доказательство текущей проблемы в alerts history. Выделен readCollectorSourceSnapshot с injectable reader: engine и history используют одинаковые current/config/identity/unknown/freshness/per-probe guards170. History читает source facts через параметризованный Drizzle adapter в том же repeatable read/read only transaction overview, без глобального pool обхода snapshot. Значения запроса остаются bound params, raw fragments — только внутренние постоянные SELECTs. Network GRE/BGP не перечитывается для этой ветки. Конфигурация, источники и lookup metadata остаются readonly; defaults/credentials не загружаются.

monitoringHistory строит live problems только по подтверждённым offline/degraded серверам и down/warn пробам. Заголовок сервера «Доступность сервера» соответствует объединению resource/REST, а не выдуманному outage CPU. Live sent=false/source=live сохраняются: это мониторинг, не факт отправки Telegram. ISO timestamps нормализованы, IDs используют stable hash вместо удаления символов, чтобы разные подписи не схлопывались. Persisted source=db receipts и sent flags сохранены независимо от доступности устройства/источника. Сортировка merged history сравнивает реальное время, чтобы новый ISO live timestamp и PostgreSQL datetime string не нарушали порядок. Это совместимость форматов; старый overview уже корректно проходил schema, driver Date bug не заявляется.

Source/build/unit/ESLint прошли. Локальные alert-engine и12 скриптов alerts-telegram прошли в доступных ветках; локальный PG skipped.4 профильных reader/history E2E прошли11.0s; frontend исходники не менялись, полную UI/context regression не повторяли. Owned Node22/PG18.6 сначала выполнил25 source/history cases; после дополнительного chronology control финальный профиль26 cases прошёл19421ms, плюс GRE/BGP8 и actual stability, PG skips0.9 history scenarios поверх прежних16 и1 chronology: positive live+synthetic stored receipt, disabled device/source, stale JSON при свежих raw tables, newer NULL/error, empty/current absence, same-name server ambiguity с независимой пробой, changed probe identity, raw-only samples без подтверждения; более новая DB receipt стоит первой при смешанном формате дат. Синтетический receipt в own DB не доказывает реальную Telegram доставку.

Все известные baseline/fix DB names и роли удалены, test containers отсутствуют. Один SCP connection закрылся после задержки authentication; финальный bundle повторно передан и verified перед deploy. Промежуточные25-case результаты не выданы за финальные26. Source437 и1020 emitted files совпали SHA256/LF normalization. Production build прошёл; backend ux-history172/version1.0.0-test.history172 развёрнут, imageId совпал с проверенным, backend/PG healthy, frontend ux-targets171 прежний. Existing.env изменён только backend tag, rollback ux-targets171 сохранён без копии secret env. Running containers3.

Первый live GET совпал с закрытием старого контейнера и получил socket closed; после healthy повтор прошёл.3 API reads (/api/alerts и оба selected CHR BGP)200,2 /alerts UI1440/320 accepted/overflow/pageerrors0, configuration warning171 сохранён. Source engine facts и UI journal теперь согласованы в проверенных границах. Raw-only/manual measurements без подтверждённого scheduler snapshot не синтезируются как текущие alerts; их provenance требует отдельного профиля. Native configs/пароли не менялись, RouterOS writes/messages0. Реальная packet loss/current state для scope устройств в этом блоке не создавалась: собственные SQL fixtures, не новый data-plane тест.

Протоколы: first baseline hypothesis, real baseline, SQL26/cleanup, source437, compiled1020, runtime, API/UI.

Следующий173 — source finding: collectPingProbesOnce/pingProbesNow catch превращает ошибку REST-команды в lossPct100/down; decoder пока разрешает ok=false/down/null/100. Это не независимое доказательство потери пакетов. Проверить и исправить подтверждение измерений/empty payload; не объявлять legacy raw UI stats и manual provenance уже исправленными. Также остаются unconfirmed/missing target diagnostics, stable-ID migration, scale/multi-instance/physical WAN и внешние Telegram/Portal/client OS.12.5 открыт. Локальный коммит без push.

12.5.173 — ошибка Ping не подменяет измеренные потери (2026-10-12)

Завершён целый раздел producer→SQL→API→UI. parsePing теперь возвращает measured: empty/unsupported replies, zero sent и противоречивые/malformed counts не подтверждают процент потерь. Подтверждённые received0/sent4 остаются100%/down с RTTnull; успешный настоящий RTT0/loss0 сохранён. Scheduled и manual collectors различают успешное измерение и ошибку REST/недостаточный ответ; after-bandwidth Ping при неизвестном результате возвращает null metrics/error, а не выдуманный outage. Alert decoder принимает только ok=true и известное состояние; retained legacy ok=false/down/100 не срабатывает как измеренная потеря. Malformed due-probe rows без ID — barrier, не разрешение восстановить старое измерение.

Миграция0010 добавляет uptime_probe_samples.measurement_known boolean defaulttrue и observation_error text; CHECK/legacy storage status и integer loss не ломаются. Raw100/down в failed rows — прежние storage sentinel с явным measurement_known=false, не публичное измерение. Snapshot/public observations/API loss становятсяnull/statusunknown, есть причина ошибки. Новые flags пишутся при scheduled и manual error/empty response. Старые scheduled failure samples переклассифицируются readonly по точному probeId+sampledAt retained v1 JSON provenance; genuine100% без failure flag не меняется. Старые manual/retention-lost failures без provenance надёжно восстановить нельзя: они остаются legacy ambiguity, полного historical cleanup не заявляем. Migration additive, прошлые данные не удаляет; source JSON internal v1 теперь допускает nullable loss/unknown. Для rollback старый код не интерпретирует measurement_known, поэтому совместимость хранения не означает корректное чтение новых unknown attempts старой версией.

Overview выдаёт unknown/null без fallback100/down и без padded historical0. Observations timestamps канонизированы; parser проверяет согласованность unknown/null. /uptime использует тот же observed decoder, что dashboard: «Нет данных», — для RTT/loss, причина execution error, отдельный filter/URLstatus=unknown. Новая draft probe тоже не объявляется заранее up/0. Мини-Sparkline сохраняет gaps; expanded RTT chart больше не превращаетnull в0 и не дублирует одиночную точку для выдуманной линии. Dashboard status tooltip получает причину. Source/speed-interface read endpoints теперь409 до RouterOS при disabled server; ошибочная подпись «для ping всё равно можно выбрать выключенный» исправлена. Это соответствует прямому правилу пользователя не опрашивать выключенные устройства любых типов. UI/ReUI primitives/theme не заменены.

Состояние Эталон Результат
Ошибка REST/нет измерения Существующие probe rows/StatusDot/Sparkline ПК1440, телефон320 — API-fixture, не production positive sample
Подтверждённые100% Тот же public observed path Down и100% сохранены отдельным positive control

Unit parser/observations/frontend dashboard-probes/URL guards прошли; backend build, application-source TypeScript и ESLint прошли (в uptime-collector два прежних unused settings warnings, functional scope не расширен). Первый npm --prefix exec взял неверный cwd, повтор direct tsx корректен; новый тест сначала использовал неверное имя Zod package, исправлен на установленный @fastify/type-provider-zod. Local cancellation test получил sandbox EACCES, разрешённый сетевой профиль прошёл; local own SQL skipped без выделенной базы.85 unique E2E Uptime/Ping/Speed: initial83passed/2failed были новые ambiguous test selectors (имя есть в sidebar и строке); selector исправлен на конкретную причину ошибки, delta3passed9.5s. Existing83 scenarios повторно не запускались;2 screenshot captures passed8.5s отдельно. Это не85 clean single-run и не87 новых сценариев. Два перезаписанных тестами прежних speed images восстановлены SHA256;8 user dirty GRE/VXLAN images не тронуты. Новые снимки просмотрены, nullable состояние читаемо при320px.

Owned Node22/PG18.6 профили alert-engine+probes прошли42380ms:26 source/history SQL cases, GRE/BGP8/actual stability и8 новых Ping cases. Последние проходят через реальный MikrotikClient HTTP к loopback simulator, persisted flags, GET overview Fastify path:401,empty,manual,real loss/zero,API,legacy exact provenance и disabled no-outbound requests. Simulator не является физическим RouterOS/network failure. Финальные unit guards zero/inconsistent counts/malformed probe проверены перед scoped rerun; temporary DB/role/container удалены. Production credentials/JWT не копировались. Type/producer tests подключены к стандартному test:probes; default profile count не увеличен.

Source440 backend+518 frontend inputs/1020 emitted parity совпали SHA256. Both production builds passed, backend image включает новый drizzle0010. Staged deploy: frontend ux-ping173 сначала принял старый API ux-history172, затем backend ux-ping173/version1.0.0-test.ping173. Migration0010 и2 новых columns подтверждены readonly в main PG. Backend/PG healthy, frontend running/HTTP/UI, imageIds verified, running containers3. В.env менялись толькоimage tags; rollback tags сохранились отдельно без secret env копии. Cached прежний frontend следует перезагрузить: новые nullable/unknown DTO требуют совместимого reader.

Независимо выполнен настоящий native Ping4 packets194.226.121.150→104.165.244.7 иобратно через running compiled173: обе команды приняты, обе4/4,0%loss, parsed RTT53ms. Это короткое наблюдение, не WAN SLA/max throughput. Main DB read-only, native конфигурация/пароли не менялись;2 operational Ping commands, routerConfigWrites0/messages0. На production configured probes0:2live UI1440/320 подтверждают actual empty catalog/new filter/reader/overflow/pageerrors0; nonempty/error UI доказан fixtures, не выдан за main positive measurement. Collector row/error flags проверены ownSQL, real parser отдельно native payloads.

Протоколы: SQL/HTTP8+cleanup, native4/4, source, compiled, interop, runtime, live UI.

Следующий174 — audit first-wave/invalid traffic rate confidence: ok request и numeric sum не всегда доказывают измеренный rate без previous wave. Не заявлять эту гипотезу как уже выполненное исправление. Source unconfirmed/missing target diagnostics, manual history provenance, unsupported/compound time formats, legacy ambiguous samples, scale/multi-instance/physical WAN/external integrations остаются отдельными условиями12.5. Полная acceptance открыта. Локальный коммит без push.

12.5.174 — достоверность суммы трафика: аудит и локальное исправление (2026-10-12)

На исходном8fb46b1 гипотеза подтверждена исполнением настоящих private sampleRate/toNum, извлечённых TypeScript AST, затем существующих collectSourceSignals/evaluateRule. Семь source fixtures: first-wave/reset/equal timestamps/missing/malformed counters дают0 и ложный RX<1; genuine zero даёт правильное срабатывание, positive1Mbps не срабатывает. Протокол baseline audit намеренно fixed=false и относится к исходной версии, а не к финальному исправлению. Это локальное source воспроизведение; отправки Telegram, реальной SQL persistence и физического сброса RouterOS не было.

Добавлен pure traffic-observation: строгие safe nonnegative integer counters, без parseFloat prefix/negative clamp/missing→0; observed rate подтверждается только двумя валидными дельтами. Traffic collector оставляет numeric stored-rate shape, но публикует sumRxMbps/sumTxMbps только при наличии учитываемых интерфейсов и measured=true у всех. First wave, reset, равное/invalid время, частично неизвестный интерфейс и отсутствие учитываемых интерфейсов не становятся измеренным нулём; genuine zero сохраняется. Некорректный interface counter завершает текущий server snapshot с ok=false до insert. WG peers остаются optional: ошибка их чтения/декодирования не превращает корректный interface snapshot в failure; частичные валидные peer rows могут остаться. Это не новая гарантия полноты peer history.

Existing snapshot types уже имеют optional суммы; source decoder174 не менялся и исключает отсутствующие суммы. Таблица snapshots уже показывает — при отсутствии значения; ReUI/theme не менялись. Historical traffic builder уже различает первый sample и measured zero при includeObservations=true. Старые загрязнённые counters/rates не переписаны: ошибку прежнего missing-counter→0 нельзя надёжно реконструировать без provenance. Consumer raw numeric-rate compatibility, freshness/failed attempts history, безопасный baseline после смены объекта, unsafe integer counters и масштаб требуют отдельной SQL/HTTP-приёмки.

npm --prefix backend run test:traffic-rate прошёл: существующие формулы/observations, новый counter/rate/source guard и actual collectTrafficOnce body через AST с in-memory DB/HTTP boundaries (first wave, zero, reset, malformed/no insert, excluded interfaces). Извлечение исполняет исходный collector, не копию алгоритма; это не реальный PostgreSQL или RouterOS. npm --prefix backend run build прошёл. Local check фиксирует хеши изменённых source и границы доказательства. Full regression/remote deployment не выполнялись, поскольку изменён только локальный producer guard.

Следующий175: real MikrotikClient loopback HTTP→owned PostgreSQL→scheduler resultJson→source decoder с first-wave/next-zero/reset/malformed/mixed-interface controls; проверить очистку своих объектов и исключение stale historical samples. После profile acceptance собрать backend и развернуть guard на тестовом стенде; frontend ux-ping173 совместим с absent optional totals. Сейчас оба сервиса удалённого стенда всё ещё ux-ping173, native Ping4/4 подтверждён в173; новое исправление там ещё не доступно. Пароли, конфигурация CHR и тестовый runtime этим блоком не менялись. Локальный коммит без push.

12.5.175 — SQL/HTTP-приёмка достоверности трафика и развёртывание (2026-10-12)

Producer guard174 проверен через настоящий MikrotikClient к loopback HTTP simulator, actual collectTrafficOnce, PostgreSQL18.6 и buildSignalSnapshotFromCollectors. Девять SQL controls: first wave без суммы/со stored valid counters; следующая genuine zero; reset без суммы; malformed123bad и missing counter дают ok=false/no insert; новый второй интерфейс не даёт частичную сумму; следующая полная zero wave; положительная скорость; disabled server без outbound HTTP. Каждая актуальная wave сохраняется в scheduler_runs и проходит реальный source reader. Fixture clock не задерживает тест: в своей базе сохраняется только последняя baseline wave и сдвигается её время на30s. Это не проверка длинной historical continuity/retention и не физический RouterOS counter reset.

Профиль test:traffic-rate дополнен тестом traffic-observation-sql.test.ts. Локально SQL явно skipped без own database; удалённый Node22/PG18.6 профиль прошёл9358ms без SQL skip. База mm_accept_166_1791803283546 принадлежала временному LOGIN без SUPERUSER/CREATEDB/CREATEROLE/BYPASSRLS. Актуальные production DB/JWT secrets не копировались. Тестовые rows убраны finally, база/роль/container удалены trap и отсутствие DB/role проверено каталогами; остались только3 основные контейнера. SQL.

Production backend build прошёл локально и на Debian; 1024 compiled artifacts совпали SHA256 с локальными, different/missing0. Backend ux-traffic175/version1.0.0-test.traffic175 развёрнут; frontend ux-ping173 сохранён и совместим с optional sums. До сборки исправлена строка Docker base, которую ошибочно заменила blanket tag substitution; неисправный Dockerfile не собирался и не выпускался. В.env менялся только BACKEND_IMAGE_TAG, rollback tag ux-ping173 сохранён без копии секретного env. Runtime: verified imageIds, backend healthy/frontend running.

Read-only live smoke: /traffic1440/320, traffic servers200/no pageerrors/no overflow; /servers,/traffic/servers,/scheduler/runs?jobKey=traffic200. Это проверка доступности/совместимости UI, не доказательство доставки Telegram или возникновения всех edge cases в main DB. Нет manual scheduler run/config/password/message writes; автоматический scheduler остаётся штатным. Пароли CHR не менялись; native Ping4/4 в обе стороны подтверждён ранее в173, здесь повторно не заявлен.

Следующий176 — inspect native compound durations53ms561us и parseFloat prefix fallback в Ping parser; положительные source payloads уже сохранены в173, не требуются новые сетевые сущности для первоначального доказательства. Legacy invalid traffic counters/raw-rate consumers, history freshness/failed attempt barriers, interface identity/config changes, scale/multiple backend и внешние интеграции остаются условиями12.5. Не считать guard174–175 полной приёмкой трафика. Локальный коммит без push.

12.5.176 — точность составных длительностей Ping RTT (2026-10-12)

В native payloads173 обоих CHR есть53ms561us и другие ms/us. Прежний parseFloat fallback терял microsecond component; например53ms900us превращалось в53ms вместо rounded54ms,1s53ms561us — в1ms вместо1054ms. parsePingTimeMs теперь разбирает ordered s/ms/us, простые decimal units, comma decimal, clock c minute/second<60 и полную bare millisecond numeric string; duplicate/reverse units, negative, exponent, unknown suffix и numeric-prefix garbage возвращаютnull. Значения хранят дробную точность до прежнего integer rounding общего RTT. Success-reply fallback теперь требует валидную duration; garbage time без explicit counts/loss не изображает успешное измерение. Summary с подтверждённым packet loss может иметь RTTnull — loss от этого не подменяется.

Добавлены unit positive/negative controls, genuine0,53ms900us→54 и1s53ms561us→1054. Offline replay двух сохранённых настоящих CHR responses173 подтвердил дробные значения53.xms и прежний правильный rounded mean53ms/0%loss. Это повторная интерпретация записанного ответа, не новый физический Ping. Local/native replay protocol. Файл evidence optional в test runner: если отсутствует в image, replay явно skipped, форматные guards продолжают исполняться.

Backend production build и полный профиль test:probes прошли (8.0s): HTTP/allowlist/cancellation/actual local fake RouterOS POST, parser/observations. SQL test явно skipped локально без own database; предыдущая SQL173 не выдана за приёмку изменённого176. Это не подтверждает полную RouterOS duration grammar или malformed summary loss/count consistency; остальные источники unknown/provenance и legacy rows остаются открыты. Новые Docker build/deploy/remote SQL на этом остатке квоты не запускались.

Следующий177 — owned SQL/HTTP regression Ping8 на изменённом parser, при необходимости добавить compound/raw-garbage producer cases; затем incremental backend build, compiled parity, deploy и read-only browser smoke. Backend удалённого стенда остаётся ux-traffic175 healthy, frontend ux-ping173. Отдельный реальный success replay не заменяет SQL error persistence. Конфигурация/пароли CHR, production DB, отправки сообщений этим блоком не менялись. Все изменения176 сохранены локальным коммитом без push;12.5 не закрыта.

12.5.177 — SQL-регрессия составного RTT и обновление стенда (2026-10-12)

Ping ownSQL173 расширен двумя controls: summary53ms900us сохраняется как RTT54ms/loss0; raw53bad без подтверждённых counts/loss сохраняется как unknown/null/error. Остальные8 controls сохранены:401/empty/manual/actual100%/zero/API/legacy exact provenance/disabled no outbound. Node22/PG18.6 полный test:probes прошёл24383ms,10 SQL cases без skip. Тесты используют настоящий MikrotikClient к локальному HTTP simulator и действующий collector/PG observations; физический RouterOS malformed response не создавался. Native replay2 выполнен локально176; в удалённом test image evidence file отсутствует и replay явно skipped, не выдан за повторную physical проверку. SQL.

Временная ownDB mm_accept_166_1791803917983 и ограниченная роль удалены trap; отсутствие проверено PG-каталогами, отсутствие test container — docker inventory. Рабочие DB/JWT secrets не копировались. Новая backend image ux-rtt177/version1.0.0-test.rtt177 собрана поверх ux-traffic175; 1024 compiled files совпали с локальными SHA256/missing0/different0. В.env изменён только BACKEND_IMAGE_TAG; rollback tag ux-traffic175. Runtime: backend healthy, frontend ux-ping173 running, imageIds совпали.

Live UI1440/320 прошёл: uptime overview200, unknown filter, no overflow/pageerrors. Actual production probes catalog пустой — эта smoke проверка не изображает main compound/error sample; они подтверждены отдельной ownSQL. Новых native Ping/config/password/Telegram операций не выполнялось. Пароли CHR не менялись. Исправления Ping173/176 и traffic174–175 теперь совместно доступны на тестовом backend; UI layout не менялся.

Следующий178 — read-only audit traffic history freshness при failed collection и legacy invalid-counter provenance; не объявлять старые неоднозначные строки исправленными по новому producer guard. Source unconfirmed/missing diagnostics, summary loss/count consistency, scale/multi-backend, физические WAN и внешние интеграции остаются условиями12.5. Журнал/план синхронизированы; локальный коммит без push. Новых блоков до следующего окна не начинать.

12.5.178 — достоверная история трафика, ручной сбор и свежесть UI (2026-10-12)

Подтверждены source gaps: исторические deltas могли выдавать старую скорость как текущую после failed collection; manual collect-now игнорировал snapshot failures и публиковал success. Добавлена migration0011/traffic_collection_state (одна актуальная запись на server): pending до HTTP, ok/error после записи, lastAttemptAt/lastSucceededAt и конфигурационный updatedAt fingerprint. Pending/error не стирают successful history. Completion обновляет только свою lastAttemptAt; pending не переписывает более новую попытку. Это ограничивает гонки записей, но не является распределённым lock/полной приёмкой нескольких backend.

Freshness reader read-only: enabled device/source, совпадение config fingerprint, state.ok и exact latest sample/success/attempt, TTL3periods (min5s), future tolerance1period. Error/pending/stale/disabled/config change/unknown маскируют current RX/TX; historical observed masks сохраняются. API серверов, клиентов и привязок получает observations/provenance; interface inventory больше не использует stored-rate fallback и не смешивает WG peer rows с interface counters. Source facts дополнительно учитывают новую attempt barrier, поэтому manual error/pending не оставляет старое traffic alarm активным. Для устройств без новой state пока читается прежняя scheduler provenance; первая новая попытка создаёт authoritative barrier. Не считать этот переход доказательством точности каждого старого snapshot.

В flags зарезервирован bit4 countersKnown, выставляется только новым strict collector. Старые/imported rows не переписаны и не объявлены достоверными; previous wave отбирает known counters. Исторический builder не строит deltas между legacy/unknown counters. Учтённые bytes суммируются по подтверждённым соседним дельтам; reset не добавляет произвольный новый counter как объём. Это lower-bound accounted volume, не утверждение полного покрытия периода. В UI подпись «Учтено RX/TX по замерам»; неизвестные скорости/пики/объёмы — —, chart gaps — null. Genuine measured0 сохраняется. Сортировка держит unknown после measured values. Dashboard existing decoder продолжает использовать masks.

Manual collect-now теперь через runSchedulerJobNow/общую запись результата и execution lock. Busy409; fatal/partial failures502 c failures/succeeded и сохранённым scheduler error; confirmed success200. Scheduler traffic ok=false теперь execution limitation, а genuine0 — success; valid offline/down других collectors не изменены. Ошибка setup больше не оставляет collecting=true навсегда: getSettingsRow находится внутри try/finally. Existing event/journal-unknown semantics сохранены.

Frontend projectTrafficObservations валидирует metadata/метрики, маскирует legacy numeric-only DTO, допускает RX/TX histories разной длины при корректных собственных masks. local10s clock переводит expired DTO в stale без новых сетевых запросов. Видны причина failed collection, последняя попытка и successful collection (не выдаётся за подтверждение measured rate). Offline object не скрывает сохранившуюся историю. ReUI Frame/installed Alert/KpiStatGrid/chart-23 adaptation и theme/base-nova сохранены; новые blocks/vendor components не устанавливались.

Сценарий Эталон и схема Артефакт
Ошибка опроса Существующая ReUI Alert → current — → сохранённая RX/TX история ПК1440, телефон320, API-fixture
Genuine0 → TTL Подтверждённая0 → expiry → —, история остаётся E2E clock/control; без clock-based refetch
Legacy counters Нет происхождения → unknown → новая baseline → measured delta Owned SQL/HTTP collector path

Backend test:traffic-rate прошёл: existing formulas, producer body/in-memory boundaries, strict counter/rate guards, freshness/merge. Frontend projection/dashboard unit tests, traffic flags, scheduler11, application-source TypeScript/backend production build/ESLint passed (unused obsolete ifaceNow helper удалён). Первоначальная freshness unit ошиблась default-param undefined, исправлена на прямой missing-state вызов; backend type adapter учитывает PG Date/string. Scheduler regression assertion разделена: traffic command failure является ошибкой исполнения, не device offline observation.

35 unique E2E eventually passed: initial31=27pass/4fail выявили лишнее требование равной RX/TX длины и положительные fixtures без explicit observations; malformed negative gap fixture заменена правильным null. Delta14=13pass/1fail выявил shorthand-json fixture без metadata; исправлено, delta1 passed. Остальные изменённые positive fixtures21 passed29.5s. Новые4 cases error1440/320/history retained even offline, true0/TTL/no refetch, numeric legacy unknown прошли. Screenshot-only scoped repeats2×2 для видимого warning/history внутри main scroller не считаются новыми сценариями; финальные изображения просмотрены. Existing8 user GRE/VXLAN dirty screenshots не тронуты. Full UI1260/backend24 не повторялись без необходимости.

Owned PG18.6/Node22: test:traffic-rate15709ms,9 counter/source +14 history controls (legacy/first/current/error/old-alarm barrier/users/interfaces/manual failure/success/stale/pending/config/disabled). Real MikrotikClient к loopback HTTP simulator, real SQL + Fastify GET/POST; не physical CHR fault. Common test:alert-engine20075ms:26 source/history SQL/GRE8/actual stability. Второй runner имел старую command label в report; corrected по actual command/harness и asserts before public recording, профиль не подменён повторным traffic run. Own DBs mm_accept_166_1791809970201 иmm_accept_166_1791810266923/ограниченные roles/test containers удалены; отсутствие проверено каталогами/docker. Production secrets не копировались. SQL.

Source448 backend+521 frontend/1032 compiled совпали SHA256. Обе production builds прошли (frontend185s Next phase); frontend ux-history178 staged with old backend ux-rtt177 interop, затем backend ux-history178/version1.0.0-test.history178. Runtime healthy/running/verified imageIds; в.env менялись только tags, rollback ux-rtt177/ux-ping173 без копии секретного env. Migration0011 подтверждена main PG. Новый frontend следует перезагрузить: прежняя вкладка не получает новый truth reader автоматически. Additive storage не гарантирует truthful interpretation старым UI.

Native read-only: оба CHR194.226.121.150/104.165.244.7, GET identity/interface200, по2 interfaces, counters valid;4 native GET, no routerConfigWrites/password changes/messages. Это не loss/speed/WAN proof. Live smoke1440/320+3 APIs подтверждает actual provenance/UI/overflow/pageerrors0; error/legacy branches — отдельно fixtures/ownSQL. Main DB read-only только для native checker; schema migration и штатный scheduler writes были частью deploy.

Следующий179 — inspect/fix live monitor-traffic empty/partial/malformed rates (текущий parseMonitorTraffic заменяет их нулями), per-interface fallback и disabled-after-stream-start polling. Не объявлять этот путь принятым по history guards. Peer collection completeness, long sparse intervals, interface recreation/identity, snapshot after restore, scale/multiple instances и external integrations остаются условиями12.5. Локальный коммит без push.

12.5.179 — достоверный live-трафик, остановка и переподключение (2026-10-12)

parseMonitorTraffic больше не превращает empty/missing/malformed/negative/prefix values в0. Требуются именованные уникальные интерфейсы и обе конечные неотрицательные скорости; для aggregate — полный expected set актуальных активных интерфейсов, loopback исключён. Duplicate/wrong/missing interface и неполный ответ дают error. Настоящий measured0 сохраняется. Дельты и Mbps больше не округляются до хранения/передачи: positive1byte/30s не исчезает; legacy bigint rxBps/txBps округляются только при insert, read consumers используют counters. sum snapshot сохраняет полную точность. UI positive меньше разрешения отображается «<1 Кбит/с», а не fake idle0. Это не подтверждение максимальной производительности интерфейса.

Новый readTrafficLiveSample revalidates enabled/current config перед каждым новым native request и перед публикацией. Device disabled/deleted/config change закрывает SSE с причиной; HTTP401/403 закрывают поток без повторного опроса. Inventory обновляется каждый aggregate tick. Только joined HTTP400 при нескольких интерфейсах допускает per-interface fallback; failures не заглушаются пустыми массивами, partial sum не публикуется. Fallback≤4 concurrent commands, complete-wave budget8s; parent abort/deadline отменяет POST/ожидаемые продолжения. Существующий GET транспорт не принимает AbortSignal, его already-started read ограничен4s; после abort не запускаются следующие commands. Нельзя отозвать уже отправленную native команду. Multiple instances/large inventory/long WAN/revocation of already-established JWT streams отдельно не приняты.

Hook сохраняет конкретную причину error при end-of-stream, закрывает transport после decoding/HTTP failure и cleanup, валидирует timestampKind. «Переподключить live» создаёт новый request key в том же object scope, сохраняет последнее подтверждённое значение как historical до нового sample. При смене scope значения не переносятся. Connecting/error состояния явные; disabled retry during connecting предотвращает повторный запуск. Короткая подпись «Последнее live» помещается на320px, причина видна отдельной Alert. TimestampKind backend-receipt подписан «ответ RouterOS получен приложением»: at не выдаётся за часы устройства. Existing ReUI primitives/layout/theme сохранены.

Состояние Схема Артефакт
Source выключен / SSE закрыт Причина → последнее значение → переподключить → новый sample ПК1440, телефон320, API-fixture
Partial native response Inventory → expected set → unknown/error вместо partial0 Real TCP/HTTP owned SQL

Unit tests parser/completeness/fallback/auth/source/abort/10-interface concurrency/positive-small-rate прошли; frontend formatter/projection, application-source TypeScript/backend build/ESLint прошли. Новая unit initially использовала undefined default argument вместо missing field; fixture исправлена.7 unique E2E (2new retry/cause/320/1440 +5 existing SSE), final pass13.3s. Screenshot scoped repeats2 не новые scenarios; visual review выявила clipped long hint, caption сокращена и final frontend пересобран. Hidden tooltip duplicates в production smoke selector исключены filter visible, functional UI не менялся ради теста.

Owned Node22/PG18.6 profile test:traffic-rate24570ms без skip:9 counters/source+14history+10 live transport cases. Последние — actual Fastify TCP SSE и MikrotikClient HTTP к loopback simulator:0,empty,malformed,partial,complete fallback,failed fallback,401 terminal,disable after first sample/no further native requests,initial disabled404/no native requests,config change/closed stream. Fake RouterOS response не объявлен физической неисправностью CHR. Budget/concurrency refinement вызвала оправданный scoped rerun; финальный DB mm_accept_166_1791814796307/ограниченная role/container удалены, отсутствие проверено. Предыдущий временный mm_accept_166_1791813403915 также удалён trap. Production env/credentials/JWT не копировались. SQL.

Source451 backend+522 frontend/1036 compiled совпали. Production builds прошли; первый frontend build с длинной caption superseded до deploy. Staged frontend ux-live179 с backend ux-history178 interop, затем both ux-live179/version1.0.0-test.live179 runtime healthy/running/imageIds. Только.env tags, rollback both ux-history178 без secret env copy; storage migration не добавлялась.

Настоящие CHR SSE получили первый полный sample на обоих sourceId1/2, затем streams отменены: native interface GET + monitor-traffic read-only POST. Пример краткого наблюдения194 RX0.031584/TX0.002016Mbps,104 RX/TX0.002112Mbps; это не SLA/capacity/WAN proof. Пароли/конфигурация не менялись, messages0. Production browser1440/320: actual live labels/receipt provenance,3APIs200,no overflow/pageerrors. Lab AUTH_REQUIRED=false; JWT/RBAC scopes не объявлены полностью принятыми по этой smoke.

Следующий180 — volume precision/binary units. Read-only baseline уже показал: measured1KiB/1MiB API round to0;100×1MiB также aggregate0;1GiB подписан1.0GB. Baseline сохранён в ignored tmp/volume180-baseline.json и пока не выдан за исправление. Sparse intervals/peer completeness/identity recreation/restore/multi-instance/scale и внешние integrations остаются12.5. Локальный коммит без push.

12.5.180 — точность учтённых объёмов и бинарные единицы (2026-10-12)

Read-only baseline подтверждён до правки: measured1KiB/1MiB превращались в API0 и0.0GB;100×1MiB также aggregate0;1GiB выдавался с decimal labelGB. Убрано toFixed(1) из buildTrafficFromSamples/mergeBuiltTraffic: округление отдельных слагаемых больше не теряет суммарный трафик. Учёт остаётся по known соседним counter deltas, reset/unknown не добавляют выдуманные bytes. Отсутствующий baseline и coverage gaps по-прежнему ограничивают полноту периода.

DTO серверов, пользователей и привязок объявляет volumeUnit=GiB. Frontend принимает эту единицу явно, absent unit оставляет volume — без потери known speed/history; unsupportedGB marker отклоняет DTO. fmtGiB отображает Б/КиБ/МиБ/ГиБ/ТиБ/ПиБ, positive ниже1B как<1B, true0 как0B. Число округляется только при форматировании. Existing rate formatter остаётся decimal Кбит/Мбит/Гбит, binary объёмы не смешиваются с decimal rates. TotalsRow получил semantic group label. ReUI layout/theme/components сохранены. Удалён N+1 server-status SELECT на каждую binding: используется уже прочитанный catalog snapshot.

Состояние Схема Пример
Small positive bytes bytes → exact GiB DTO → подходящая binary unit ПК, 320, API-fixture component capture
Old response without unit unknown unit → —, speeds/history retained E2E actual API path fixture

Backend formulas/volume assertion (known positive delta counts; reset does not), frontend unit boundary/unknown/zero/projection, TypeScript/backend build/ESLint passed.18 E2E passed36.3s (2new volume+10detail+6mobile), screenshot delta2 passed10.5s не новые cases; final widget captures просмотрены. Новые positive fixtures явно объявляют GiB. Existing user8 GRE/VXLAN screenshots не тронуты.

Owned Node22/PG18.6 test:traffic-rate31474ms:9 counters+14history+10actual TCP SSE+6new volume SQL cases, без SQL skip. Новые6 — storage/API GET для1B/1KiB/1MiB/1GiB на server/user/binding;100-part aggregate100MiB; reset lower-bound1MiB+512B. Seeded marker5 rows — собственные SQL fixtures, не физические device counts; отсутствие RouterOS calls в volume-only case не объявлено native acceptance. OwnDB mm_accept_166_1791816469068/ограниченная role/container удалены, absence verified. SQL.

Source452/522/compiled1036 SHA256 parity passed. Обе production builds прошли. Frontend ux-volume180 staged with backend ux-live179 interop: volumes без unit unknown до backend update. Затем both ux-volume180/version1.0.0-test.volume180 runtime healthy/running/imageIds. Только.env tags, rollback both ux-live179; no secret env copy/new migration. Старую вкладку следует перезагрузить для новых unit labels.

Actual volume API показывает GiB и неокруглённые quantities обоих CHR из штатных collector rows; этот checker не отправлял новых native commands. Browser1440/320:3APIs200, actual live/receipt labels/provenance, no errors/overflow. Рабочая конфигурация/пароли не менялись, messages0; auto collectors остаются штатными. Это не WAN byte billing/capacity/SLA proof и не exact arithmetic acceptance за пределами safe integer/scale bounds.

Следующий181 — freshness статуса привязанных интерфейсов: enabled device+old running flag не должен объявлять online после failed/stale poll; peer enabled не доказывает handshake. Проверить native flag provenance и scalar shape, не переписывать legacy rows по догадке. Coverage/peer completeness/recreated interfaces/restore/multi-instance/scale/external integrations остаются12.5. Локальный коммит без push.

12.5.181 — достоверность статусов привязанных интерфейсов (2026-10-12)

Статус привязки теперь требует свежего успешного опроса текущей конфигурации устройства и подтверждённых native флагов. Ошибка, pending, disabled source, истёкший TTL или legacy row без status-known marker дают «Нет данных». Первое корректное измерение интерфейса может подтвердить его running, даже когда ещё недостаточно соседних counters для скорости. История и объёмы сохраняются.

Producer строго принимает true/false и native строки true/false/yes/no; missing/invalid flags больше не подменяются false. Новый бит8 status-known добавляется только новым успешным измерениям; bit4 counter-known не меняется, legacy rows не переписываются. Interface inventory проверяет имена/дубликаты. Включённый WG peer означает конфигурацию, поэтому даёт unknown без handshake proof; disabled peer — «Неактивен». Это не проверка реального VPN-туннеля.

DTO привязок содержит statusObservedAt/statusExpiresAt. Frontend проверяет provenance и TTL, обновляет состояние по своему clock даже без повторной загрузки; прежний payload без дат не считается подтверждением. Общие ReUI layout/base-nova и компоненты сохранены.

Состояние Схема Проверка
Native running + свежий успешный poll native flag → known marker → TTL → Работает own SQL и UI1440/320
Ошибка / старый flag / истёкший TTL последнее измерение → Нет данных own SQL и UI1440/320
Enabled WireGuard peer configuration flag → Нет данных own SQL; handshake не заявлен

TypeScript/backend build/ESLint и профильные unit проверки прошли.8 E2E15.7s (2new+6mobile), после последней правки final delta2 passed10s. Один повтор первоначально не запустился из-за Windows sandbox/SWC access denied; корректный разрешённый запуск прошёл, это не UI failure.

Own PG SQL:48 cases9counter+14history+10TCP SSE+6volume+9status,36163ms, без unavailable skip. Новые9 проверяют настоящий collector→SQL→GET bindings на локальном HTTP RouterOS fixture: первое измерение, enabled/disabled peer, inactive interface, malformed flag,401,legacy bit,stale и disabled source. OwnDB mm_accept_166_1791818856762/ограниченная role/container удалены, отсутствие проверено. Первый запуск harness имел неверный путь распаковки; тесты не начались, его временная база/роль также удалены; пути исправлены до приведённого успешного результата.

Source454/524/compiled1036 SHA256 parity, обе production builds прошли. Frontend ux-status181 сначала проверен с backend ux-volume180 interop; затем both ux-status181 healthy/running/imageIds. Только .env tags, rollback ux-volume180, без копирования secret env и новой миграции.

Native GET: оба CHR доступны, interface counters и boolean flags валидны; DB read-only, RouterOS config writes0/password changes0/messages0. Browser1440/320: actual API/live/receipt labels без ошибок/overflow. Положительные binding branches доказаны собственными SQL/UI fixtures, не выданы за существующие пользовательские привязки стенда. Вкладку следует перезагрузить.

Следующий182 — полнота peer-среза при optional endpoint failure и пропуски истории. Interface running не доказывает end-to-end connectivity, enabled peer не доказывает handshake. Coverage/recreated identity/restore/multi-instance/scale/external integrations остаются открыты в12.5. Локальный коммит без push.

12.5.182 — атомарный приём измерений WireGuard peers (2026-10-12)

Разбор optional peers раньше добавлял каждую строку в общий массив сразу: ошибка следующей строки перехватывалась, а корректный префикс сохранялся как свежий срез. Отсутствующие ключи также молча пропускались. Теперь parseTrafficPeers сначала проверяет весь ответ: массив, объекты, непустые interface/public-key, уникальность пары interface+key, counter values и boolean disabled. Только полностью корректный массив передаётся collector. Ошибка не сохраняет ни одного peer из этого ответа; обычные интерфейсные измерения остаются доступны. Пустой массив — корректный пустой срез.

Ответ Схема результата Проверка
Все peers валидны полная проверка → запись полного среза existing SQL collector profile
Корректный peer → некорректный counter полный срез отклонён → interface сохранён → peer Нет данных новая own SQL проверка
Повторная пара / ответ не массив полный срез отклонён → interface сохранён ещё2 own SQL проверки

Owned PG:51 cases9counter+14history+10TCP SSE+6volume+12status,37534ms, без SQL skip.3 новые проверки используют настоящий HTTP fixture→collector→SQL→GET bindings; проверяют отсутствие partial peer rows, unknown peer status и online native iface. Временная база mm_accept_166_1791819465644, ограниченная роль и контейнер удалены, отсутствие проверено.

Backend TypeScript/build passed; source455/524, compiled1040 SHA256 parity. Frontend не менялся: используется уже собранный и проверенный ux-status181. Новая backend production build ux-peer182 развёрнута и healthy; frontend imageId также проверен. Только backend tag в .env, rollback ux-status181, без новой миграции и копирования секретов.

Native read-only проверил ответы identity/interface/peers обоих CHR; оба доступны. Фактическое число peers сохранено в отчёте: пустой native список не выдан за приёмку активного туннеля. Положительные/некорректные peer случаи доказаны собственными fixtures; новые VPN объекты не создавались, этот блок исправляет collector parser. DB read-only, RouterOS config writes0/password changes0/messages0. Production UI1440/320 проверен с actual API/live/receipt labels без ошибок/overflow.

Следующий183: optional peer endpoint failure пока не получает отдельной видимой причины — interface success остаётся успешным, stale peer становится unknown по предыдущему181. Нужно сохранить причину частичного сбоя, не превращая успешные interface measurements в ошибку. Покрытие пропусков истории, recreated identity, масштаб и внешние интеграции остаются12.5. Локальный коммит без push.

12.5.183 — понятная причина частичного сбоя peer-опроса (2026-10-12)

Optional WireGuard peer error больше не исчезает в catch. Collector сохраняет причину в текущей записи traffic_collection_state, snapshot.warning и trafficSettings.lastError. Успешный interface poll остаётся status=ok: известные interface скорости/история не теряются из-за ошибки отдельного peer endpoint. Перезапуск с корректным peer ответом очищает прежнюю причину.

Existing observations.error передаёт причину в DTO. ReUI Alert показывает «Часть измерений недоступна» при current measurements с предупреждением; при unknown/stale остаётся профильная подпись и та же причина. Manual collect response содержит warnings с serverId; event получает warning level и «завершён с ограничениями». Нового schema/state enum и миграции нет. Общий scheduler не объявляет interface poll неуспешным из-за optional peers; ограничение сохранено в его snapshot.

Состояние Схема Результат
Interface success + peer401/invalid measured rates + warning → пользователь видит часть недоступных данных known0 остаётся0; peer Нет данных
Следующий полный poll warning очищен → обычное текущее состояние причина прежнего сбоя не остаётся ложной

TypeScript/backend build/ESLint прошли.4 E2E11.2s:2 новых на1440/320 сохраняют measured0/history и показывают WireGuard401 reason,2 проверяют status TTL/legacy. Это API-fixture UI, не отказ реальных credentials.

Own PG SQL:53 cases9counter+14history+10TCP SSE+6volume+14status,37478ms, без skip.3 предыдущих malformed/duplicate/shape cases теперь также проверяют сохранение warning;2 новые — peer-only401 с успешным iface+DTO cause и recovery с очищением причины. Временная база/ограниченная role/container удалены; exact namespace и отсутствие отражены в публичном отчёте.

Source455/524/compiled1040 SHA256 parity. Обе production builds прошли. Frontend ux-warning183 сначала проверен с backend ux-peer182 interop, затем both ux-warning183 healthy/running/imageIds. Только .env tags; rollback frontend ux-status181/backend ux-peer182, без secret env copy.

Actual API/browser1440/320 подтвердили нормальный runtime/live/receipt labels без page errors/overflow. Оба CHR доступны в preceding182 native read; этот checker не отправлял новых native commands и не создавал искусственный отказ на реальных устройствах. Пароли/конфигурация не менялись, messages0. Туннельное соединение не заявлено: native peers182 были пустыми, fault/recovery доказаны в изолированном SQL/HTTP сценарии. Перезагрузить вкладку для нового Alert.

Следующий184 — явно определить покрытие периода при отсутствующих poll waves/переименовании или пересоздании интерфейса и не выдавать lower-bound за полный период. Внешние интеграции/масштаб и итоговая12.5 остаются открыты. Локальный коммит без push.