docs: changelog for msg_secret semaphore fix (whatsapp-rust#832) - #306
docs: changelog for msg_secret semaphore fix (whatsapp-rust#832)#306jlucaso1 wants to merge 1 commit into
Conversation
📝 WalkthroughWalkthroughThis PR documents a bug fix for SQLite in-memory read/write race conditions. The changelog entry describes how ChangesSQLite Semaphore Bug Fix Documentation
Estimated code review effort🎯 1 (Trivial) | ⏱️ ~3 minutes Poem
🚥 Pre-merge checks | ✅ 5✅ Passed checks (5 passed)
✏️ Tip: You can configure your own custom pre-merge checks in the settings. ✨ Finishing Touches🧪 Generate unit tests (beta)
Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out. Comment |
There was a problem hiding this comment.
Actionable comments posted: 1
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
Inline comments:
In `@changelog/2026-06-10-msg-secret-semaphore.mdx`:
- Around line 10-16: Rewrite the changelog entry into active voice and address
the reader directly using second person; clearly state what you changed and why,
e.g., "You previously dispatched get_msg_secret and get_msg_secret_with_ts via
raw spawn_blocking, which bypassed the db_semaphore; this could cause
SQLITE_LOCKED on :memory: stores and silent misses because busy_timeout didn’t
apply. You now call those methods via with_semaphore so reads wait for the
single-permit write and avoid phantom misses. Note the relation to the
write-behind drain (`#831`) and symptom (undecrypted reactions/comments introduced
in `#829`), and list affected stores (in-memory :memory: only; file-backed WAL not
affected)."
🪄 Autofix (Beta)
Fix all unresolved CodeRabbit comments on this PR:
- Push a commit to this branch (recommended)
- Create a new PR with the fixes
ℹ️ Review info
⚙️ Run configuration
Configuration used: defaults
Review profile: CHILL
Plan: Pro Plus
Run ID: 0312eae6-b1bc-4a96-9653-7eda5e1e6693
📒 Files selected for processing (2)
changelog/2026-06-10-msg-secret-semaphore.mdxdocs.json
| `get_msg_secret` and `get_msg_secret_with_ts` were dispatched via raw `spawn_blocking`, bypassing the single-permit `db_semaphore` that all write paths (and most other reads) already acquire via `with_semaphore`. On in-memory (`:memory:`) stores a read that overlaps an active write transaction hits the shared-cache table lock and fails with `SQLITE_LOCKED` — an error not covered by `busy_timeout`. Both call sites treat a backend error as a lookup miss, so the failure was silent. | ||
|
|
||
| In practice, the write-behind drain introduced in [#831](https://github.com/oxidezap/whatsapp-rust/pull/831) made this race consistently reachable: the detached batch write could race the very next incoming message's secret lookup. The symptom was encrypted reactions and channel comments (added in [#829](https://github.com/oxidezap/whatsapp-rust/pull/829)) arriving undecrypted, with no error logged. | ||
|
|
||
| Both methods now go through `with_semaphore`. A read that arrives during a write waits for the permit instead of failing as a phantom miss. | ||
|
|
||
| **Affected stores:** in-memory (`:memory:`) SQLite — used by the test suite and any embedded consumer. File-backed stores with WAL mode are not affected (WAL readers do not block on concurrent writers). |
There was a problem hiding this comment.
🛠️ Refactor suggestion | 🟠 Major | ⚡ Quick win
Rewrite to use active voice and second person per documentation guidelines.
The description uses passive voice and third person, violating the documentation style guidelines. Changelog entries are user-facing documentation and should address the reader directly.
As per coding guidelines, documentation should use active voice and second person ("you"). The guideline text states: "Use active voice and second person ('you') in documentation."
♻️ Suggested rewrite in active voice and second person
-`get_msg_secret` and `get_msg_secret_with_ts` were dispatched via raw `spawn_blocking`, bypassing the single-permit `db_semaphore` that all write paths (and most other reads) already acquire via `with_semaphore`. On in-memory (`:memory:`) stores a read that overlaps an active write transaction hits the shared-cache table lock and fails with `SQLITE_LOCKED` — an error not covered by `busy_timeout`. Both call sites treat a backend error as a lookup miss, so the failure was silent.
+Previously, if you used `get_msg_secret` or `get_msg_secret_with_ts`, the calls dispatched via raw `spawn_blocking` and bypassed the single-permit `db_semaphore`. Write paths and most other reads already acquire this semaphore via `with_semaphore`. When you run an in-memory (`:memory:`) store and a read overlaps an active write transaction, the read hits the shared-cache table lock. It then fails with `SQLITE_LOCKED` — an error `busy_timeout` does not cover. The call sites treated backend errors as lookup misses, so you saw silent failures.
-In practice, the write-behind drain introduced in [`#831`](https://github.com/oxidezap/whatsapp-rust/pull/831) made this race consistently reachable: the detached batch write could race the very next incoming message's secret lookup. The symptom was encrypted reactions and channel comments (added in [`#829`](https://github.com/oxidezap/whatsapp-rust/pull/829)) arriving undecrypted, with no error logged.
+The write-behind drain from [`#831`](https://github.com/oxidezap/whatsapp-rust/pull/831) made this race consistently reachable. The detached batch write could race your next incoming message's secret lookup. You would see encrypted reactions and channel comments (from [`#829`](https://github.com/oxidezap/whatsapp-rust/pull/829)) arrive undecrypted. No error appeared in your logs.
-Both methods now go through `with_semaphore`. A read that arrives during a write waits for the permit instead of failing as a phantom miss.
+Both methods now route through `with_semaphore`. When your read arrives during a write, it waits for the permit instead of failing as a phantom miss.
-**Affected stores:** in-memory (`:memory:`) SQLite — used by the test suite and any embedded consumer. File-backed stores with WAL mode are not affected (WAL readers do not block on concurrent writers).
+**Affected stores:** This fix applies when you use in-memory (`:memory:`) SQLite — common in test suites and embedded consumers. If you use file-backed stores with WAL mode, you are not affected (WAL readers do not block on concurrent writers).🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
In `@changelog/2026-06-10-msg-secret-semaphore.mdx` around lines 10 - 16, Rewrite
the changelog entry into active voice and address the reader directly using
second person; clearly state what you changed and why, e.g., "You previously
dispatched get_msg_secret and get_msg_secret_with_ts via raw spawn_blocking,
which bypassed the db_semaphore; this could cause SQLITE_LOCKED on :memory:
stores and silent misses because busy_timeout didn’t apply. You now call those
methods via with_semaphore so reads wait for the single-permit write and avoid
phantom misses. Note the relation to the write-behind drain (`#831`) and symptom
(undecrypted reactions/comments introduced in `#829`), and list affected stores
(in-memory :memory: only; file-backed WAL not affected)."
Source: Coding guidelines
|
Preview deployment for your docs. Learn more about Mintlify Previews.
💡 Tip: Enable Workflows to automatically generate PRs for you. |
Summary
Adds a changelog entry for oxidezap/whatsapp-rust#832 — the bug fix that routes
get_msg_secretandget_msg_secret_with_tsthroughwith_semaphoreinstead of rawspawn_blocking.changelog/2026-06-10-msg-secret-semaphore.mdxdocumenting the bug, root cause, and fixdocs.jsonupdated to list the new entry at the top of the June 10 changelog groupWhat changed in the library
get_msg_secret/get_msg_secret_with_tsonSqliteStorepreviously usedtokio::task::spawn_blockingdirectly, bypassing the single-permitdb_semaphore. On in-memory (:memory:) stores a read racing a write transaction would getSQLITE_LOCKED, which both call sites silently treated as a lookup miss. The write-behind drain from #831 made this race consistently reachable, causing encrypted reactions and comments to arrive undecrypted. The fix routes both reads throughwith_semaphoreso they wait rather than fail.Breaking changes
None.
Generated by Claude Code
Summary by CodeRabbit
Bug Fixes
Documentation