diff --git a/CHANGELOG.md b/CHANGELOG.md index 922fedc..8880294 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -7,10 +7,19 @@ The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.1.0/). ## [Unreleased] ### Fixed -- **Italian locale was ~51% Spanish.** `src/data/it.json` had been built from `es.json` and only partially re-translated — 632 of its long strings were byte-identical Spanish, and the `_protected` brand map mistranslated `Claude → Claudio`, `Anthropic → Antropico`, `Claude Code → Codice Claudio`, silently breaking runtime brand-term restoration for Italian (our #1 install market). Re-translated every contaminated string from the English source via the same Google Translate endpoint the extension uses, restored brand/technical terms to canonical English, and rebuilt `_protected` with the correct Italian wrong-forms. Italian↔Spanish overlap is now 0.1% (parity with the other 10 locales). +- **Italian locale was ~51% Spanish.** `src/data/it.json` had been built from `es.json` and only partially re-translated — 632 of its long strings were byte-identical Spanish, and the `_protected` brand map mistranslated `Claude → Claudio`, `Anthropic → Antropico`, `Claude Code → Codice Claudio`, silently breaking runtime brand-term restoration for Italian (our #1 install market). Re-translated every contaminated string from the English source via the same Google Translate endpoint the extension uses, restored brand/technical terms to canonical English, and rebuilt `_protected` with the correct Italian wrong-forms. Italian↔Spanish overlap is now 0.1% (parity with the other 10 locales). (#166, #167) +- **Protected-term restoration corrupted correct CJK prose.** Across ko/ja/zh-CN/zh-TW, common words were mapped as brand "wrong-forms" (클라우드→Claude, 인류→Anthropic, 企业→Enterprise, …), so `restoreProtectedTerms` rewrote correct translations into wrong English (e.g. "클라우드 컴퓨팅" → "Claude 컴퓨팅"). Removed the ambiguous common-word wrong-forms; intended brand restoration (클로드→Claude, etc.) still works. (#172) +- **AI tutor spinner could hang forever** when the Puter bridge wasn't ready — `chatStream` resolved to a discarded error string instead of throwing, so the caller never rendered the error+retry. It now rejects on bridge-not-ready. (#174) +- **Gemini verify could render a non-translation as the translation.** A short affirmation ("Okay", "OK입니다", "OK?") or whitespace reply fell through and was cached/shown in place of the correct translation (an empty reply blanked the element). Added a length guard so anything far shorter than the source keeps the Google translation. (#175, #176) ### Added -- **Locale cross-contamination guard** (`scripts/check-locale-contamination.js`, `npm run check:locales`, wired into CI). Fails when any locale shares >8% of its long strings with another — the bug class the key/shape checks (`check-i18n`, `check-dict-coverage`) cannot see because they only verify structure, not language. Clean locales sit at ≤2.1%; the contaminated Italian file was 51%. +- **Locale cross-contamination guard** (`scripts/check-locale-contamination.js`, `npm run check:locales`, wired into CI). Fails when any locale shares >8% of its long strings with another — the bug class the key/shape checks (`check-i18n`, `check-dict-coverage`) cannot see because they only verify structure, not language. Clean locales sit at ≤2.1%; the contaminated Italian file was 51%. (#166) +- **`skillbridge-academy-terms` companion Claude Code plugin** (`claude-plugin/`) re-exposing the curated Academy terminology dictionary for Claude Code / Cowork. Its data is generated from `src/data/*.json` and kept in sync by CI (`npm run check:plugin`). (#170) + +### Changed +- **build-plugin generator** now reads `FLASHCARD_COURSE_MAP` via the same evaluation the sibling checkers use (was a fragile regex parse of the source); `--check` also detects orphan output files. (#171) +- **jest** no longer warns about a Haste name collision from `dist/` builds (`modulePathIgnorePatterns`). (#179) +- **Privacy policy** permission table realigned with the manifest (removed the stale `tabs` entry, disclosed `api.github.com`); language count corrected to 32. (#180) ## [3.5.39] - 2026-06-01 diff --git a/PRIVACY_POLICY.md b/PRIVACY_POLICY.md index ab6712d..15f48e0 100644 --- a/PRIVACY_POLICY.md +++ b/PRIVACY_POLICY.md @@ -1,6 +1,6 @@ # Privacy Policy — SkillBridge -**Last updated:** April 11, 2026 +**Last updated:** June 9, 2026 ## Overview diff --git a/README.md b/README.md index a85f69d..3e29377 100644 --- a/README.md +++ b/README.md @@ -145,11 +145,12 @@ Generic translation tools often **mistranslate brand names and technical terms** ## Installation -> **Status: pending re-publication after icon redesign.** The Chrome Web -> Store listing was removed pending an icon redesign and is not currently -> available. Install via the manual / developer-mode path below — the -> code in `main` is the up-to-date release. The store listing will be -> restored once the new icon ships. +> **Status: live as v1.0.1; re-publication of the current v3.5.39 pending.** +> The Chrome Web Store listing is available in all locales **except the United +> States**, where it was removed on 2026-05-12 over a trademark issue with the +> old icon (since redesigned on `main`). The published store build is v1.0.1; +> `main` is the up-to-date release (v3.5.39). For the latest version — and for +> US users until re-listing — install via the manual / developer-mode path below. ### Chrome / Edge / Chromium browsers @@ -236,7 +237,7 @@ The full "things we will not do" list is kept public on purpose in [POSITIONING. | 🇹🇼 中文繁體 (Chinese Traditional) | `zh-TW` | 570+ entries | | 🇪🇸 Español (Spanish) | `es` | 570+ entries | | 🇫🇷 Français (French) | `fr` | 570+ entries | -| 🇮🇹 Italiano (Italian) | `it` | 570+ entries (v1 — Spanish-derived, native review welcome) | +| 🇮🇹 Italiano (Italian) | `it` | 570+ entries (re-translated from English; native review welcome) | | 🇩🇪 Deutsch (German) | `de` | 570+ entries | | 🇧🇷 Português (Brazilian) | `pt-BR` | 570+ entries | | 🇷🇺 Русский (Russian) | `ru` | 570+ entries | diff --git a/TESTING.md b/TESTING.md index de374fe..f355bd8 100644 --- a/TESTING.md +++ b/TESTING.md @@ -70,14 +70,21 @@ tests/protected-terms.test.js → re-implements logic (legacy pattern) | `format-response.test.js` | ~18 | Markdown-to-HTML conversion, XSS escaping, heading/list/inline formatting | | `glossary-checker.test.js` | ~10 | Cross-language glossary consistency, protected terms validation | -### What is NOT tested (known gaps) - -- DOM manipulation (`content.js` — 30+ functions) -- Background service worker (`background.js` — rate limiter, fetchWithRetry) -- Chrome API interactions (message passing, storage, tabs) -- YouTube subtitle logic (`youtube-subtitles.js`) -- Puter.js bridge (`page-bridge.js`) -- E2E flows (page load → translate → restore) +### Tested end-to-end (Playwright, in CI) + +A Playwright E2E suite loads the built extension into headed Chromium (xvfb in +CI — see the `e2e` job in `.github/workflows/ci.yml`) and exercises the +integrated flows: page load → translate → restore, SPA navigation, lazy +translation, IndexedDB cache, protected-term restoration, tutor streaming + +cancel, exam-mode safety, code-comment translation, and PDF-export +sanitization. Specs live in `tests/e2e/` (`npm run test:e2e`). + +### Thin coverage / known gaps + +- Unit-level coverage of `content.js` DOM helpers and `background.js` internals + beyond what the E2E suite exercises +- Real YouTube iframe caption activation (E2E can't drive the embedded player) +- Visual / dark-mode QA, mobile layout, long-session memory — manual only --- diff --git a/claude-plugin/skills/academy-terms/data/terms.it.json b/claude-plugin/skills/academy-terms/data/terms.it.json index a580cf8..91b5e95 100644 --- a/claude-plugin/skills/academy-terms/data/terms.it.json +++ b/claude-plugin/skills/academy-terms/data/terms.it.json @@ -3,7 +3,7 @@ "lang": "it", "langName": "Italiano", "sourceVersion": "3.5.39", - "sourceLastUpdated": "2026-05-25", + "sourceLastUpdated": "2026-06-03", "generatedFrom": "src/data/it.json", "termCount": 999 }, diff --git a/src/data/it.json b/src/data/it.json index 66012e3..5dd3575 100644 --- a/src/data/it.json +++ b/src/data/it.json @@ -3,8 +3,8 @@ "lang": "it", "langName": "Italiano", "version": "3.5.39", - "lastUpdated": "2026-05-25", - "translation_provenance": "v1 — derived from src/data/es.json via Spanish→Italian regex transformation (Romance proximity ~80%). Native Italian PRs welcome to replace any section wholesale; structural keys must remain identical to other premium dictionaries (enforced by scripts/check-dict-coverage.js)." + "lastUpdated": "2026-06-03", + "translation_provenance": "Re-translated from the English source via Google Translate (2026-06), with brand/technical terms restored to canonical English; Italian↔Spanish overlap is now 0.1% (parity with the other 10 locales). Earlier v1 was a Spanish-derived regex transform — fully replaced. Structural keys must remain identical to other premium dictionaries (enforced by scripts/check-dict-coverage.js); native Italian PRs welcome." }, "ui": { "Anthropic Academy": "Anthropic Academy", diff --git a/src/lib/constants.js b/src/lib/constants.js index 40e522e..312feb0 100644 --- a/src/lib/constants.js +++ b/src/lib/constants.js @@ -158,8 +158,8 @@ const SKILLBRIDGE_LIMITS = { // Italian promoted to Premium in v3.5.34 after the 2026-05-23 CWS dashboard // pull showed it as the #2 install language (~72 installs in May, second only // to English-US, ahead of French/Spanish/Korean) while shipping with no -// curated terminology. src/data/it.json v1 was derived from es.json via -// Spanish→Italian regex (Romance proximity ~80%); native Italian PRs welcome. +// curated terminology. src/data/it.json was since re-translated from the +// English source (Italian↔Spanish overlap now 0.1%); native Italian PRs welcome. const PREMIUM_LANGUAGES = [ { code: 'ko', label: '한국어' }, { code: 'ja', label: '日本語' }, diff --git a/store-assets/RELEASE_CHECKLIST.md b/store-assets/RELEASE_CHECKLIST.md index 8fad9f0..cb97952 100644 --- a/store-assets/RELEASE_CHECKLIST.md +++ b/store-assets/RELEASE_CHECKLIST.md @@ -148,7 +148,6 @@ If Tracer / Anthropic IP enforcement files another complaint against v3.5.39: ## SNS launch (separate session, after listing is live) -Drafts are queued in `store-assets/promotion/` (see `x-thread-italian.md` and -`plugin-directory-submission.md`). Do not post until the CWS listing reflects -v3.5.39 — posting before would point users at a listing missing all the work -the post talks about. +SNS launch drafts are kept outside this repo (internal). Do not post until the +CWS listing reflects v3.5.39 — posting before would point users at a listing +missing all the work the post talks about.