y83 code / инструмент

Браузер

Встроенный в приложение браузер на Android WebView. Две независимые сессии:

раздел реестра
Инструменты
код
4 714 строк в 15 файлах
документ
01-browser.md

Снимок: 2026-10-11. Секция хаба Tools, тайл «Веб» / «Web», подпись «Встроенный браузер с вкладками и закладками» / «Browser with tabs and bookmarks». Доступен всегда (тайл на главной).

Что это

  • Видимая — обычный WebView в Compose, пользователь смотрит и кликает.
  • Скрытая (overlay) — постоянная сессия HiddenBrowserSession в невидимом окне TYPE_APPLICATION_OVERLAY за правой границей экрана (alpha = 0), агент управляет ей в фоне без переключения экрана. Используется web_fetch, browser_* MCP-тулами, скриншотами. Куки и storage — общие на процесс (CookieManager), единый профиль с видимым браузером: docs/tech/browser-unified-identity.md.

Фолбэк, когда overlay-разрешения нет или окно отказались рендерить, — одноразовый HeadlessFetcher и Activity FetchOverlayActivity.

Это не «ссылка наружу, открыть в Chrome» — полноценный браузер с вкладками, закладками, историей, сессиями, поиском по странице, куками и storage.

Экран и навигация

Маршрут: y83://browser → Screen.Browser(initialUrl) → BrowserScreen в MainRouter (строки 210–220).

Вложенные состояния (внутри BrowserState, всё в одном экране):

  • вкладки (browser_createTab/closeTab/switchTab),
  • меню (browser_setShowMenu),
  • закладки (browser_toggleBookmark/isBookmarked/getBookmarks/deleteBookmark),
  • история (browser_addToHistory/getHistory/clearHistory),
  • сохранённые сессии (browser_saveSession/loadSession/listSessions/deleteSession),
  • поиск по странице (browser_showFindBar/findOnPage/findNext/findPrev),
  • ошибки (browser_setError/errorJson).

Стартовая страница (BrowserStartPage) — плитки частых сайтов (browser_getFrequentSites), скрывается после первого перехода (browser_dismissStartPage).

Возможности (подробно)

Навигация и вкладки

  • Ввод URL/поискового запроса в адресную «таблетку» (UrlPill), browser_resolveInput сам решает: это URL или поисковый запрос (движок настраивается browser_setSearchEngine).
  • Назад/вперёд (browser_goBack/goForward), перезагрузка (browser_reload).
  • Много вкладок (createTab, closeTab, switchTab, openInNewTab), вкладки персистятся в prefs (browser_saveTabsToPrefs/restoreTabsFromPrefs).
  • Домашняя страница (browser_goHome).

WebView и страница

  • WebViewHost создаёт WebView на вкладку (createTabWebView, prepareWebView), настройки страницы (browser_applyPageSettings/applyPageSettingsToAll): desktop-режим (browser_setDesktopMode), масштаб текста (browser_setTextZoom), JavaScript, WebChromeClient для диалогов (onJsAlert/onJsConfirm), onCreateWindow для popup-ов.
  • SSL-ошибки перехватываются (onReceivedSslError), страница-заглушка при ошибке.
  • Полноэкранная запись (FullPageCapture): run/prewarm/scrollTo — скроллит страницу и склеивает кадры в один PNG через ScreenshotImagePreparer.

Поиск по странице

browser_showFindBar → findOnPage/findNext/findPrev (подсветка, счётчик).

Закладки, история, сессии

  • Закладки и история сохраняются на диск (saveBookmarksToDisk/loadBookmarksFromDisk, saveHistoryToDisk/loadHistoryToDisk) — персист между запусками.
  • Сессии (named-сессии вкладок) — saveSession/loadSession/listSessions/deleteSession, имя санитизируется bridge.sanitizeSessionName.

