Skip to content

Fix canEncodeMatcher accepting queries with unsafe expressions and nested Q.on - #1977

Open
jsamelak wants to merge 4 commits into
masterfrom
jarek/can-encode-matcher-unsafe-exprs
Open

jsamelak wants to merge 4 commits into
masterfrom
jarek/can-encode-matcher-unsafe-exprs

Conversation

@jsamelak

Copy link
Copy Markdown
Contributor

Currently, these queries are wrongly reported as encodable:

  • Q.unsafeSqlExpr(...)
  • Q.unsafeLokiExpr(...)
  • Q.on(...) nested inside Q.and / Q.or

and they result in throwing Illegal clause … / Illegal Q.on found … by encodeMatcher.

Fix

  • Add isEncodableWhere, which follows the same branches as encodeWhere: where is encodable, and/or are encodable if all their conditions are, and anything else is not.
  • canEncodeMatcher now also requires every top-level where condition to pass this check, so these queries fall back to reloading observation.
  • Update forbiddenError to mention Q.unsafeSqlExpr and Q.unsafeLokiExpr.

StasDoskalenko added a commit to StasDoskalenko/NitromelonDB that referenced this pull request Sep 24, 2026
…ted Q.on)

canEncodeMatcher rejected only sql/loki conditions. A Q.on nested inside
Q.and/Q.or still reached the matcher and threw "Illegal Q.on". Mirror
encodeWhere() instead: only where, and and/or made entirely of them, are
matchable in JS; everything else re-fetches. Approach from
Nozbe#1977.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
StasDoskalenko added a commit to StasDoskalenko/NitromelonDB that referenced this pull request Sep 25, 2026
…erveOrNull; sortBy with unsafeSqlExpr (#141)

* fix(observation): observe queries with raw SQL/Loki expressions; add findAndObserveOrNull and Q.sortBy(Q.unsafeSqlExpr())

- canEncodeMatcher now rejects Q.unsafeSqlExpr / Q.unsafeLokiExpr anywhere
  in the where tree, so those queries re-run on change instead of throwing
  "Illegal clause sql" from the JS matcher (WatermelonDB#1679)
- Collection#findAndObserveOrNull(id): emits null for a missing record,
  the record once it appears, and null again once it's deleted
- Q.sortBy accepts Q.unsafeSqlExpr() on SQLite adapters; LokiJS rejects it

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>

* fix(observation): allow-list JS-matchable conditions (also covers nested Q.on)

canEncodeMatcher rejected only sql/loki conditions. A Q.on nested inside
Q.and/Q.or still reached the matcher and threw "Illegal Q.on". Mirror
encodeWhere() instead: only where, and and/or made entirely of them, are
matchable in JS; everything else re-fetches. Approach from
Nozbe#1977.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>

---------

Co-authored-by: Claude Opus 5.5 <noreply@anthropic.com>

This branch has not been deployed

No deployments
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant