Sync engines and embedded databases re-implement SQL operators in JavaScript. Subtle gaps between those JS implementations and the SQL semantics they're meant to mirror make queries silently drop or over-match rows. No exception. No log. Just wrong data — the worst kind of bug.
| Database | Class | Status |
|---|---|---|
| PowerSync sync-rules | 5 separate evaluator bugs (NOT/NULL, LIKE, CAST, div-zero, json_each) + JOIN diagnostic + 3 closed (operator-direction call) | 5 merged + 1 open + 3 closed |
| Rocicorp's Zero | Range & comparison evaluation | 2 merged |
| InstantDB | $like / $ilike newline handling | 1 merged |
| ElectricSQL | LIKE newline + escaped wildcards | 1 open |
| Dexie | Case-fold silent row drops | 1 open |
| RxDB, Convex, TanStack DB, Autumn, Refly | Adjacent fixes & integrations | shipped / replied |
From self-serve playbook to a full sprint. Every tier is bounded scope, fixed price, no-find-no-charge above the playbook level.
Terms above the playbook tier: I find the bug or I don't charge. Once a divergence is confirmed, I ship the fix within 48 hours. Receipt and Polar-issued invoice automatic. No subscription, no upsell.
upper() / lower() — JS uses locale-aware Unicode fold (length-changing on ß, fi, Turkish dotted-i); SQLite default is ASCII-only. Bucket keys diverge silently between server and client.length() — JS counts UTF-16 code units; SQLite counts Unicode code points. 2x divergence on emoji, CJK Extension B-G, ancient scripts.substring() / substr() — slices by UTF-16 code units and can split surrogate pairs, returning unpaired-surrogate strings.LIKE across newlines — RegExp-based LIKE often forgets the s flag; % stops spanning \n; rows leak through.CAST on signed strings — CAST('-12abc' AS integer) returns NaN where SQLite returns -12.The base checker is open-source and runnable today against your DB:
silentdrop on npm — zero-dep TypeScript, MITsilentdrop-llm — the agent-output / LLM-response equivalent