diff --git a/CHANGELOG.md b/CHANGELOG.md index 858f67b..a022ae6 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -13,6 +13,7 @@ Follows [Keep a Changelog](https://keepachangelog.com/en/1.0.0/) · versioned wi - **Voice list rows no longer show the "Source unknown" badge** (it crowded the play buttons). The badge stays in the voice inspector, next to the Source & consent panel. ### Fixed +- **Duplicate German i18n keys and dead frontend code.** Removed 14 shadowed duplicate keys in `i18n.js` (effective translations unchanged), the unreachable body of `audiobookShowPreview`, and two identical-branch ternaries. - **Security hardening (Sonar findings).** The Docker installer downloads `get-docker.sh` into a private `mkdtemp` dir (not a predictable `/tmp` path) and removes it afterwards; the OMDb poster lookup uses HTTPS; the fish.audio cache key marks MD5 as `usedforsecurity=False`. - **Background jobs could be garbage-collected mid-run.** Fire-and-forget `asyncio.create_task` calls (magazine, conversation, tts, stt, library, sources) now go through `core.tasks.spawn`, which keeps a strong reference until the task ends and logs failures by exception class only. - **Voice archetype gallery broke `npm run check:frontend`**: its `say` helper collided with `magazine.js`; renamed to `archSay`. diff --git a/static/js/audiobook-preview-export.js b/static/js/audiobook-preview-export.js index 3110343..36f4535 100644 --- a/static/js/audiobook-preview-export.js +++ b/static/js/audiobook-preview-export.js @@ -56,36 +56,6 @@ async function audiobookOpenCurrentInRehearser() { function audiobookShowPreview() { audiobookOpenCurrentInRehearser(); - return; - const segs = _audiobook.segments || []; - const roster = _audiobook.roster || []; - document.getElementById('audiobook-preview')?.remove(); - const ov = document.createElement('div'); - ov.id = 'audiobook-preview'; - ov.className = 'audiobook-overlay'; - // datalist = Narrator + LLM roster + any speakers present in the segments (incl. Unknown) - const speakerSet = [...new Set(['Narrator', ...roster, ...segs.filter(s => s.type === 'dialogue' && s.speaker).map(s => s.speaker)])]; - const charCount = speakerSet.filter(n => !/^Unknown|Unbekannt/i.test(n)).length; - const opts = speakerSet.map(n => `