-
Notifications
You must be signed in to change notification settings - Fork 0
Architecture ru
English | 中文 | 日本語 | 한국어 | Español | Português | Русский
browsa — расширение Chrome MV3 с чат-UI в боковой панели. Исходники расширения не требуют сборки — Chrome загружает каждый JS-файл напрямую; единственная сборка (build/build.mjs) бандлит вендорские библиотеки через esbuild.
page content scripts (MAIN-world interceptors / ISOLATED-world selection toolbar)
│ chrome.runtime.sendMessage / port
▼
background.js (service worker, single message router)
│ handle() switch — case bodies live in lib/handlers/*
▼
sidepanel.js (the UI orchestrator)
▲
├── browsa-nav long-lived port: NAVIGATED / XHS pushes / SELECTION_ACTION
├── browsa-chat fresh per turn: main chat stream (chunk protocol)
└── browsa-subchat fresh per send: detail-thread stream
-
background.js— единственный маршрутизаторchrome.runtime.onMessage. Один switch вhandle()остаётся единственным экспортируемым диспетчером, который импортируют тесты; тела самых больших кейсов живут вlib/handlers/(chat / subchat / session / семейство attach / mermaid-repair / provider-resolver / approval-relay / agent-stream-session / prompt-assembly / site-cache-store …). - Состояние стримов (
streamPorts/streamState/chatControllers/ Map-ы ожидающих одобрений …) живёт в одном экземпляре вlib/state.js, которыйbackground.jsреэкспортирует — тесты, импортирующие из../background.js, получают те же экземпляры Map.
-
browsa-nav— долгоживущий: подключается один раз при инициализации панели, переподключается после перезапусков SW по паттернуconnectNavPort()(backoff 1с; у нового объекта порта должны быть заново навешены все onMessage-слушатели). Он означает «какую бы вкладку панель ни смотрела» — перерегистрация под новым tabId черезNAV_FOLLOWи есть его семантика. -
browsa-chat/browsa-subchatоткрываются заново на каждый ход / каждую отправку: один ход = один порт. Разрыв из-за заснувшего SW не требует самолечения — следующая отправка откроет новый. Это намеренно: жизненный цикл одного хода никогда не протекает в следующий.
- Большинство обработчиков: успех
{ ok: true, data }/ брошенная ошибка{ ok: false, error, code, hint }. - Некоторые (
APPROVAL_RESPOND/CLARIFY_RESPOND…) ловят сбои реле внутренне и возвращают внутренний{ ok, ... }внутриdata. - Читайте конкретный кейс, прежде чем делать предположения. Неправильное прочтение конверта — целое семейство реальных багов, найденных в общеремозиторном проходе 2026-08 (например,
LOAD_SESSIONвозвращает -1 при промахе — 0 это легальная пустая сессия; внутреннийres.data.ok— настоящий флаг успеха).
Переключение разговоров больше не отменяет идущий ход. Правило маршрутизации в одну строку: пока панель смотрит на стрим, ход пишет в ЖИВУЮ историю (bg === false); как только ход уходит в фон, он пишет в снимок ИСХОДНОЙ сессии. persistTurnEntry — единственный писатель; REASSIGN_STREAM_SESSION (автосохранение при переключении прочь) и STREAM_PEEK (переподключение при возврате) — единственные два сообщения, меняющие bg. Прерванный ход с уже стримленным текстом спасается как { interrupted: true } в исходную сессию (Esc / idle-таймаут / обрыв сети); явное уничтожение истории использует salvage: false.
- SW засыпает после ~30с простоя. Модульные Map-ы сбрасываются при каждом перезапуске — никогда не храните там долговечное состояние.
-
setTimeoutвнутри SW ненадёжен после возврата из обработки сообщения — используйтеchrome.alarmsилиchrome.storage.session. -
Регистрация слушателей по требованию — доменный стиль: три слушателя
chrome.webNavigationрегистрируются, только пока существует navPort,tabs.onRemovedрегистрируется по требованию, будильник stream-GC существует, только покаstreamStateнепуст — иначе каждая навигация/закрытие вкладки холодно стартуют SW (парсинг модуля 644KB) ради no-op. -
chrome.storage.sessionпереживает перезапуски SW в рамках одной сессии браузера (восстановление site-кэшей, ожидающие SELECTION_ACTION …).
chrome.tabs.onActivated не должен трогать DOM — Chrome сохраняет документ боковой панели живым при переключениях вкладок. Обновляйте currentTabId и текст page-meta, отправляйте NAV_FOLLOW. Прерывания стрима адресуют СОБСТВЕННУЮ вкладку стрима (streamTabIdOf()), никогда текущую вкладку панели.
| Путь | Ответственность |
|---|---|
background.js |
SW; диспетчеризация handle() + инлайновые мелкие кейсы (ATTACH_PAGE …) |
lib/handlers/* |
Тела больших кейсов: chat / subchat / session / attach-* / approval-relay / provider-resolver / stream-dispatch / agent-stream-session / site-cache-store / attach-store / attach-modes |
lib/state.js |
Map-ы состояния стримов + протокол pushChunk + терминальные надгробия (tombstones) |
lib/llm-client.js |
Слой сетевых протоколов: четыре стрима на одном скелете openSseStream()
|
lib/message-builder.js |
Формы запросов по провайдерам + ageStaleAttachments
|
lib/agent-turn.js / lib/image-budget.js
|
Общий слой агентских ходов (бюджет/backfill текста/изображений) |
lib/prompt-assembly.js |
CAPABILITY_HINTS_ENTRIES — единственный источник текста render-контракта |
lib/storage.js |
обёртка chrome.storage.local; глобальная история + разделённые ключи сессий |
lib/sidepanel/* |
26 UI-модулей (конвейер рендеринга, панель сессий, detail thread, таймлайн …) |
lib/content-scripts/* |
Сайтовые перехватчики в MAIN world + панель выделения в ISOLATED; знание по сайтам в SITES.md
|
lib/page-extractor.js … |
Слой прикрепления/экстракции (каскад reader/dom/full/auto + сайтовые fast-path + хэндоффы PDF/Office/ASR) |
Авторитетные версии: Architecture (англ.) / Architecture-zh (кит.) — снимок первичного перевода ИИ, синхронизирован 2026-10-01.
English
- Home
- Architecture
- Rendering Pipeline
- Storage Model
- Providers and Agents
- ASR and Video Analysis
- Security Model
- Design Decisions
- Contributing
中文
相关 / Related
日本語
한국어
Español
- Inicio
- Arquitectura
- Pipeline de renderizado
- Modelo de almacenamiento
- Proveedores y agentes
- ASR y análisis de vídeo
- Modelo de seguridad
- Decisiones de diseño
- Contribuir
Português
- Início
- Arquitetura
- Pipeline de renderização
- Modelo de armazenamento
- Provedores e agentes
- ASR e análise de vídeo
- Modelo de segurança
- Decisões de design
- Contribuindo
Русский