···11+# synthes.is
22+33+To install dependencies:
44+55+```bash
66+bun install
77+```
88+99+To run:
1010+1111+```bash
1212+bun run index.ts
1313+```
1414+1515+This project was created using `bun init` in bun v1.3.0. [Bun](https://bun.com) is a fast all-in-one JavaScript runtime.
+63
entrypoints/background.ts
···11+export default defineBackground(() => {
22+ // Create context menu on install
33+ browser.runtime.onInstalled.addListener(() => {
44+ browser.contextMenus.create({
55+ id: 'annotate-selection',
66+ title: 'Annotate',
77+ contexts: ['selection'],
88+ });
99+ });
1010+1111+ // Handle context menu click
1212+ browser.contextMenus.onClicked.addListener(async (info, tab) => {
1313+ if (info.menuItemId === 'annotate-selection' && tab?.id) {
1414+ // Tell content script to save annotation immediately
1515+ browser.tabs.sendMessage(tab.id, {
1616+ type: 'SAVE_ANNOTATION',
1717+ });
1818+ }
1919+ });
2020+2121+ // Open sidepanel when extension icon is clicked
2222+ browser.action.onClicked.addListener(async (tab) => {
2323+ if (tab.id) {
2424+ // Chrome API
2525+ if (browser.sidePanel) {
2626+ await browser.sidePanel.open({ tabId: tab.id });
2727+ }
2828+ }
2929+ });
3030+3131+ // Handle auth state changes
3232+ browser.runtime.onMessage.addListener((message, sender, sendResponse) => {
3333+ if (message.type === 'AUTH_STATE_CHANGED') {
3434+ // Broadcast auth state change to all extension contexts
3535+ browser.runtime.sendMessage({
3636+ type: 'AUTH_STATE_CHANGED',
3737+ isAuthenticated: message.isAuthenticated,
3838+ }).catch(() => {
3939+ // Ignore if no listeners
4040+ });
4141+ sendResponse({ success: true });
4242+ return true;
4343+ }
4444+4545+ if (message.type === 'LOGOUT') {
4646+ handleLogout().then(() => sendResponse({ success: true }));
4747+ return true;
4848+ }
4949+ });
5050+5151+ async function handleLogout() {
5252+ // Clear OAuth session from storage
5353+ await browser.storage.local.remove('synthesis-oauth:session');
5454+5555+ // Notify all contexts
5656+ browser.runtime.sendMessage({
5757+ type: 'AUTH_STATE_CHANGED',
5858+ isAuthenticated: false,
5959+ }).catch(() => {
6060+ // Ignore if no listeners
6161+ });
6262+ }
6363+});