Skip to content

fix: UnSubscribe removes entry from map regardless of socket state + add removeSubscriptions, clearAllSubscriptions and resetInstance utilities#1142

Open
assajeeb wants to merge 4 commits into
parse-community:masterfrom
assajeeb:master
Open

fix: UnSubscribe removes entry from map regardless of socket state + add removeSubscriptions, clearAllSubscriptions and resetInstance utilities#1142
assajeeb wants to merge 4 commits into
parse-community:masterfrom
assajeeb:master

Conversation

@assajeeb

@assajeeb assajeeb commented Jun 8, 2026

Copy link
Copy Markdown

Problem

When unSubscribe() is called after the WebSocket is already closed,
the _requestSubscription map entry is never removed because the
removal was gated inside if (channel != null).

This causes ghost subscriptions to accumulate in the map. On every
WebSocket reconnect, the connected handler iterates the map and
re-sends subscribe messages for all entries — including stale ones
from previous sessions that should have been cleaned up.

Root Cause

void unSubscribe(Subscription subscription) {
  WebSocketChannel? channel = _channel;
  if (channel != null) {
    channel.sink.add(jsonEncode(unsubscribeMessage));
    subscription._enabled = false;
    _requestSubscription.remove(subscription.requestId); // ← never reached if socket closed
  }
  // if channel is null → entry stays in map forever
}

A common teardown pattern is:

client.unSubscribe(sub);
await client.disconnect();

In this case unSubscribe works correctly. But if disconnect() is
called first — or if the socket drops before unSubscribe is called —
the channel is already null and the map entry is never removed.

Changes

1. Fix unSubscribe — always remove from map

The unsubscribe op is only sent over the socket if the channel is open
(correct behaviour), but _enabled = false and map removal now always
execute regardless of socket state.

void unSubscribe(Subscription subscription) {
  WebSocketChannel? channel = _channel;
  if (channel != null) {
    channel.sink.add(jsonEncode(unsubscribeMessage));
  }
  subscription._enabled = false;
  _requestSubscription.remove(subscription.requestId);
}

2. Add removeSubscriptions(List<Subscription> subs)

Removes a targeted set of subscriptions from the internal map without
affecting others. Useful when multiple independent features share the
same singleton client and only one group needs to be torn down.

void removeSubscriptions(List<Subscription> subs) {
  for (final sub in subs) {
    sub._enabled = false;
    _requestSubscription.remove(sub.requestId);
  }
}

3. Add clearAllSubscriptions()

Disables and removes all entries from _requestSubscription without
closing the socket.

void clearAllSubscriptions() {
  _requestSubscription.values.toList().forEach((sub) {
    sub._enabled = false;
  });
  _requestSubscription.clear();
}

4. Add resetInstance()

Full singleton reset for cases where a completely fresh client is
needed. Clears all subscriptions, closes the socket, and nulls the
singleton so the next LiveQueryClient() call creates a new instance.
Uses userInitialized: false so the reconnecting controller remains
active after reset.

static Future<void> resetInstance() async {
  final existing = _instance;
  if (existing != null) {
    existing.clearAllSubscriptions();
    try {
      await existing.disconnect(userInitialized: false);
    } catch (_) {}
  }
  _instance = null;
  _requestIdCount = 1;
}

Impact

  • No breaking changes — existing unSubscribe call signature unchanged
  • Ghost subscriptions no longer accumulate after socket closes
  • Reconnect only re-subscribes entries still present in the map
  • New utility methods give callers explicit control over subscription
    lifecycle without workarounds

Summary by CodeRabbit

  • New Features

    • Remove specific live-query subscriptions, clear all active subscriptions, and fully reset the live-query client to a fresh state.
  • Improvements

    • Safer event emission to the live-query stream when the client is closed.
    • Unsubscribe flow now always disables and removes local subscriptions and only sends network unsubscribe when connected.

assajeeb added 2 commits June 9, 2026 03:01
Fix unSubscribe (remove from map even when socket is closed)
Add clearAllSubscriptions() inside LiveQueryClient
Add resetInstance() static method inside LiveQueryClient


Future<void> disposeRoom() async {
  // ... close streams, cancel timers, clear queues ...

  final subs = [subscription, subscription2, subscription3];
  subscription  = null;
  subscription2 = null;
  subscription3 = null;

  // unSubscribe all first (Edit 1 ensures this works even if socket closed)
  for (final sub in subs) {
    if (sub != null) {
      try { LiveQueryClient.instance.unSubscribe(sub); } catch (_) {}
    }
  }

  // Full reset — map cleared, socket closed, singleton nulled
  await LiveQueryClient.resetInstance();

  print("disposeRoom done");
}
add remove single subscription remove
@parse-github-assistant

