Releases: luongndcoder/Scribble
v1.2.15
v1.2.14
- 🌐 Phát hiện mất mạng tự động + banner cảnh báo trong khi upload
- 🔁 Soniox upload tách 2 bước (upload riêng → STT riêng) an toàn hơn
- ⚡ Auto-retry chunk fail với backoff thông minh (1s → 2s → 4s)
- 📜 Transcript dài 4h+ không còn lag (sliding window + auto-load)
- 👥 Speaker IDs sequential 1-2-3-4 (hết cảnh nhảy 3 → 101)
- 💾 Crash giữa upload không mất tiến trình — có nút "Thử lại"
- ⏱ Hiển thị stage rõ: "Đang tải file" vs "Soniox đang xử lý"
v1.2.11
- 🎬 Tự động cài ffmpeg — không cần
brew install/choco installnữa - 🪟 Sửa lỗi không kéo được cửa sổ app trên Mac
- 📝 Transcript luôn được lưu kể cả khi tạo biên bản AI lỗi (chưa cấu hình API Key) — không còn cảnh "công cốc"
- 🧹 Auto-xóa cuộc họp rỗng khi upload lỗi (hết bug "đã tồn tại" giả)
- 🔄 Soniox tự reconnect khi session timeout (~1h) + transcript dài 4h không còn lag
v1.2.10
Scribble v1.2.10 — Soniox Auto-Reconnect & Transcript Load-More
🐛 Bug Fixes
STT realtime ổn định cho meeting dài (Soniox)
- Trước: Soniox real-time WebSocket có session cap server-side (~1h tùy plan). Khi vượt, server đóng kết nối nhưng app không biết — transcript dừng đột ngột trong khi timer vẫn chạy, audio thread chết âm thầm.
- Giờ: app tự reconnect tới 8 lần với exponential backoff (cap 5s). Timeline
start_ms/end_msđược giữ liên tục qua các session bằng cumulative offset. Frontend hiện badge🔄 Soniox session reconnecting...trong ~1s khi đang nối lại. Lỗi rõ ràng nếu hết quota / sai API key (không còn nuốt âm thầm).
Transcript dài 4h không còn lag
- Trước: render full
transcriptParts(500+ đoạn × split-sentence × translation) làm DOM lag kinh khủng khi cuộc họp dài. - Giờ: pagination — chỉ render 200 đoạn cuối, nút "↑ Tải thêm 200 đoạn cũ hơn" ở đầu, scroll position được preserve. Export / Copy / Tạo biên bản vẫn lấy TOÀN BỘ transcript (pagination chỉ ảnh hưởng render).
Auto-scroll không yank user nữa
- Trước: cứ có transcript mới là kéo scroll xuống bottom → khó đọc đoạn cũ khi đang ghi âm.
- Giờ: chỉ auto-scroll khi user đang trong 80px cuối list. Cuộn lên đọc thoải mái.
📦 Downloads
- macOS (Apple Silicon):
.dmghoặc auto-update - Windows (x64):
.exeinstaller - Linux (amd64):
.AppImagehoặc.deb
v1.2.9
🎙️ Soniox realtime — speaker attribution + timestamps (the actual fix)
User report: dùng Soniox STT realtime, text đúng nhưng speaker labels bị lẫn lộn và timestamps stuck ở 0:00 – 0:00 đặc biệt trong session dài.
Root cause
-
Speaker jumbling.
SonioxRealtimeStreamer.results()chỉ updatecurrent_speakerở cuối loop event. Khi 1 event Soniox trả[S1, S2, S1]tokens trong cùng batch, guard "speaker change" checkaccumulated_final = [](chưa merge) nên không flush — tất cả tokens collapsed vào speaker cuối cùng. -
Timestamps = 0:00. Backend không forward
start_ms/end_mscủa Soniox tokens cho realtime. Frontend fall backstate.secondstừ recording timer, race với WS open → events đầu arrive lúcseconds=0→ cảstartTimelẫnendTimepin về"0".
Fix
- Rewrite token loop trong
src-python/stt.py: flush speaker change INLINE,current_speakeradvance per-token. Tracksegment_start_ms/segment_end_mstừ token offsets thực, gửi trong mọi event. - Frontend (
use-streaming-stt.ts) prefer ms offsets từ backend khi có, fallbackstate.secondscho Nvidia/STT khác.
Verify
Long session với 3+ speakers: speaker labels stable, timestamps grow đều (vd: 2:34 – 3:12). Log sẽ thấy [stt:soniox-stream] Speaker change mid-event: S1 -> S2, flushing: '...' khi đổi giọng giữa event.
v1.2.8
🖱️ Drag window from the topnav (the actual fix)
Previous attempts wired data-tauri-drag-region everywhere, but the attribute is silently ignored on Tauri 2 + macOS Overlay-titlebar — confirmed via user testing. Switched to Tauri's recommended manual approach: an onMouseDown handler that imperatively calls getCurrentWindow().startDragging().
What changed
- Click-drag anywhere in the topnav (other than buttons / language toggle / settings cog) moves the window
- Double-click the topnav background triggers
toggleMaximize()— mirrors native title-bar behavior - Interactive elements (buttons, links, inputs) still get their onClick — drag handler bails out when the target is one of those
macOS — first "silent update" test
This is the first release after v1.2.7's stable-cert work, so it's the proof point for the TCC permissions fix. Updating from v1.2.7 → v1.2.8 should NOT trigger a macOS permission dialog (mic, system audio). Both releases are signed with the same Scribble Code Signing identity, so TCC sees them as the same app.
If you DO still get prompted, something in the cert chain changed between builds — open an issue.
v1.2.7
🔐 macOS — permissions now persist across updates
Stop being asked for mic + system-audio permissions every time you update. The fix is on the build side: every macOS release is now signed with a stable code-signing identity, so macOS TCC recognises each update as "the same app" and keeps prior grants alive.
What changed
.github/workflows/build-macos.ymlimports a code-signing cert from secrets and uses it assigningIdentityinstead of ad-hoc (-). Falls back to ad-hoc when the secret is absent, so non-mac builds aren't affected.- Identity extraction tolerates self-signed certs (the strict
codesigningpolicy filter rejects them, but codesign itself accepts them by name).
Heads-up — one last permission prompt
Upgrading from v1.2.6 → v1.2.7 will still trigger the macOS permission dialog one more time (mic, system audio), because v1.2.6 was ad-hoc-signed and v1.2.7 has a real identity — different designated requirement = different "app" to TCC.
From v1.2.7 onward, every future update will keep your permissions. No more annoying prompts.
Verification
codesign -dvv /Applications/Scribble.app 2>&1 | grep Authority
# Expected: Authority=Scribble Code Signing (NOT: Authority=(ad-hoc))v1.2.6
🔐 Soniox realtime — round two (the actual fix)
v1.2.4 fixed the websockets.sync bundle gap. The Soniox realtime WebSocket then progressed further but immediately died on TLS handshake:
ssl.SSLCertVerificationError: [SSL: CERTIFICATE_VERIFY_FAILED]
certificate verify failed: unable to get local issuer certificate
Root cause
Python's stdlib ssl module uses compile-time hardcoded CA paths (/System/Library/OpenSSL/cert.pem etc) that don't exist in a PyInstaller bundle. The file-upload path was never affected because httpx ships certifi's CA bundle internally — but websockets.sync falls back to the raw stdlib and broke.
Fix
main.py: at the very top of boot (before uvicorn, websockets, or anything caches an SSL context), setSSL_CERT_FILE/SSL_CERT_DIR/REQUESTS_CA_BUNDLEtocertifi.where(). Guard withsys.frozenso dev runs still use the system trust store.scribble-sidecar.spec:collect_all('certifi')socacert.pemis actually present in the bundle. Previously certifi was only there incidentally via httpx; now it's explicitly required and load-bearing.
After this update
Settings → STT Provider = Soniox → "Cuộc họp mới" → start recording → transcript appears in real time, with built-in speaker diarization.
📦 Downloads
Scribble_1.2.6_aarch64.dmg— macOS Apple SiliconScribble_1.2.6_x64-setup.exe— Windows x64Scribble_1.2.6_amd64.AppImage— Linux x64 (AppImage)scribble_1.2.6_amd64.deb— Linux x64 (Debian/Ubuntu)
v1.2.5
🪟 Sticky meeting-list header
Tiny UX fix on top of v1.2.4.
What changed
- Meeting history title + search bar now stay pinned at the top while you scroll the meeting cards
- Previously the whole
.viewwas the scroll container — scrolling past the first screen lost the title, the "Upload file" / "Cuộc họp mới" buttons, AND the search field together - The
.meetings-gridis now the only scrolling region inside the list view; detail view is unaffected (uses its own layout)
📦 Downloads
Scribble_1.2.5_aarch64.dmg— macOS Apple SiliconScribble_1.2.5_x64-setup.exe— Windows x64Scribble_1.2.5_amd64.AppImage— Linux x64 (AppImage)scribble_1.2.5_amd64.deb— Linux x64 (Debian/Ubuntu)
🔗 Quick recap of v1.2.x changes
| Version | Highlight |
|---|---|
| 1.2.5 | Sticky meeting-list header + search (this release) |
| 1.2.4 | Soniox realtime fix + draggable window + clickable links |
| 1.2.3 | Clickable markdown links in update modal |
| 1.2.2 | Real markdown renderer + bottom-right banner + drop "Ready" toast |
| 1.2.1 | Auto-update infra (signing + manifest + Settings controls) |
| 1.2.0 | Audio upload + reference materials + UX redesign |
v1.2.4
🐛 Fixes
This is a triple-bugfix release covering window controls, clickable docs links, and the broken Soniox realtime transcription that several users reported after v1.2.3.
🎤 Soniox realtime transcription works again
- Root cause: the PyInstaller bundle was missing
websockets.sync(onlyspeedups.sogot packed). The Soniox SDK importsfrom websockets.sync.client import connectfor realtime sessions — every WebSocket attempt threwModuleNotFoundErrorand was silently swallowed by an emptyexcept. Frontend looped reconnect 2x/sec. - Fix: spec uses
collect_all('websockets')now, pulling every submodule. The Soniox file-upload path was never affected because it uses HTTP (httpx), not WebSockets. - Also added:
log.error(..., exc_info=True)on the soniox-stream exception path. Future failures will show a real traceback instead of going silent.
🪟 Window draggable from the topnav
- macOS overlay title-bar mode hid the native chrome — clicking on "Scribble v1.2.x" just selected the version text. Same on Windows/Linux.
- Fix: topnav, brand, status chip, and language label all get
data-tauri-drag-region+-webkit-app-region: drag+user-select: none. Click-and-drag the topnav to move the window. Buttons opt out of drag withno-dragso their onClick still fires.
🔗 Clickable markdown links actually open
- v1.2.3 added
[text](url)rendering in the update modal but routed through@tauri-apps/plugin-shellwithout granting the permission. Click did nothing visible. - Fix:
shell:allow-openadded to capabilities. Click any release-notes link → opens in your system browser.
📦 Downloads
Scribble_1.2.4_aarch64.dmg— macOS Apple SiliconScribble_1.2.4_x64-setup.exe— Windows x64Scribble_1.2.4_amd64.AppImage— Linux x64 (AppImage)scribble_1.2.4_amd64.deb— Linux x64 (Debian/Ubuntu)