Skip to content

Add realtime queries docs and announcement blog#2746

Open
atharvadeosthale wants to merge 2 commits intomainfrom
realtime-queries
Open

Add realtime queries docs and announcement blog#2746
atharvadeosthale wants to merge 2 commits intomainfrom
realtime-queries

Conversation

@atharvadeosthale
Copy link
Member

@atharvadeosthale atharvadeosthale commented Feb 12, 2026

Currently based off branch realtime-channel-helper because it has the newest realtime changes, will change to main once the other branch is merged.

Summary by CodeRabbit

  • Documentation
    • New blog post announcing Realtime queries and server-side event filtering for subscriptions
    • Expanded API documentation with multi-language code examples for Realtime query filtering
    • Added comprehensive list of supported query methods and payload schema details

@coderabbitai
Copy link
Contributor

coderabbitai bot commented Feb 12, 2026

Walkthrough

This pull request adds documentation and blog content for realtime query filtering capabilities. A new blog post is introduced to announce realtime queries, and the realtime API documentation is expanded with a dedicated "Queries" section. The documentation section includes code examples across four client languages (web, Flutter, Apple, Android), details on supported query methods (equality, comparison, null-check, and logical operators), and response payload specifications. No changes to actual code or public APIs are introduced.

Estimated code review effort

🎯 2 (Simple) | ⏱️ ~12 minutes

🚥 Pre-merge checks | ✅ 3 | ❌ 1
❌ Failed checks (1 warning)
Check name Status Explanation Resolution
Merge Conflict Detection ⚠️ Warning ❌ Merge conflicts detected (30 files):

⚔️ .optimize-cache.json (content)
⚔️ server/sitemap.js (content)
⚔️ src/hooks.server.ts (content)
⚔️ src/lib/utils/canonical.ts (content)
⚔️ src/routes/docs/advanced/security/encryption/+page.markdoc (content)
⚔️ src/routes/docs/apis/realtime/+page.markdoc (content)
⚔️ src/routes/docs/products/databases/csv-imports/+page.markdoc (content)
⚔️ src/routes/docs/products/databases/legacy/type-generation/+page.markdoc (content)
⚔️ src/routes/docs/products/databases/tables/+page.markdoc (content)
⚔️ src/routes/docs/products/databases/type-generation/+page.markdoc (content)
⚔️ src/routes/docs/quick-starts/dart/+page.markdoc (content)
⚔️ src/routes/docs/quick-starts/deno/+page.markdoc (content)
⚔️ src/routes/docs/quick-starts/dotnet/+page.markdoc (content)
⚔️ src/routes/docs/quick-starts/go/+page.markdoc (content)
⚔️ src/routes/docs/quick-starts/kotlin/+page.markdoc (content)
⚔️ src/routes/docs/quick-starts/node/+page.markdoc (content)
⚔️ src/routes/docs/quick-starts/php/+page.markdoc (content)
⚔️ src/routes/docs/quick-starts/python/+page.markdoc (content)
⚔️ src/routes/docs/quick-starts/ruby/+page.markdoc (content)
⚔️ src/routes/docs/quick-starts/swift/+page.markdoc (content)
⚔️ src/routes/docs/tooling/command-line/tables/+page.markdoc (content)
⚔️ src/routes/docs/tutorials/android/step-6/+page.markdoc (content)
⚔️ src/routes/docs/tutorials/nextjs/step-6/+page.markdoc (content)
⚔️ src/routes/docs/tutorials/nuxt/step-6/+page.markdoc (content)
⚔️ src/routes/docs/tutorials/react-native/step-6/+page.markdoc (content)
⚔️ src/routes/docs/tutorials/react/step-6/+page.markdoc (content)
⚔️ src/routes/docs/tutorials/refine/step-5/+page.markdoc (content)
⚔️ src/routes/docs/tutorials/sveltekit/step-6/+page.markdoc (content)
⚔️ src/routes/docs/tutorials/vue/step-6/+page.markdoc (content)
⚔️ src/routes/robots.txt/+server.ts (content)