Copy link
Copy Markdown

I will reformat the title to use the proper commit message syntax.

@parse-github-assistant parse-github-assistant Bot changed the title fix: unSubscribe removes entry from map regardless of socket state + add removeSubscriptions, clearAllSubscriptions and resetInstance utilities fix: UnSubscribe removes entry from map regardless of socket state + add removeSubscriptions, clearAllSubscriptions and resetInstance utilities Jun 8, 2026
@parse-github-assistant

Copy link
Copy Markdown

🚀 Thanks for opening this pull request! We appreciate your effort in improving the project. Please let us know once your pull request is ready for review.

Tip

  • Keep pull requests small. Large PRs will be rejected. Break complex features into smaller, incremental PRs.
  • Use Test Driven Development. Write failing tests before implementing functionality. Ensure tests pass.
  • Group code into logical blocks. Add a short comment before each block to explain its purpose.
  • We offer conceptual guidance. Coding is up to you. PRs must be merge-ready for human review.
  • Our review focuses on concept, not quality. PRs with code issues will be rejected. Use an AI agent.
  • Human review time is precious. Avoid review ping-pong. Inspect and test your AI-generated code.

Note

Please respond to review comments from AI agents just like you would to comments from a human reviewer. Let the reviewer resolve their own comments, unless they have reviewed and accepted your commit, or agreed with your explanation for why the feedback was incorrect.

Caution

Pull requests must be written using an AI agent with human supervision. Pull requests written entirely by a human will likely be rejected, because of lower code quality, higher review effort and the higher risk of introducing bugs. Please note that AI review comments on this pull request alone do not satisfy this requirement. Our CI and AI review are safeguards, not development tools. If many issues are flagged, rethink your development approach. Invest more effort in planning and design rather than using review cycles to fix low-quality code.

@coderabbitai

coderabbitai Bot commented Jun 8, 2026

Copy link
Copy Markdown

Review Change Stack

📝 Walkthrough

Walkthrough

This PR extends the LiveQueryClient with batch subscription removal and clear-all utilities, adds a static resetInstance() to fully reset the singleton, and refactors unSubscribe to always clean up local subscription state while only sending the websocket unsubscribe when a channel exists.

Changes

Subscription lifecycle management

Layer / File(s) Summary
Subscription management utilities
packages/dart/lib/src/network/parse_live_query.dart
Introduces removeSubscriptions(List<Subscription>) to disable and remove specific subscriptions, clearAllSubscriptions() to disable and clear all tracked subscriptions, and static Future<void> resetInstance() to fully reset the singleton instance by clearing subscriptions, attempting disconnect (errors swallowed), closing the internal event stream controller, nulling the instance, and resetting the request ID counter.
Resilient unsubscribe handling
packages/dart/lib/src/network/parse_live_query.dart
Refactors unSubscribe(...) to unconditionally disable subscriptions and remove them from the internal request map, while conditionally sending the unsubscribe websocket message only when a websocket channel is available.
Disconnect and websocket lifecycle handlers
packages/dart/lib/src/network/parse_live_query.dart
Replaces direct sink.add calls with _safeAddEvent(...) for disconnect, websocket onDone, onError, and incoming connected handling to prevent emitting events after the controller is closed.

🎯 3 (Moderate) | ⏱️ ~20 minutes

🚥 Pre-merge checks | ✅ 5 | ❌ 2

❌ Failed checks (1 warning, 1 inconclusive)

Check name Status Explanation Resolution
Security Check ⚠️ Warning Line 371 directly calls sink.add() without the _safeAddEvent() guard introduced elsewhere, risking crashes if the stream controller closes during error handling. Replace direct sink.add() at line 371-373 with _safeAddEvent() to prevent writing to closed streams.
Engage In Review Feedback ❓ Inconclusive Single commit with generic message shows no visible review engagement in git history, but GitHub PR comments not accessible via code analysis. Verify on GitHub PR #1142 that author engaged with review comments before merging or implementing changes.
✅ Passed checks (5 passed)
Check name Status Explanation
Title check ✅ Passed The PR title begins with 'fix:' prefix as required and accurately describes the main changes: fixing unSubscribe behavior and adding three utility methods.
Description check ✅ Passed The description provides comprehensive context including problem statement, root cause, detailed change explanations, and impact analysis, though it deviates from the template structure.
Docstring Coverage ✅ Passed No functions found in the changed files to evaluate docstring coverage. Skipping docstring coverage check.
Linked Issues check ✅ Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check ✅ Passed Check skipped because no linked issues were found for this pull request.

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

✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests

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.

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

Actionable comments posted: 2

🤖 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 `@packages/dart/lib/src/network/parse_live_query.dart`:
- Around line 235-241: resetInstance currently leaves the old
LiveQueryReconnectingController able to reconnect because it only calls
disconnect(userInitialized: false); update resetInstance to explicitly
stop/disable the reconnect loop on the old instance's controller (e.g., call the
LiveQueryReconnectingController's disable/stop/dispose method) before or
immediately after calling disconnect and before clearing _instance so the old
instance cannot respond to lifecycle/connectivity events; reference the existing
variable (existing) and its reconnect controller (e.g.,
existing.reconnectingController) and ensure the controller is put into a
non-reconnecting state.
- Around line 302-308: The unSubscribe snippet currently only checks that
_channel is non-null but may still be closed/closing; update the logic in the
unSubscribe handling around _channel (referencing _channel, unsubscribeMessage,
_debug, _printConstLiveQuery) to ensure the socket is open before calling
channel.sink.add: first check an "open" indicator (e.g. channel.closeCode ==
null / no closeCode or other available open-state property on the concrete
channel implementation) and only call sink.add when open, and additionally wrap
the send in a try/catch to swallow/log errors instead of letting sink.add throw
on closing/closed sockets.
🪄 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: Organization UI

Review profile: CHILL

Plan: Pro

Run ID: 03f5e004-1ed2-4621-9315-d224c2387a94

📥 Commits

Reviewing files that changed from the base of the PR and between 785f76b and 48da59b.

📒 Files selected for processing (1)
  • packages/dart/lib/src/network/parse_live_query.dart

