From 13681c297b2d3e87f84dd4b5cf5ab0e1dfde99d9 Mon Sep 17 00:00:00 2001 From: mic Date: Sat, 28 Mar 2026 11:03:56 +0100 Subject: [PATCH 1/7] summarize batch option added --- _locales/en/messages.json | 4 ++++ options/mzta-options-default.js | 2 +- pages/summarize/mzta-summarize.html | 1 + 3 files changed, 6 insertions(+), 1 deletion(-) diff --git a/_locales/en/messages.json b/_locales/en/messages.json index 15824bc7..8693213a 100644 --- a/_locales/en/messages.json +++ b/_locales/en/messages.json @@ -2084,5 +2084,9 @@ "prefs_chatgpt_win_position_info":{ "message": "Leave empty to use the default position.", "description": "" + }, + "prefs_OptionText_action_auto_batch": { + "message": "When the email is received", + "description": "" } } \ No newline at end of file diff --git a/options/mzta-options-default.js b/options/mzta-options-default.js index c7cbfcd8..c278455c 100644 --- a/options/mzta-options-default.js +++ b/options/mzta-options-default.js @@ -138,7 +138,7 @@ export const prefs_default = { spamfilter_threshold: 70, spamfilter_enabled_accounts: [], summarize: false, - summarize_auto: 1, // 0: disabled, 1: manual button, 2: automatic + summarize_auto: 1, // 0: disabled, 1: manual button, 2: automatic, 3: batch processing summarize_display_mode: 'inline', // 'inline' or 'webchat' summarize_max_display_length: 0, // 0 = no limit, otherwise max chars shown inline spamfilter_show_msg_panel: true, diff --git a/pages/summarize/mzta-summarize.html b/pages/summarize/mzta-summarize.html index ea6f59c7..2bf1d486 100644 --- a/pages/summarize/mzta-summarize.html +++ b/pages/summarize/mzta-summarize.html @@ -34,6 +34,7 @@ +
__MSG_prefs_OptionText_summarize_auto_Info__ From 92b8853861daadca8c5cffb5be28c77e3198e5bd Mon Sep 17 00:00:00 2001 From: bittin1ddc447d824349b2 Date: Sat, 28 Mar 2026 10:42:38 +0100 Subject: [PATCH 2/7] Translated using Weblate (Swedish) Currently translated at 100.0% (519 of 519 strings) Translation: ThunderAI for Thunderbird/main Translate-URL: https://hosted.weblate.org/projects/thunderai/main/sv/ --- _locales/sv/messages.json | 115 +++++++++++++++++++++++++++++++++++++- 1 file changed, 114 insertions(+), 1 deletion(-) diff --git a/_locales/sv/messages.json b/_locales/sv/messages.json index 41df75e4..ec2b7af2 100644 --- a/_locales/sv/messages.json +++ b/_locales/sv/messages.json @@ -1087,7 +1087,7 @@ "message": "Tröskel skräppost" }, "spamfilter_no_reports": { - "message": "Inga meddelanden har ännu granskats för skräppost. Här hittar du en lista över de senaste 100 skräppostrapporterna för den aktuella sessionen." + "message": "Inga meddelanden har ännu granskats för skräppost. Här hittar du en lista över de senaste 100 skräppostrapporter." }, "SpamReport_Title": { "message": "Rapporter om skräppostfilter" @@ -1457,5 +1457,118 @@ }, "prefs_chatgpt_win_position_info": { "message": "Lämna tomt för att använda standardpositionen." + }, + "webchat_save_as_summary": { + "message": "Spara som sammanfattning" + }, + "prefs_cache_title": { + "message": "Cachelagring" + }, + "prefs_cache_storage_size": { + "message": "Cachestorlek" + }, + "prefs_cache_clear_button": { + "message": "Rensa cache" + }, + "prefs_cache_clear_confirm": { + "message": "Är du säker på att du vill rensa all cachad data (sammanfattningar, skräppostrapporter, översättningar)? Den här åtgärden kan inte ångras." + }, + "prefs_cache_clear_done": { + "message": "$COUNT$ register borttagna.", + "placeholders": { + "count": { + "content": "$1" + } + } + }, + "prefs_OptionText_auto_summary": { + "message": "Aktivera automatisk AI-sammanfattning för förhandsgranskningar av meddelanden" + }, + "prefs_OptionText_auto_summary_Info": { + "message": "Om markerat kommer ThunderAI automatiskt att generera och visa AI-sammanfattningar ovanför e-postmeddelanden när de öppnas. Observera att detta innebär att alla meddelanden du förhandsgranskar omedelbart skickas till den konfigurerade AI-tjänsten." + }, + "auto_summary_title": { + "message": "ThunderAI sammanfattning" + }, + "auto_summary_generating": { + "message": "Genererar AI-sammanfattning..." + }, + "auto_summary_failed": { + "message": "Misslyckades att generera AI-sammanfattning. Bekräfta dina inställningar och försök igen." + }, + "prefs_OptionText_summarize_auto": { + "message": "Sammanfatta meddelanden automatiskt" + }, + "prefs_OptionText_summarize_auto_disabled": { + "message": "Inaktiverad" + }, + "prefs_OptionText_summarize_auto_manual": { + "message": "Visa sammanfattningsknapp" + }, + "prefs_OptionText_summarize_auto_automatic": { + "message": "Generera automatiskt" + }, + "prefs_OptionText_summarize_auto_Info": { + "message": "Välj om sammanfattningar ska genereras automatiskt när meddelanden visas. Kräver en API-baserad anslutning (inte ChatGPT Web)." + }, + "prefs_OptionText_summarize_display_mode": { + "message": "Visa sammanfattning i" + }, + "prefs_OptionText_summarize_display_mode_inline": { + "message": "Meddelandepanel (inbäddad)" + }, + "prefs_OptionText_summarize_display_mode_webchat": { + "message": "Chatt fönster" + }, + "prefs_OptionText_summarize_display_mode_Info": { + "message": "Välj var sammanfattningsresultatet visas. I infogat läge visas en sammanfattningsbanderoll direkt i meddelandefönstret. I chattfönsterläget öppnas AI-chattfönstret." + }, + "prefs_OptionText_summarize_max_display_length": { + "message": "Max skärmlängd" + }, + "prefs_OptionText_summarize_max_display_length_Info": { + "message": "Maximalt antal tecken som ska visas i den inbäddade sammanfattningen. Ange 0 för obegränsad gräns." + }, + "summarize_see_more": { + "message": "Se mer" + }, + "summarize_see_less": { + "message": "Se mindre" + }, + "summarize_title": { + "message": "ThunderAI översikt" + }, + "get_ai_summary": { + "message": "AI sammanfattning" + }, + "summarize_collapse": { + "message": "Fäll in sammanfattning" + }, + "summarize_generating": { + "message": "Genererar sammanfattning..." + }, + "summarize_error": { + "message": "Misslyckades att generera sammanfattning" + }, + "summarize_click_to_generate": { + "message": "Klicka här för att skapa en sammanfattning" + }, + "summarize_chatgpt_web_not_supported": { + "message": "Autosammanfattning kräver en API-baserad anslutning. Konfigurera en API-anslutning i ThunderAI-inställningarna." + }, + "summarize_refresh": { + "message": "Uppdatera sammanfattning" + }, + "spamfilter_refresh": { + "message": "Uppdatera skräppostrapport" + }, + "spamfilter_delete": { + "message": "Ta bort skräppostrapport" + }, + "summarize_delete": { + "message": "Ta bort sammanfattning" + }, + "summary_by": { + "message": "Sammanfattning av" } } From a8c69d44267af4809cfd977fe2ffb77db21549cc Mon Sep 17 00:00:00 2001 From: mic Date: Sat, 28 Mar 2026 11:39:11 +0100 Subject: [PATCH 3/7] summarize now is possibile on aslo mail receive. see #580 #723 --- _locales/en/messages.json | 2 +- claude-spec/01-architecture.md | 23 +++++++++++ claude-spec/05-options.md | 4 +- mzta-background.js | 67 ++++++++++++++++++++----------- options/mzta-options-default.js | 2 +- pages/summarize/mzta-summarize.js | 15 +++++++ 6 files changed, 86 insertions(+), 27 deletions(-) diff --git a/_locales/en/messages.json b/_locales/en/messages.json index 8693213a..2c8d22d3 100644 --- a/_locales/en/messages.json +++ b/_locales/en/messages.json @@ -1966,7 +1966,7 @@ "description": "" }, "prefs_OptionText_summarize_auto_automatic": { - "message": "Generate automatically", + "message": "When the email is opened", "description": "" }, "prefs_OptionText_summarize_auto_Info": { diff --git a/claude-spec/01-architecture.md b/claude-spec/01-architecture.md index 085affed..a5b08756 100644 --- a/claude-spec/01-architecture.md +++ b/claude-spec/01-architecture.md @@ -47,6 +47,7 @@ The `summarize_display_mode` preference (`'inline'` or `'webchat'`) controls whe the summary is displayed. The `summarize_auto` preference controls when it is triggered. - `summarize_auto = 2` (automatic) always generates inline, regardless of `summarize_display_mode`. +- `summarize_auto = 3` (on receive) pre-caches the summary silently when the email arrives via `onNewMailReceived`. When the user later opens the message, the cache hit triggers an instant display. - `summarize_auto = 1` (manual button) respects `summarize_display_mode`: - `'inline'` → button click triggers inline generation - `'webchat'` → button click opens the AI chat window via `_openSummaryWebchat()` @@ -67,6 +68,7 @@ mzta-background.js (checks summarize_auto + summarize_display_mode prefs) │ display_mode = inline → click triggers inline gen │ │ display_mode = webchat → click opens chat window │ │ summarize_auto = 2 → generate immediately (always inline)│ + │ summarize_auto = 3 → cache hit (pre-cached on receive) │ └──────────────────────────────────────────────────────────┘ ↓ (if generating inline) taSummaryStore (check cache / set processing) @@ -78,6 +80,27 @@ mzta-background.js (checks summarize_auto + summarize_display_mode prefs) mzta-compose-script.js (render summary banner in message body) ``` +### Data Flow: Background Summary on Email Receive (summarize_auto = 3) + +When `summarize_auto = 3`, a summary is generated silently when a new email arrives. The flow mirrors `add_tags_auto`: + +``` +New email arrives + ↓ +browser.messages.onNewMailReceived + ↓ +newEmailListener (checks _process_incoming, which includes summarize_auto === 3) + ↓ +processEmails({ summarizeOnReceive: true }) + ↓ (single loop — shared with addTagsAuto / spamFilter) +_generateSummaryForMessage(headerMessageId, null, { messageData }) + ← tabId is null → no UI messages sent, silent pre-cache + ↓ +taSummaryStore.saveSummary() + ↓ +[later] user opens the message → initSummary → cache hit → showSummary instantly +``` + ## Key Modules | File | Role | diff --git a/claude-spec/05-options.md b/claude-spec/05-options.md index b61cd92b..d929ceb9 100644 --- a/claude-spec/05-options.md +++ b/claude-spec/05-options.md @@ -95,8 +95,8 @@ These are generated programmatically at the bottom of `mzta-options-default.js` | `spamfilter_enabled_accounts` | `[]` | Accounts where spam filter is active | | `spamfilter_show_msg_panel` | `true` | Show info panel on spam detection | | `summarize` | `false` | Enable email summarization | -| `summarize_auto` | `1` | Auto-summarize mode: `0` = disabled, `1` = manual (show "click to generate" button), `2` = automatic (generate on message open) | -| `summarize_display_mode` | `'inline'` | Where to display summaries: `'inline'` = message pane banner, `'webchat'` = AI chat window. Note: `summarize_auto = 2` always uses inline regardless of this setting. | +| `summarize_auto` | `1` | Auto-summarize mode: `0` = disabled, `1` = manual (show "click to generate" button), `2` = automatic (generate on message open), `3` = generate on email receive (background pre-cache via `onNewMailReceived`, no UI during generation) | +| `summarize_display_mode` | `'inline'` | Where to display summaries: `'inline'` = message pane banner, `'webchat'` = AI chat window. Note: `summarize_auto = 2` and `summarize_auto = 3` always use inline regardless of this setting. | | `summarize_max_display_length` | `0` | Maximum characters shown in inline summary before truncation. `0` = no limit (show full text). When set, text is truncated at a word boundary and a "See more"/"See less" toggle link is shown. | ### Summarize Settings Page (`pages/summarize/`) diff --git a/mzta-background.js b/mzta-background.js index 29ec2828..27d99f62 100644 --- a/mzta-background.js +++ b/mzta-background.js @@ -505,7 +505,9 @@ function cleanSummaryText(text) { return cleaned; } -async function _generateSummaryForMessage(headerMessageId, tabId) { +// tabId is optional — if null, runs silently (background pre-cache, no UI update) +// options.messageData: { message, fullMessage } — pass pre-fetched data to avoid re-querying +async function _generateSummaryForMessage(headerMessageId, tabId = null, options = {}) { try { let prefs = await browser.storage.sync.get({ connection_type: prefs_default.connection_type, @@ -517,40 +519,46 @@ async function _generateSummaryForMessage(headerMessageId, tabId) { let cachedSummary = await summaryStore.loadSummary(headerMessageId); if (cachedSummary && !cachedSummary.error) { - browser.tabs.sendMessage(tabId, { command: "showSummary", data: { ...cachedSummary, maxDisplayLength: prefs.summarize_max_display_length } }); + if (tabId) browser.tabs.sendMessage(tabId, { command: "showSummary", data: { ...cachedSummary, maxDisplayLength: prefs.summarize_max_display_length } }); return; } if (await summaryStore.isProcessing(headerMessageId)) { - browser.tabs.sendMessage(tabId, { command: "showSummaryGenerating" }); + if (tabId) browser.tabs.sendMessage(tabId, { command: "showSummaryGenerating" }); return; } await summaryStore.setProcessing(headerMessageId); taWorkingStatus.startWorking(); - browser.tabs.sendMessage(tabId, { command: "showSummaryGenerating" }); + if (tabId) browser.tabs.sendMessage(tabId, { command: "showSummaryGenerating" }); - const messageResult = await browser.messages.query({ headerMessageId: headerMessageId }); - if (!messageResult || messageResult.messages.length === 0) { - await summaryStore.saveError(headerMessageId, "Message not found"); - browser.tabs.sendMessage(tabId, { command: "showSummary", data: { error: true, message: "Message not found" } }); - taWorkingStatus.stopWorking(); - return; + let message, fullMessage; + if (options.messageData) { + message = options.messageData.message; + fullMessage = options.messageData.fullMessage; + } else { + const messageResult = await browser.messages.query({ headerMessageId: headerMessageId }); + if (!messageResult || messageResult.messages.length === 0) { + await summaryStore.saveError(headerMessageId, "Message not found"); + if (tabId) browser.tabs.sendMessage(tabId, { command: "showSummary", data: { error: true, message: "Message not found" } }); + taWorkingStatus.stopWorking(); + return; + } + message = messageResult.messages[0]; + fullMessage = await browser.messages.getFull(message.id); } - const fullMessage = await browser.messages.getFull(messageResult.messages[0].id); - const connectionType = getConnectionType(prefs, {}, 'summarize'); - + if (connectionType === 'chatgpt_web') { const errorMsg = browser.i18n.getMessage('summarize_chatgpt_web_not_supported'); await summaryStore.saveError(headerMessageId, errorMsg); - browser.tabs.sendMessage(tabId, { command: "showSummary", data: { error: true, message: errorMsg } }); + if (tabId) browser.tabs.sendMessage(tabId, { command: "showSummary", data: { error: true, message: errorMsg } }); taWorkingStatus.stopWorking(); return; } - const { promptText } = await taPromptUtils.buildSummaryPrompt([{ message: messageResult.messages[0], fullMessage }]); + const { promptText } = await taPromptUtils.buildSummaryPrompt([{ message, fullMessage }]); const cmd = new mzta_specialCommand({ prompt: promptText, @@ -572,13 +580,13 @@ async function _generateSummaryForMessage(headerMessageId, tabId) { headerMessageId: headerMessageId }; await summaryStore.saveSummary(summaryData, headerMessageId); - browser.tabs.sendMessage(tabId, { command: "showSummary", data: { ...summaryData, maxDisplayLength: prefs.summarize_max_display_length } }); + if (tabId) browser.tabs.sendMessage(tabId, { command: "showSummary", data: { ...summaryData, maxDisplayLength: prefs.summarize_max_display_length } }); taWorkingStatus.stopWorking(); } catch (error) { console.error("[ThunderAI] Error generating summary:", error); await summaryStore.saveError(headerMessageId, error.message || String(error)); - browser.tabs.sendMessage(tabId, { command: "showSummary", data: { error: true, message: error.message || "Failed to generate summary" } }); + if (tabId) browser.tabs.sendMessage(tabId, { command: "showSummary", data: { error: true, message: error.message || "Failed to generate summary" } }); taWorkingStatus.stopWorking(); } } @@ -1162,13 +1170,14 @@ async function reload_pref_init(){ add_tags_auto_only_inbox: prefs_default.add_tags_auto_only_inbox, spamfilter: prefs_default.spamfilter, summarize: prefs_default.summarize, + summarize_auto: prefs_default.summarize_auto, spamfilter_threshold: prefs_default.spamfilter_threshold, spamfilter_show_msg_panel: prefs_default.spamfilter_show_msg_panel, dynamic_menu_force_enter: prefs_default.dynamic_menu_force_enter, chatgpt_win_save_position: prefs_default.chatgpt_win_save_position, ...getDynamicSettingsDefaults(['use_specific_integration', 'connection_type']) }); - _process_incoming = prefs_init.add_tags_auto || prefs_init.spamfilter; + _process_incoming = prefs_init.add_tags_auto || prefs_init.spamfilter || (prefs_init.summarize && prefs_init.summarize_auto === 3); _sparks_presence = await checkSparksPresence(); } @@ -1395,7 +1404,8 @@ const newEmailListener = (folder, messagesList) => { await processEmails({ messages: messages, addTagsAuto: add_tags_auto_enabled, - spamFilter: prefs_init.spamfilter + spamFilter: prefs_init.spamfilter, + summarizeOnReceive: prefs_init.summarize && prefs_init.summarize_auto === 3 }); if(prefs_init.spamfilter){ @@ -1428,15 +1438,16 @@ async function processEmails(args) { messages, addTagsAuto = false, spamFilter = false, - summarize = false + summarize = false, + summarizeOnReceive = false } = args; taWorkingStatus.startWorking(); - // We keep two different loops, one for addTagsAuto and spamFilter and one for summarize - // because summarize is never called when an email is received, but only when using the context menu item + // One loop handles addTagsAuto, spamFilter, and summarizeOnReceive (on email receive). + // The separate summarize block below handles the context menu flow. - if (addTagsAuto || spamFilter) { + if (addTagsAuto || spamFilter || summarizeOnReceive) { let prefs_aats = await browser.storage.sync.get({ add_tags_maxnum: prefs_default.add_tags_maxnum, connection_type: prefs_default.connection_type, @@ -1531,6 +1542,16 @@ async function processEmails(args) { }); if (!result.success) continue; } + + if (summarizeOnReceive) { + if (!curr_fullMessage) { + curr_fullMessage = await browser.messages.getFull(message.id); + } + taLog.log("[ThunderAI] Pre-caching summary on receive for: " + message.headerMessageId); + await _generateSummaryForMessage(message.headerMessageId, null, { + messageData: { message, fullMessage: curr_fullMessage } + }); + } } } diff --git a/options/mzta-options-default.js b/options/mzta-options-default.js index c278455c..76510994 100644 --- a/options/mzta-options-default.js +++ b/options/mzta-options-default.js @@ -138,7 +138,7 @@ export const prefs_default = { spamfilter_threshold: 70, spamfilter_enabled_accounts: [], summarize: false, - summarize_auto: 1, // 0: disabled, 1: manual button, 2: automatic, 3: batch processing + summarize_auto: 1, // 0: disabled, 1: manual button, 2: automatic on message open, 3: generate on email receive summarize_display_mode: 'inline', // 'inline' or 'webchat' summarize_max_display_length: 0, // 0 = no limit, otherwise max chars shown inline spamfilter_show_msg_panel: true, diff --git a/pages/summarize/mzta-summarize.js b/pages/summarize/mzta-summarize.js index edb8ffec..dd945231 100644 --- a/pages/summarize/mzta-summarize.js +++ b/pages/summarize/mzta-summarize.js @@ -76,6 +76,7 @@ document.addEventListener("DOMContentLoaded", async () => { document.querySelectorAll(".option-input").forEach(element => { element.addEventListener("change", saveOptions); }); + document.getElementById('summarize_auto').addEventListener('change', updateDisplayModeConstraint); let prefs_summarize = await browser.storage.sync.get({ summarize_enabled_accounts: [], connection_type: 'chatgpt_web' }); let summarize_textarea = document.getElementById("summarize_prompt_text"); @@ -180,6 +181,19 @@ document.addEventListener("DOMContentLoaded", async () => { // Methods to manage options, derived from: /options/mzta-options.js +function updateDisplayModeConstraint() { + const summarize_auto_el = document.getElementById('summarize_auto'); + const display_mode_el = document.getElementById('summarize_display_mode'); + const autoVal = String(summarize_auto_el.value); + if (autoVal === '2' || autoVal === '3') { + display_mode_el.value = 'inline'; + display_mode_el.disabled = true; + browser.storage.sync.set({ summarize_display_mode: 'inline' }); + } else { + display_mode_el.disabled = false; + } +} + function saveOptions(e) { e.preventDefault(); let options = {}; @@ -294,4 +308,5 @@ async function restoreOptions() { } setCurrentChoice(getting); + updateDisplayModeConstraint(); } From 374d598d70bb4b12c028e72ca6bae68af8aeec52 Mon Sep 17 00:00:00 2001 From: mic Date: Sat, 28 Mar 2026 12:46:04 +0100 Subject: [PATCH 4/7] cache renamed to storage --- _locales/en/messages.json | 26 +++++++++++++------------- options/mzta-options.html | 6 +++--- options/mzta-options.js | 2 +- 3 files changed, 17 insertions(+), 17 deletions(-) diff --git a/_locales/en/messages.json b/_locales/en/messages.json index 2c8d22d3..f0954250 100644 --- a/_locales/en/messages.json +++ b/_locales/en/messages.json @@ -331,25 +331,25 @@ "message": "Manage your data placeholders", "description": "" }, - "prefs_cache_title": { - "message": "Cache Storage", - "description": "Title for cache management section in options" + "prefs_storage_title": { + "message": "Additional Info Storage", + "description": "Title for additional info storage management section in options" }, - "prefs_cache_storage_size": { - "message": "Cache size", - "description": "Label for cache storage size display" + "prefs_storage_size": { + "message": "Storage size", + "description": "Label for storage size display" }, - "prefs_cache_clear_button": { - "message": "Clear Cache", - "description": "Button to clear all cached message data" + "prefs_storage_clear_button": { + "message": "Clear Storage", + "description": "Button to clear all stored message data" }, "prefs_cache_clear_confirm": { - "message": "Are you sure you want to clear all cached data (summaries, spam reports, translations)? This action cannot be undone.", - "description": "Confirmation dialog for clearing cache" + "message": "Are you sure you want to clear all stored data (summaries, spam reports, translations)? This action cannot be undone.", + "description": "Confirmation dialog for clearing storage" }, - "prefs_cache_clear_done": { + "prefs_storage_clear_done": { "message": "$COUNT$ records removed.", - "description": "Message shown after cache is cleared", + "description": "Message shown after storage is cleared", "placeholders": { "count": { "content": "$1" diff --git a/options/mzta-options.html b/options/mzta-options.html index 0033a590..3e23111e 100644 --- a/options/mzta-options.html +++ b/options/mzta-options.html @@ -242,10 +242,10 @@ - __MSG_prefs_cache_title__ + __MSG_prefs_storage_title__ - __MSG_prefs_cache_storage_size__: -   + __MSG_prefs_storage_size__: +   diff --git a/options/mzta-options.js b/options/mzta-options.js index 51baa538..9adb6099 100644 --- a/options/mzta-options.js +++ b/options/mzta-options.js @@ -383,7 +383,7 @@ document.addEventListener('DOMContentLoaded', async () => { return; } let count = await taStorage.clearAllRecords(); - alert(browser.i18n.getMessage("prefs_cache_clear_done", [String(count)])); + alert(browser.i18n.getMessage("prefs_storage_clear_done", [String(count)])); updateCacheSize(); }); From 1650322f4d860b1fc7b2c51d4613bf0f804f56f8 Mon Sep 17 00:00:00 2001 From: mic Date: Sat, 28 Mar 2026 12:46:42 +0100 Subject: [PATCH 5/7] cache renamed to storage --- _locales/en/messages.json | 2 +- options/mzta-options.js | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/_locales/en/messages.json b/_locales/en/messages.json index f0954250..88e4357a 100644 --- a/_locales/en/messages.json +++ b/_locales/en/messages.json @@ -343,7 +343,7 @@ "message": "Clear Storage", "description": "Button to clear all stored message data" }, - "prefs_cache_clear_confirm": { + "prefs_storage_clear_confirm": { "message": "Are you sure you want to clear all stored data (summaries, spam reports, translations)? This action cannot be undone.", "description": "Confirmation dialog for clearing storage" }, diff --git a/options/mzta-options.js b/options/mzta-options.js index 9adb6099..eac61c34 100644 --- a/options/mzta-options.js +++ b/options/mzta-options.js @@ -379,7 +379,7 @@ document.addEventListener('DOMContentLoaded', async () => { updateCacheSize(); document.getElementById('btnClearCache').addEventListener('click', async () => { - if (!confirm(browser.i18n.getMessage("prefs_cache_clear_confirm"))) { + if (!confirm(browser.i18n.getMessage("prefs_storage_clear_confirm"))) { return; } let count = await taStorage.clearAllRecords(); From a1632f628edc78bb13e0528995ddcf511af60a75 Mon Sep 17 00:00:00 2001 From: mic Date: Sat, 28 Mar 2026 12:50:06 +0100 Subject: [PATCH 6/7] sv locale updated --- _locales/sv/messages.json | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/_locales/sv/messages.json b/_locales/sv/messages.json index ec2b7af2..8cd8802e 100644 --- a/_locales/sv/messages.json +++ b/_locales/sv/messages.json @@ -1461,19 +1461,19 @@ "webchat_save_as_summary": { "message": "Spara som sammanfattning" }, - "prefs_cache_title": { + "prefs_storage_title": { "message": "Cachelagring" }, - "prefs_cache_storage_size": { + "prefs_storage_size": { "message": "Cachestorlek" }, - "prefs_cache_clear_button": { + "prefs_storage_clear_button": { "message": "Rensa cache" }, - "prefs_cache_clear_confirm": { + "prefs_storage_clear_confirm": { "message": "Är du säker på att du vill rensa all cachad data (sammanfattningar, skräppostrapporter, översättningar)? Den här åtgärden kan inte ångras." }, - "prefs_cache_clear_done": { + "prefs_storage_clear_done": { "message": "$COUNT$ register borttagna.", "placeholders": { "count": { From 5eab777885064a0ca1c83daf784eb05dca261f76 Mon Sep 17 00:00:00 2001 From: Andreas Pettersson Date: Sun, 29 Mar 2026 18:44:19 +0200 Subject: [PATCH 7/7] Translated using Weblate (Swedish) Currently translated at 100.0% (520 of 520 strings) Translation: ThunderAI for Thunderbird/main Translate-URL: https://hosted.weblate.org/projects/thunderai/main/sv/ --- _locales/sv/messages.json | 13 ++++++++----- 1 file changed, 8 insertions(+), 5 deletions(-) diff --git a/_locales/sv/messages.json b/_locales/sv/messages.json index 8cd8802e..5a7071cd 100644 --- a/_locales/sv/messages.json +++ b/_locales/sv/messages.json @@ -1462,16 +1462,16 @@ "message": "Spara som sammanfattning" }, "prefs_storage_title": { - "message": "Cachelagring" + "message": "Ytterligare informationslagring" }, "prefs_storage_size": { - "message": "Cachestorlek" + "message": "Lagringsstorlek" }, "prefs_storage_clear_button": { - "message": "Rensa cache" + "message": "Rensa lagring" }, "prefs_storage_clear_confirm": { - "message": "Är du säker på att du vill rensa all cachad data (sammanfattningar, skräppostrapporter, översättningar)? Den här åtgärden kan inte ångras." + "message": "Är du säker på att du vill rensa all lagrad data (sammanfattningar, skräppostrapporter, översättningar)? Den här åtgärden kan inte ångras." }, "prefs_storage_clear_done": { "message": "$COUNT$ register borttagna.", @@ -1506,7 +1506,7 @@ "message": "Visa sammanfattningsknapp" }, "prefs_OptionText_summarize_auto_automatic": { - "message": "Generera automatiskt" + "message": "När e-postmeddelandet öppnas" }, "prefs_OptionText_summarize_auto_Info": { "message": "Välj om sammanfattningar ska genereras automatiskt när meddelanden visas. Kräver en API-baserad anslutning (inte ChatGPT Web)." @@ -1570,5 +1570,8 @@ }, "summary_by": { "message": "Sammanfattning av" + }, + "prefs_OptionText_action_auto_batch": { + "message": "När e-postmeddelandet tas emot" } }