A browser extension that lets you summarize any webpage and ask questions using AI.
1
fork

Configure Feed

Select the types of activity you want to include in your feed.

Wire extension display name from config; generic Summarizer + AI chat copy

- CONFIG.EXTENSION drives options title/shortcuts; remove duplicate version
- Manifest name/description; popup branding and chat placeholder
- AGENTS.md: name/version/shortcut maintenance notes
- Console log tags [Summarizer]; build.sh comment

+52 -29
+4
AGENTS.md
··· 18 18 19 19 ## Other Browser Differences 20 20 Read BROWSER_SUPPORT.md for info. 21 + 22 + ## Name, version, shortcuts 23 + - **Version** lives in the active manifest (`version`) and any browser-specific manifest you ship. Do not duplicate it in `scripts/config.js`. 24 + - **Display name and default shortcut copy** for the settings page come from `CONFIG.EXTENSION` (`NAME`, `SHORTCUT`, `SHORTCUT_MAC`), filled in `options/options.js`. When you change the extension **name** or **suggested keyboard shortcuts**, update the manifest **`name` / `commands`** and the same fields in **`CONFIG.EXTENSION`** so the options tab title and shortcut help stay accurate.
+1 -1
build.sh
··· 1 1 #!/bin/bash 2 2 3 - # Build script for WebAI Summarizer 3 + # Build script for the Summarizer extension 4 4 # Usage: ./build.sh [chrome|firefox] 5 5 6 6 BROWSER=${1:-chrome}
+2 -2
manifest-chrome.json
··· 1 1 { 2 2 "manifest_version": 3, 3 - "name": "WebAI Summarizer", 3 + "name": "Summarizer", 4 4 "version": "1.0.0", 5 - "description": "Ask questions and summarize any webpage with AI", 5 + "description": "Summarize any webpage and use AI chat about what you're reading", 6 6 "permissions": [ 7 7 "activeTab", 8 8 "tabs",
+2 -2
manifest-firefox.json
··· 1 1 { 2 2 "manifest_version": 3, 3 - "name": "WebAI Summarizer", 3 + "name": "Summarizer", 4 4 "version": "1.0.0", 5 - "description": "Ask questions and summarize any webpage with AI", 5 + "description": "Summarize any webpage and use AI chat about what you're reading", 6 6 "browser_specific_settings": { 7 7 "gecko": { 8 8 "id": "webai-summarizer@anomaly.co",
+2 -2
manifest.json
··· 1 1 { 2 2 "manifest_version": 3, 3 - "name": "WebAI Summarizer", 3 + "name": "Summarizer", 4 4 "version": "1.0.0", 5 - "description": "Ask questions and summarize any webpage with AI", 5 + "description": "Summarize any webpage and use AI chat about what you're reading", 6 6 "permissions": [ 7 7 "activeTab", 8 8 "tabs",
+2 -5
options/options.html
··· 2 2 <html> 3 3 <head> 4 4 <meta charset="UTF-8" /> 5 - <title>Summarize — Settings</title> 5 + <title>Summarizer — Settings</title> 6 6 <link rel="stylesheet" href="options.css" /> 7 7 </head> 8 8 <body> ··· 295 295 296 296 <div class="form-group"> 297 297 <label>Keyboard Shortcut</label> 298 - <div class="shortcut-display"> 299 - <code>Ctrl+Shift+U</code> (Windows/Linux) &nbsp;·&nbsp; 300 - <code>Cmd+Shift+U</code> (Mac) 301 - </div> 298 + <div class="shortcut-display" id="shortcut-display"></div> 302 299 <p class="help"> 303 300 <a href="#" id="keyboard-shortcuts-link" 304 301 >Change or enable keyboard shortcut</a
+18
options/options.js
··· 295 295 return infoDiv; 296 296 } 297 297 298 + /** Tab title + shortcut help from CONFIG.EXTENSION (keep in sync with manifest name / commands). */ 299 + function applyExtensionMetadata() { 300 + document.title = `${CONFIG.EXTENSION.NAME} — Settings`; 301 + const el = document.getElementById("shortcut-display"); 302 + if (!el) return; 303 + const { SHORTCUT, SHORTCUT_MAC } = CONFIG.EXTENSION; 304 + el.replaceChildren(); 305 + const win = document.createElement("code"); 306 + win.textContent = SHORTCUT; 307 + el.appendChild(win); 308 + el.appendChild(document.createTextNode(" (Windows/Linux) \u00a0\u00b7\u00a0 ")); 309 + const mac = document.createElement("code"); 310 + mac.textContent = SHORTCUT_MAC; 311 + el.appendChild(mac); 312 + el.appendChild(document.createTextNode(" (Mac)")); 313 + } 314 + 298 315 async function initializePage() { 316 + applyExtensionMetadata(); 299 317 const { theme } = await chrome.storage.sync.get("theme"); 300 318 currentTheme = theme || "system"; 301 319 applyTheme(currentTheme);
+2 -2
popup/popup.html
··· 17 17 <div class="logo-mark"> 18 18 <span class="brand-icon" aria-hidden="true"></span> 19 19 </div> 20 - <span class="logo-text">Summarize</span> 20 + <span class="logo-text">Summarizer</span> 21 21 </div> 22 22 <div class="header-right"> 23 23 <!-- Theme toggle: cycles light → dark → system --> ··· 130 130 type="text" 131 131 id="chat-input" 132 132 class="chat-input" 133 - placeholder="Ask about this article..." 133 + placeholder="AI chat — ask about this page…" 134 134 /> 135 135 <button id="chat-send" class="chat-send-btn" title="Send"> 136 136 <svg
+2 -1
popup/popup.js
··· 1 - // Popup script - Simple summarizer, no streaming, no history, resets on close 1 + // Popup: quick summary + chat; streams via background; in-memory chat until the popup closes. 2 2 let isLoading = false; 3 3 let currentPageContent = ""; 4 4 let isExtracting = true; 5 5 let quickSummary = ""; 6 6 let detailedSummary = ""; 7 + /** Tracks summary mode ("quick" while generating); not read elsewhere yet — safe to use for future UI. */ 7 8 let currentSummaryMode = "none"; // "none", "quick", "detailed" 8 9 let currentTabId = null; 9 10 let currentTabUrl = "";
+2 -4
scripts/background.js
··· 130 130 131 131 // ── Prompt templates from CONFIG ───────────────────────────────────────── 132 132 const OLLAMA_CONTEXT_TEMPLATE = CONFIG.OLLAMA.CONTEXT_TEMPLATE; 133 - const OLLAMA_SINGLE_MESSAGE_TEMPLATE = CONFIG.OLLAMA.SINGLE_MESSAGE_TEMPLATE; 134 133 135 134 chrome.runtime.onInstalled.addListener(() => { 136 135 // Set default settings only if they don't already exist ··· 180 179 CONFIG.CACHE.SUGGESTIONS + tabId, 181 180 ]); 182 181 } catch (e) { 183 - console.error("[WebAI] Error clearing cache:", e); 182 + console.error("[Summarizer] Error clearing cache:", e); 184 183 } 185 184 } 186 185 ··· 191 190 } 192 191 }); 193 192 194 - // Handle keyboard shortcut 195 - // Chrome & Firefox: Listen for "summarize-page" command 193 + // Handle keyboard shortcut (manifest command + optional legacy alias) 196 194 chrome.commands.onCommand.addListener((command) => { 197 195 if (command === "summarize-page" || command === "open-summarizer") { 198 196 chrome.tabs.query({ active: true, currentWindow: true }).then((tabs) => {
+12 -7
scripts/config.js
··· 1 1 /** 2 - * Shared configuration for WebAI Summarizer 2 + * Shared configuration for the Summarizer extension 3 3 * Centralizes all defaults, constants, and settings 4 4 */ 5 5 ··· 37 37 KEEP_ALIVE: "0", 38 38 }, 39 39 40 - // Content extraction settings 40 + // Content extraction settings (scripts/content.js — Readability + paragraph fallback) 41 41 EXTRACTION: { 42 42 MAX_LENGTH: 50000, 43 + /** Not used by content.js today (fallback uses `p` nodes); kept for future richer fallback. */ 43 44 FALLBACK_SELECTORS: [ 44 45 "article p", 45 46 "article div", ··· 101 102 CHAT_SUGGESTIONS: `Based on this chat response, generate 2 natural follow-up questions the reader might want to ask next. Keep questions short (5-8 words). Make them specific to what was just discussed. Return only the 2 questions, one per line, no numbering or bullet points.`, 102 103 }, 103 104 104 - // Ollama template strings 105 + // Ollama template strings (background native `/api/generate` prompt assembly) 105 106 OLLAMA: { 106 107 CONTEXT_TEMPLATE: "Context:\n${context}\n\nUser: ${userMessage}", 108 + /** Single-turn prompts use the raw user string in code; kept here for parity / edits. */ 107 109 SINGLE_MESSAGE_TEMPLATE: "${userMessage}", 108 110 }, 109 111 110 - // Extension metadata 112 + /** 113 + * Display strings wired in `options/options.js` (document title + shortcut help). 114 + * Name: keep aligned with manifest `name`. Shortcuts: same chord as manifest `commands.summarize-page.suggested_key`. 115 + * Extension version lives only in the manifest(s); use `chrome.runtime.getManifest().version` in code if needed. 116 + */ 111 117 EXTENSION: { 112 - NAME: "WebAI Summarizer", 113 - VERSION: "1.0.0", 118 + NAME: "Summarizer", 114 119 SHORTCUT: "Ctrl+Shift+U", 115 - SHORTCUT_MAC: "Command+Shift+U", 120 + SHORTCUT_MAC: "Cmd+Shift+U", 116 121 }, 117 122 }; 118 123
+3 -3
scripts/content.js
··· 142 142 } 143 143 144 144 // Otherwise fall back to basic extraction 145 - console.log( 146 - "[WebAI] Readability extracted minimal content, trying fallback...", 145 + console.debug( 146 + "[Summarizer] Readability extracted minimal content, trying fallback...", 147 147 ); 148 148 const fallback = extractFallback(); 149 149 ··· 154 154 155 155 return result; 156 156 } catch (error) { 157 - console.error("[WebAI] Readability error:", error); 157 + console.error("[Summarizer] Readability error:", error); 158 158 // On error, try fallback 159 159 return extractFallback(); 160 160 }