Comment on lines +235 to +241
static Future<void> resetInstance() async {
final existing = _instance;
if (existing != null) {
existing.clearAllSubscriptions();
try {
await existing.disconnect(userInitialized: false);
} catch (_) {}

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

⚠️ Potential issue | 🟠 Major | 🏗️ Heavy lift

resetInstance() does not fully disable the old reconnect loop

Line 240 uses disconnect(userInitialized: false), which leaves the old LiveQueryReconnectingController in reconnect-capable state. After reset, the old instance can still reconnect from lifecycle/connectivity events.

Suggested fix
 static Future<void> resetInstance() async {
   final existing = _instance;
   if (existing != null) {
     existing.clearAllSubscriptions();
     try {
-      await existing.disconnect(userInitialized: false);
+      await existing.disconnect(userInitialized: true);
     } catch (_) {}
   }
   _instance = null;
   _requestIdCount = 1;
 }
📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
static Future<void> resetInstance() async {
final existing = _instance;
if (existing != null) {
existing.clearAllSubscriptions();
try {
await existing.disconnect(userInitialized: false);
} catch (_) {}
static Future<void> resetInstance() async {
final existing = _instance;
if (existing != null) {
existing.clearAllSubscriptions();
try {
await existing.disconnect(userInitialized: true);
} catch (_) {}
}
_instance = null;
_requestIdCount = 1;
}
🤖 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 `@packages/dart/lib/src/network/parse_live_query.dart` around lines 235 - 241,
resetInstance currently leaves the old LiveQueryReconnectingController able to
reconnect because it only calls disconnect(userInitialized: false); update
resetInstance to explicitly stop/disable the reconnect loop on the old
instance's controller (e.g., call the LiveQueryReconnectingController's
disable/stop/dispose method) before or immediately after calling disconnect and
before clearing _instance so the old instance cannot respond to
lifecycle/connectivity events; reference the existing variable (existing) and
its reconnect controller (e.g., existing.reconnectingController) and ensure the
controller is put into a non-reconnecting state.

Comment on lines +302 to 308
WebSocketChannel? channel = _channel;
if (channel != null) {
if (_debug) {
print('$_printConstLiveQuery: UnsubscribeMessage: $unsubscribeMessage');
}
channel.sink.add(jsonEncode(unsubscribeMessage));
}

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

⚠️ Potential issue | 🟠 Major | ⚡ Quick win

unSubscribe still sends on non-open channels

Line 303 only checks non-null channel; it does not ensure the socket is open. In disconnected/closing states this can throw on sink.add(...).

Suggested fix
   WebSocketChannel? channel = _channel;
-  if (channel != null) {
+  final webSocket = _webSocket;
+  if (channel != null &&
+      webSocket != null &&
+      webSocket.readyState == parse_web_socket.WebSocket.open) {
     if (_debug) {
       print('$_printConstLiveQuery: UnsubscribeMessage: $unsubscribeMessage');
     }
     channel.sink.add(jsonEncode(unsubscribeMessage));
   }
📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
WebSocketChannel? channel = _channel;
if (channel != null) {
if (_debug) {
print('$_printConstLiveQuery: UnsubscribeMessage: $unsubscribeMessage');
}
channel.sink.add(jsonEncode(unsubscribeMessage));
}
WebSocketChannel? channel = _channel;
final webSocket = _webSocket;
if (channel != null &&
webSocket != null &&
webSocket.readyState == parse_web_socket.WebSocket.open) {
if (_debug) {
print('$_printConstLiveQuery: UnsubscribeMessage: $unsubscribeMessage');
}
channel.sink.add(jsonEncode(unsubscribeMessage));
}
🤖 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 `@packages/dart/lib/src/network/parse_live_query.dart` around lines 302 - 308,
The unSubscribe snippet currently only checks that _channel is non-null but may
still be closed/closing; update the logic in the unSubscribe handling around
_channel (referencing _channel, unsubscribeMessage, _debug,
_printConstLiveQuery) to ensure the socket is open before calling
channel.sink.add: first check an "open" indicator (e.g. channel.closeCode ==
null / no closeCode or other available open-state property on the concrete
channel implementation) and only call sink.add when open, and additionally wrap
the send in a try/catch to swallow/log errors instead of letting sink.add throw
on closing/closed sockets.

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

Caution

Some comments are outside the diff and can’t be posted inline due to platform limitations.

⚠️ Outside diff range comments (1)
packages/dart/lib/src/network/parse_live_query.dart (1)

370-373: ⚠️ Potential issue | 🟠 Major | ⚡ Quick win

onError handler still uses direct sink.add instead of _safeAddEvent.

The PR objectives state that onError should use _safeAddEvent, but this handler still calls _clientEventStreamController.sink.add(...) directly. This can throw if the controller is closed, which is exactly what _safeAddEvent was introduced to prevent.

🐛 Proposed fix
       onError: (Object error) {
-        _clientEventStreamController.sink.add(
-          LiveQueryClientEvent.disconnected,
-        );
+        _safeAddEvent(LiveQueryClientEvent.disconnected);
         if (_debug) {
🤖 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 `@packages/dart/lib/src/network/parse_live_query.dart` around lines 370 - 373,
Replace the direct call to _clientEventStreamController.sink.add in the onError
handler with a call to _safeAddEvent so we don't throw when the controller is
closed: locate the onError closure that currently does
_clientEventStreamController.sink.add(LiveQueryClientEvent.disconnected) and
change it to call _safeAddEvent(LiveQueryClientEvent.disconnected) (keeping the
same event value) so the helper handles closed-controller safety.
🧹 Nitpick comments (4)
packages/dart/lib/src/network/parse_live_query.dart (4)

491-492: 💤 Low value

Fix indentation.

This line should be indented to match the method body level (6 spaces within _handleMessage).

🧹 Suggested fix
-_safeAddEvent(LiveQueryClientEvent.connected);
+      _safeAddEvent(LiveQueryClientEvent.connected);
🤖 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 `@packages/dart/lib/src/network/parse_live_query.dart` around lines 491 - 492,
The line calling _safeAddEvent(LiveQueryClientEvent.connected); followed by
return is mis-indented inside the _handleMessage method; adjust the indentation
of that statement block to the same level as the rest of the method body (6
spaces inside _handleMessage) so it aligns with surrounding statements and
maintains consistent formatting for the _handleMessage function.

228-236: 💤 Low value

Fix indentation for class method.

Same indentation fix needed here.

🧹 Suggested fix
-/// Removes all subscriptions from the internal map.
-/// Call before disconnect when leaving a live room.
-  
-void clearAllSubscriptions() {
-  _requestSubscription.values.toList().forEach((sub) {
-    sub._enabled = false;
-  });
-  _requestSubscription.clear();
-}
+  /// Removes all subscriptions from the internal map.
+  /// Call before disconnect when leaving a live room.
+  void clearAllSubscriptions() {
+    for (final sub in _requestSubscription.values) {
+      sub._enabled = false;
+    }
+    _requestSubscription.clear();
+  }
🤖 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 `@packages/dart/lib/src/network/parse_live_query.dart` around lines 228 - 236,
The method clearAllSubscriptions is misindented and should be nested correctly
inside its class; move/adjust its indentation to match other class methods so it
aligns with the class member scope (ensure clearAllSubscriptions, its body
referencing _requestSubscription,
_requestSubscription.values.toList().forEach(...) and sub._enabled are indented
consistently with surrounding methods).

204-208: 💤 Low value

Fix indentation in _safeAddEvent.

The method body is not properly indented within the function block.

🧹 Suggested fix
-  void _safeAddEvent(LiveQueryClientEvent event) {
-  if (!_clientEventStreamController.isClosed) {
-    _clientEventStreamController.sink.add(event);
-  }
-}
+  void _safeAddEvent(LiveQueryClientEvent event) {
+    if (!_clientEventStreamController.isClosed) {
+      _clientEventStreamController.sink.add(event);
+    }
+  }
🤖 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 `@packages/dart/lib/src/network/parse_live_query.dart` around lines 204 - 208,
The _safeAddEvent method's body is mis-indented; adjust indentation so the if
block and its inner call are indented one level inside the method (use the
project's Dart indentation style, e.g., two spaces) and keep the closing brace
aligned with the method declaration. Locate function _safeAddEvent and ensure
_clientEventStreamController and .sink.add(event) lines are properly nested
under the if statement and the method's braces.

218-226: 💤 Low value

Fix indentation for class method.

The method declaration should be indented to align with other class methods (2 spaces).

🧹 Suggested fix
-/// Removes specific subscriptions from the map by requestId.
-/// Use this instead of clearAllSubscriptions() when other subscriptions
-/// (banners, notifications) must stay alive.
-void removeSubscriptions(List<Subscription> subs) {
-  for (final sub in subs) {
-    sub._enabled = false;
-    _requestSubscription.remove(sub.requestId);
+  /// Removes specific subscriptions from the map by requestId.
+  /// Use this instead of clearAllSubscriptions() when other subscriptions
+  /// (banners, notifications) must stay alive.
+  void removeSubscriptions(List<Subscription> subs) {
+    for (final sub in subs) {
+      sub._enabled = false;
+      _requestSubscription.remove(sub.requestId);
+    }
   }
-}
🤖 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 `@packages/dart/lib/src/network/parse_live_query.dart` around lines 218 - 226,
The removeSubscriptions method is mis-indented; adjust its declaration and body
to use 2-space indentation to match other class methods. Locate the
removeSubscriptions(List<Subscription> subs) method and align the comment,
method signature, and body so the leading spaces are two, keeping the logic that
sets sub._enabled = false and calls _requestSubscription.remove(sub.requestId)
unchanged.
🤖 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.

Outside diff comments:
In `@packages/dart/lib/src/network/parse_live_query.dart`:
- Around line 370-373: Replace the direct call to
_clientEventStreamController.sink.add in the onError handler with a call to
_safeAddEvent so we don't throw when the controller is closed: locate the
onError closure that currently does
_clientEventStreamController.sink.add(LiveQueryClientEvent.disconnected) and
change it to call _safeAddEvent(LiveQueryClientEvent.disconnected) (keeping the
same event value) so the helper handles closed-controller safety.

---

Nitpick comments:
In `@packages/dart/lib/src/network/parse_live_query.dart`:
- Around line 491-492: The line calling
_safeAddEvent(LiveQueryClientEvent.connected); followed by return is
mis-indented inside the _handleMessage method; adjust the indentation of that
statement block to the same level as the rest of the method body (6 spaces
inside _handleMessage) so it aligns with surrounding statements and maintains
consistent formatting for the _handleMessage function.
- Around line 228-236: The method clearAllSubscriptions is misindented and
should be nested correctly inside its class; move/adjust its indentation to
match other class methods so it aligns with the class member scope (ensure
clearAllSubscriptions, its body referencing _requestSubscription,
_requestSubscription.values.toList().forEach(...) and sub._enabled are indented
consistently with surrounding methods).
- Around line 204-208: The _safeAddEvent method's body is mis-indented; adjust
indentation so the if block and its inner call are indented one level inside the
method (use the project's Dart indentation style, e.g., two spaces) and keep the
closing brace aligned with the method declaration. Locate function _safeAddEvent
and ensure _clientEventStreamController and .sink.add(event) lines are properly
nested under the if statement and the method's braces.
- Around line 218-226: The removeSubscriptions method is mis-indented; adjust
its declaration and body to use 2-space indentation to match other class
methods. Locate the removeSubscriptions(List<Subscription> subs) method and
align the comment, method signature, and body so the leading spaces are two,
keeping the logic that sets sub._enabled = false and calls
_requestSubscription.remove(sub.requestId) unchanged.

ℹ️ Review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro

Run ID: 43bf64df-2901-41f6-ada1-ee1e449cea49

📥 Commits

Reviewing files that changed from the base of the PR and between 4c6bf18 and e78f8ea.

📒 Files selected for processing (1)
  • packages/dart/lib/src/network/parse_live_query.dart

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