Хранилище страницы

  • Cookies: getCookies/setCookie/clearCookies.
  • localStorage и sessionStorage: getLocalStorage/setLocalStorage, getSessionStorage/setSessionStorage.

Загрузки

  • browser_downloadFile — системный DownloadManager, имя санитизируется bridge.sanitizeDownloadFileName (BridgeGuards.kt), файл уходит в публичную папку Download (Environment.DIRECTORY_DOWNLOADS), с уведомлением о завершении.

Скрытая overlay-сессия

Постоянный WebView в невидимом окне (HiddenBrowserSession); куки и storage общие с видимым браузером (единый профиль, см. docs/tech/browser-unified-identity.md). Ключевое:

  • окно стоит за правой границей экрана, alpha = 0; если система отказалась рендерить кадр (isBlankFrame), окно поднимается на экран с тем же alpha, снимок повторяется и окно возвращается за границу;
  • enforceViewport до загрузки выставляет размер окна и при необходимости растягивает его под плотность консоли (windowScaled), чтобы desktop-профиль получил честные 1920×1080 CSS-пикселей;
  • BrowserUrlPolicy блокирует навигацию main-frame и загрузки на localhost/приватные подсети и file:// (navigationBlocked/downloadBlocked); загрузка файлов в input[type=file] — только из allowlist;
  • extractContent/extractText — текст страницы, parseOverlayPage — JSON для web_fetch, extractScreenshot — кадр для browser_look/browser_shot;
  • одиночная навигация HeadlessFetcher и Activity FetchOverlayActivity — фолбэк, когда overlay недоступен.

Взаимодействие с VM

BrowserVmInteract.kt — мост между Compose и WebView:

  • sharedShot/preparedOptions — параметры скриншота,
  • bitmapToBase64 — снимок в base64 для vision/MCP.

Где в коде

ФайлСтрокРоль
ui/browser/BrowserScreen.kt874Экран, WebViewHost, диалоги, ошибки
ui/browser/BrowserViewModel.kt683Состояние, вкладки, навигация, закладки, сессии
ui/browser/BrowserSheets.kt546BottomSheet: меню, вкладки, закладки, история, сессии
ui/browser/BrowserStartPage.kt304Стартовая страница, плитки
ui/browser/BrowserChrome.kt385Шапка, нижняя панель, адресная таблетка
ui/browser/BrowserState.kt86StateFlow состояния
ui/browser/BrowserVmInteract.kt405Мост Compose↔WebView, скриншоты
ui/browser/FullPageCapture.kt135Склейка страницы в один PNG
ui/browser/FetchOverlayActivity.kt255Скрытая overlay-сессия для агента
ui/browser/WebViewHelper.kt135Конфиг WebView, парсинг страницы

Данные и API

  • Персист: SharedPreferences (вкладки, закладки, история, сессии) — через BrowserViewModel.
  • Скачивания: публичная папка Download системного DownloadManager.
  • Скриншоты агента: ~/.y83-ws/downloads/screenshots/ (создаёт мост).
  • Backend-эндпоинты: напрямую не зовёт; агент ходит через MCP/мост.
  • Мост: bridge.BridgeState — видимость браузера для агента.

Агент

MCP-тулы (все профили, 19 штук)

ДействиеТулы
Открытие/навигацияbrowser_open, browser_navigate, browser_reload, browser_get_state, browser_content
Действияbrowser_click, browser_type, browser_execute_js, browser_wait
Диагностикаbrowser_console, browser_network, browser_dialogs, browser_timeline, browser_clear_data
Снимки/аудитbrowser_look, browser_shot, browser_audit
Файлыbrowser_upload, browser_downloads

browser_shot {crop} по умолчанию в пикселях кадра; cropSpace: "css" — координаты из marks/browser_find с пересчётом под профиль. format/quality действуют и в скрытой сессии, и в видимой вкладке.

Подробно — ../codex-chat.md §7.

Команды моста (browser_* — 93 штуки)

