# Conflicts: # extension/background.js # extension/popup.js
KoalaSync Browser Extension
This directory contains the Manifest V3 browser extension for Chrome and Firefox. It owns the popup UI, background service worker, content-script video control, invitation bridge, audio processing, and all browser-local settings.
Where You Are
manifest.base.jsonis the source manifest. The build script creates browser-specificmanifest.jsonfiles indist/chrome/anddist/firefox/.background.jsis the long-lived coordinator: WebSocket client, room state, host-control authority, heartbeat, reconnects, tab selection, and content-script injection.content.jsruns in the selected video tab. It detects video state, applies remote play/pause/seek, handles episode transitions, and applies local audio processing.popup.htmlandpopup.jsimplement the visible extension UI.extension/shared/is generated bynpm run build:extensionfrom the rootshared/directory. Do not edit it directly.
Key Features
- Manifest V3: Service-worker architecture with session persistence and explicit keep-alive handling.
- Pure Vanilla JS: No extension runtime dependencies and no bundler inside
extension/. - On-Demand Connection: The service worker connects only while the user intends to be in a room.
- Host Control & Co-Hosts: Hosts can switch a room into
host-onlymode and grant controller rights to trusted peers. - Episode Auto-Sync: Title/episode changes can open a lobby so peers resume together once everyone is ready.
- Smart Matching & Title Privacy: Matching video tabs are highlighted, while tab/media title sharing can be reduced or disabled.
- Audio Processing: Optional local compressor settings live in the dedicated audio options page.
- Status Diagnostics: The Status tab exposes connection state, ping, video debug data, action history, and copyable logs.
- Dynamic i18n: 15 languages are supported:
en,de,fr,es,it,nl,pl,pt,pt-BR,tr,ru,ja,ko,zh, anduk.
Tab Overview
- Room: Select official/custom server, create or join rooms, view peers, share invite links, and manage Host Control when supported by the relay.
- Sync: Select the video tab, send play/pause/seek/force-sync actions, and view episode lobby state.
- Settings: Configure username, title sharing, noise filtering, auto episode sync, notifications, language, and audio options.
- Status: Inspect connection state, latency, video debug info, history, and logs for bug reports.
- Dev: Hidden developer-only controls shown for the
KoalaDevusername.
Privacy & Permissions
KoalaSync requires <all_urls> host permission so it can detect and control <video> elements on arbitrary sites.
- No browsing history is collected or uploaded.
- Room credentials and user settings are stored locally with
chrome.storage. - No analytics, external scripts, external fonts, or tracking libraries are used by the extension.
- Audio processing is local to the selected tab.
- Title privacy controls decide whether tab/media titles are shared with room peers.
Installation
From the repository root:
npm install
npm run build:extension
Then load the generated bundle:
- Chrome/Chromium: open
chrome://extensions/, enable Developer Mode, and loaddist/chrome. - Firefox: open
about:debugging, choose This Firefox, and loaddist/firefox/manifest.json.
Development
Run the build whenever shared protocol files or extension packaging inputs change:
npm run build:extension
The build copies shared/constants.js, shared/blacklist.js, shared/names.js, and shared/README.md into extension/shared/, injects synchronous constants into content.js, generates browser manifests, and creates zip artifacts in dist/.
Useful focused checks from the repository root:
node -c extension/background.js
node -c extension/content.js
node -c extension/popup.js
node scripts/test-episode-utils.mjs
node scripts/test-title-privacy.mjs
node scripts/test-audio-settings.mjs
node scripts/test-locales.cjs
For the full suite, run:
npm run verify
Do Not Break
- Keep
content.jssynchronous and IIFE-based; it cannot import ES modules directly. - Keep the injection markers used by
scripts/build-extension.cjs. - Keep protocol names in
shared/constants.jsas the source of truth. - Keep extension runtime dependencies at zero unless the project explicitly decides to introduce a bundler.
- Keep all extension assets self-hosted.
Module Structure
| File | Purpose |
|---|---|
background.js |
Service worker: WebSocket protocol, room state, host control, tab/content routing, reconnects |
content.js |
Video detection/control, audio processing, episode transition, host-only guest behavior |
popup.js |
Popup UI: room join/create, tabs, settings, peer list, status, diagnostics |
popup.html |
Popup markup, tabs, onboarding, status/debug surfaces |
bridge.js |
Invitation bridge injected into sync.koalastuff.net |
episode-utils.js |
Shared episode-title parser imported by background and injected into content at build time |
title-privacy.js |
Tab/media title privacy modes and sanitization helpers |
audio-options.html / audio-options.js / audio-options.css |
Dedicated local audio-processing settings page |
page-api-seek-overrides.js |
Page-level seek bridge for site-specific player APIs |
modules/tab-manager.js |
Tab lifecycle helper used by the background service worker |
i18n.js |
Dynamic locale loader and DOM translation helper |
locales/ |
Runtime popup translations |
_locales/ |
Browser-store manifest translations |
shared/ |
Generated mirror of root shared constants, blacklist, names, and README |