These conflicts must be resolved before merging into main.
Resolve conflicts locally and push changes to this branch.
✅ Passed checks (3 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check ✅ Passed The title 'Add realtime queries docs and announcement blog' directly and accurately describes the main changes—documentation and a blog post about realtime queries.
Docstring Coverage ✅ Passed No functions found in the changed files to evaluate docstring coverage. Skipping docstring coverage check.

✏️ Tip: You can configure your own custom pre-merge checks in the settings.

✨ Finishing touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Post copyable unit tests in a comment
  • Commit unit tests in branch realtime-queries
⚔️ Resolve merge conflicts (beta)
  • Auto-commit resolved conflicts to branch realtime-queries
  • Create stacked PR with resolved conflicts
  • Post resolved changes as copyable diffs in a comment

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.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.

@atharvadeosthale atharvadeosthale changed the base branch from realtime-channel-helper to main February 13, 2026 17:25
Copy link
Contributor

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 2

🤖 Fix all issues with AI agents
In `@src/routes/blog/post/announcing-realtime-queries/`+page.markdoc:
- Line 6: The frontmatter cover image path currently points to the other post's
asset (`/images/blog/announcing-realtime-channel-helpers/cover.png`); update the
cover field in the +page.markdoc frontmatter to reference the correct image for
this realtime-queries post (or, if intentionally reusing that image, add an
inline comment above the cover line explaining reuse and why it’s shared) so the
cover is accurate and clear.

In `@src/routes/docs/apis/realtime/`+page.markdoc:
- Around line 565-601: The subscribe calls are passing Query objects into the
queries parameter which expects a Set<String>; update each Realtime.subscribe
invocation (the three usages where Channel.tablesdb(...).table(...).row() is
used) to convert Query.equal(...) and Query.notEqual(...) to strings by calling
.toString() so queries is a Set<String> (e.g., replace Query.equal("person",
listOf("person1")) with Query.equal(...).toString()), ensuring
payloadType/onSubscribe semantics remain unchanged.
🧹 Nitpick comments (3)
src/routes/blog/post/announcing-realtime-queries/+page.markdoc (1)

50-59: Inconsistent parameter style between Query.equal and Query.notEqual.

Line 50 passes an array ['person1'] while Line 59 passes a plain string 'person1'. While both may be valid, using a consistent style in the same code example would be clearer for readers.

Suggested fix for consistency
-    [Query.equal('person', ['person1'])]
+    [Query.equal('person', 'person1')]

Or alternatively, wrap both in arrays.

src/routes/docs/apis/realtime/+page.markdoc (2)

449-451: "Third parameter" description is only accurate for the Web SDK.

The Flutter, Apple, and Android examples all use named parameters (queries:) rather than a positional third argument. Consider rephrasing to something like "passing queries when subscribing" to be SDK-agnostic.

Suggested wording
-You can filter realtime events by passing queries as a third parameter when subscribing. Events are filtered server-side based on your queries, so your callback only receives updates that match your conditions. This allows you to use familiar SDK queries like `Query.equal` to automatically filter events instead of filtering manually in your callback.
+You can filter realtime events by passing queries when subscribing. Events are filtered server-side based on your queries, so your callback only receives updates that match your conditions. This allows you to use familiar SDK queries like `Query.equal` to automatically filter events instead of filtering manually in your callback.

477-486: Same inconsistency as the blog: array vs string parameter in Query methods.

Query.equal on line 477 uses ['person1'] (array) while Query.notEqual on line 486 uses 'person1' (string). This pattern repeats across all four SDK examples. Pick one style for consistency within the same code block.

title: "Introducing Realtime queries: Server-side event filtering for subscriptions"
description: Pass SDK queries when subscribing to realtime channels to automatically filter events server-side, so your callbacks only receive the updates you care about.
date: 2026-02-16
cover: /images/blog/announcing-realtime-channel-helpers/cover.png
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🟡 Minor

Cover image path references a different blog post.

The cover path /images/blog/announcing-realtime-channel-helpers/cover.png points to the channel-helpers announcement, not this realtime-queries post. If this is intentional reuse, consider adding a comment. Otherwise, update the path to a dedicated cover image.

🤖 Prompt for AI Agents
In `@src/routes/blog/post/announcing-realtime-queries/`+page.markdoc at line 6,
The frontmatter cover image path currently points to the other post's asset
(`/images/blog/announcing-realtime-channel-helpers/cover.png`); update the cover
field in the +page.markdoc frontmatter to reference the correct image for this
realtime-queries post (or, if intentionally reusing that image, add an inline
comment above the cover line explaining reuse and why it’s shared) so the cover
is accurate and clear.

Comment on lines +565 to +601
```client-android-kotlin
import io.appwrite.Client
import io.appwrite.Query
import io.appwrite.services.Realtime
import io.appwrite.extensions.Channel

val client = Client(context)
.setEndpoint("https://<REGION>.cloud.appwrite.io/v1")
.setProject("<PROJECT_ID>")

val realtime = Realtime(client)

// Subscribe to all updates
val allVotes = realtime.subscribe(
Channel.tablesdb("<DATABASE_ID>").table("<TABLE_ID>").row()
) {
print(it.payload.toString())
}

// Subscribe to updates where person equals 'person1'
val person1Votes = realtime.subscribe(
Channel.tablesdb("<DATABASE_ID>").table("<TABLE_ID>").row(),
payloadType = Any::class.java,
queries = setOf(Query.equal("person", listOf("person1")))
) {
print(it.payload.toString())
}

// Subscribe to updates where person is not 'person1'
val otherVotes = realtime.subscribe(
Channel.tablesdb("<DATABASE_ID>").table("<TABLE_ID>").row(),
payloadType = Any::class.java,
queries = setOf(Query.notEqual("person", "person1"))
) {
print(it.payload.toString())
}
```
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🟠 Major

🧩 Analysis chain

🌐 Web query:

Appwrite Kotlin SDK Realtime subscribe method signature queries parameter documentation

💡 Result:

In the Appwrite Android (Kotlin) SDK, Realtime.subscribe has overloads that accept a queries parameter with this signature (simplified to the relevant one):

fun <T> subscribe(
    vararg channels: String,
    payloadType: Class<T>,
    queries: Set<String> = emptySet(),
    callback: (RealtimeResponseEvent<T>) -> Unit
): RealtimeSubscription

Source (SDK implementation): io.appwrite.services.Realtime in sdk-for-android repo. [1]

What queries is

  • queries is a set of query strings (the same query-string format produced by Appwrite’s Query helpers, e.g. Query.select(...), Query.equal(...), etc.). Appwrite documents queries as “passed … as an array of query strings, which can be generated using the Query class.” [2]
  • If you pass no queries (emptySet()), the SDK defaults to selecting all attributes by sending Query.select(listOf("*")). [1]

What it affects for Realtime

Realtime subscriptions are still based on channels (per the Realtime docs). [3] In the Android SDK, the queries you pass are additionally sent as URL parameters per-channel/per-subscription-slot (implementation detail), and are used to shape/filter what the server returns for that subscription. [1][3]

Example (select only specific fields in the realtime payload):

realtime.subscribe(
  "databases.$db.collections.$col.documents",
  payloadType = Document::class.java,
  queries = setOf(Query.select(listOf("\$id", "title")).toString())
) { event -> /* ... */ }

(Uses Query.select as documented.) [2]

Sources: [1] [2] [3]


Add .toString() to Query objects in the queries parameter.

The queries parameter expects a Set<String>, not Query objects. Convert each Query using .toString():

Example fix
queries = setOf(Query.equal("person", listOf("person1")).toString())

instead of:

queries = setOf(Query.equal("person", listOf("person1")))

Apply this to all three subscribe calls (lines 580, 587, and 594).

🤖 Prompt for AI Agents
In `@src/routes/docs/apis/realtime/`+page.markdoc around lines 565 - 601, The
subscribe calls are passing Query objects into the queries parameter which
expects a Set<String>; update each Realtime.subscribe invocation (the three
usages where Channel.tablesdb(...).table(...).row() is used) to convert
Query.equal(...) and Query.notEqual(...) to strings by calling .toString() so
queries is a Set<String> (e.g., replace Query.equal("person", listOf("person1"))
with Query.equal(...).toString()), ensuring payloadType/onSubscribe semantics
remain unchanged.

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.

2 participants