Видимая сессия: browser_open/navigate/back/forward/reload/click/type/ execute_js/find/scroll/select/press_key/hover/fill_form/submit_form/html/dom/ content/content_text/inject_css/get_state/tabs/new_tab/close_tab/switch_tab/ screenshot/screenshot_config/performance/downloads/download/bookmarks/ history/sessions/save_session/load_session/list_sessions/delete_session/ cookies/local_storage/session_storage/set_cookie/clear_cookies/resolve_wait/ wait_idle/wait_for_page_load/wait_for_selector/wait_for_timeout/wait_for_user/ alert/confirm/prompt/prompts/clear_cookies/service/...

Overlay-сессия (без browser_ → browser_overlay_*): open/navigate/reload/ state/content/html/click/type/select/execute_js/scroll/scroll_by/ scroll_to_element/find/frames/console/network/dialogs/dialog_answer/cookies/ storage/local_storage/permissions/set_dark/wait_idle/wait_for_page_load/ wait_for_selector/wait_for_timeout/screenshot/screenshot_config/clear_data/ download_wait/downloads/file_upload/close/...

Скрытые команды (HiddenBrowser*.kt, 2147 строк в 7 файлах): browser_fetch_overlay(s), весь browser_overlay_*, плюс browser_shots, browser_screenshot_config, browser_overlay_screenshot_config. Обработчик видимой сессии — BridgeBrowserHandlers.kt (778 строк).

Скиллы

  • y83-browser-product — продуктовое тестирование страниц через first-class MCP-тулы.
  • y83-browser-testing — скрытое интерактивное тестирование (desktop 1920×1080 и mobile-профили, консоль/сеть/диалоги/storage, честный full-page скриншот).

Как агент открывает

browser_open (MCP) или мост browser_open. Видимая сессия — для пользователя, overlay — для агента (не переключает экран).

Подводные камни

  • Куки и storage общие на процесс. Скрытая сессия видит логины видимого браузера и наоборот: это единый профиль (docs/tech/browser-unified-identity.md). Если агент «не залогинен» — значит проверку в этом профиле ещё не проходили.
  • Троттлинга скрытого окна нет. Замер на устройстве: document.visibilityState == "visible", document.hidden == false, rAF и таймеры идут штатно при alpha = 0 и выносе за экран — alpha поднимать не нужно.
  • SSL-ошибки перехватываются. onReceivedSslError — нельзя молча пропускать, иначе «страница не грузится» без причины.
  • Полноэкранный скриншот склеивает кадры. Длинная страница → много памяти, FullPageCapture работает через скролл и ScreenshotImagePreparer.
  • Вкладки персистятся в prefs, не в БД. Сброс prefs = потеря вкладок.
  • Имя скачиваемого файла санитизируется (sanitizeDownloadFileName) — произвольное имя из сети не пишется на диск как есть.
  • JS-скрипты страницы извлекаются (WebViewHelper.extractJs) — страница может быть враждебной, извлечение не исполняет код, а читает.

Как обновлять

Источник правды:

  • каталог хаба: data/InstrumentCatalog.kt (id browser),
  • маршрут: ui/navigation/Screen.kt (Screen.Browser), MainRouter,
  • код: ui/browser/*,
  • мост: bridge/BridgeBrowserHandlers.kt, bridge/HiddenBrowser*.kt, bridge/BridgeCommands.kt,
  • MCP: backend/internal/handlers/mcp/browser_*.go,
  • скиллы: skills/y83-browser-product/, skills/y83-browser-testing/, skills/y83-bridge/.

При изменении: новый MCP-тул → «Агент» здесь + ../codex-chat.md §7; новая bridge-команда → «Команды моста»; новый экран-вкладка → «Экран».

Источник: docs/project/hub/01-browser.md · Инструменты · 4 714 строк в 15 файлах. Страница собирается из документации проекта при сборке сайта.