Skip to content

Conversation

@xsahil03x
Copy link
Member

@xsahil03x xsahil03x commented Dec 8, 2025

Submit a pull request

Closes FLU-348

Description of the pull request

Introduces an onNewActivity callback to the Feed and feedFromQuery methods. This allows for custom logic to determine how new activities from real-time events are inserted into the activity list.

The callback returns an InsertionAction (addToStart, addToEnd, or ignore).

A default implementation is provided that adds activities from the current user to the start of the list if they match the query filter.

Important

Switch to pub dependency before merging the PR

Summary by CodeRabbit

  • New Features

    • Customizable activity insertion for feeds via a new onNewActivity callback (controls add-to-start, add-to-end, or ignore)
    • Added InsertionAction enum to specify insertion behavior; default preserves previous behavior
  • Dependencies

    • Updated stream_core dependency to a git-based resolution
  • Tests

    • Added comprehensive tests covering insertion customization and edge cases

✏️ Tip: You can customize this high-level summary in your review settings.

Introduces an `onNewActivity` callback to the `Feed` and `feedFromQuery` methods. This allows for custom logic to determine how new activities from real-time events are inserted into the activity list.

The callback returns an `InsertionAction` (`addToStart`, `addToEnd`, or `ignore`).

A default implementation is provided that adds activities from the current user to the start of the list if they match the query filter.
@xsahil03x xsahil03x requested a review from a team as a code owner December 8, 2025 17:46
@coderabbitai
Copy link

coderabbitai bot commented Dec 8, 2025

Warning

Rate limit exceeded

@xsahil03x has exceeded the limit for the number of commits or files that can be reviewed per hour. Please wait 11 minutes and 30 seconds before requesting another review.

⌛ How to resolve this issue?

After the wait time has elapsed, a review can be triggered using the @coderabbitai review command as a PR comment. Alternatively, push new commits to this PR.

We recommend that you space out your commits to avoid hitting the rate limit.

🚦 How do rate limits work?

CodeRabbit enforces hourly rate limits for each developer per organization.

Our paid plans have higher rate limits than the trial, open-source and free plans. In all cases, we re-allow further reviews after a brief timeout.

Please see our FAQ for further information.

📥 Commits

Reviewing files that changed from the base of the PR and between a1a8846 and b53e611.

📒 Files selected for processing (1)
  • packages/stream_feeds/test/state/feed_test.dart (4 hunks)

Walkthrough

Adds an OnNewActivity callback and InsertionAction enum to control how real-time ActivityAdded events are inserted (ignore / add-to-start / add-to-end). Threads the callback through client APIs and Feed/FeedEventHandler/FeedState, adjusts many import paths for event handlers, and switches stream_core to a git dependency.

Changes

Cohort / File(s) Summary
Dependency configuration
melos.yaml, packages/stream_feeds/pubspec.yaml
Replaced stream_core version constraint with a git dependency: URL https://github.com/GetStream/stream-core-flutter.git, ref feat/more-list-extensions, path packages/stream_core.
New insertion control types
packages/stream_feeds/lib/src/state/insertion_action.dart
Added public enum InsertionAction with values ignore, addToEnd, addToStart.
New activity callback handler
packages/stream_feeds/lib/src/state/event/on_activity_added.dart
Added OnNewActivity typedef and defaultOnNewActivity implementation (decides insertion based on current user and query filter).
Filter extension
packages/stream_feeds/lib/src/utils/filter.dart
Added MatchesExtensions<T> with bool matches(Filter<T>? filter) for null-safe filter matching.
Client API surface
packages/stream_feeds/lib/src/feeds_client.dart, packages/stream_feeds/lib/src/client/feeds_client_impl.dart
Threaded optional OnNewActivity onNewActivity through feedFromQuery, feedFromId, and feed (defaulting to defaultOnNewActivity).
Feed integration
packages/stream_feeds/lib/src/state/feed.dart, packages/stream_feeds/lib/src/state/feed_state.dart
Feed now stores OnNewActivity onNewActivity; FeedState.onActivityAdded gains InsertionAction insertionAction parameter and inserts using the specified action.
Event handler enhancement
packages/stream_feeds/lib/src/state/event/handler/feed_event_handler.dart
FeedEventHandler requires OnNewActivity and uses it to compute insertion action (replacing prior matchesQueryFilter early-exit).
Event handlers directory restructuring
many packages/stream_feeds/lib/src/state/*.dart files
Updated imports to reflect event handlers moved under event/handler/ (adjusted many relative import paths).
Event handler files
packages/stream_feeds/lib/src/state/event/handler/*
Adjusted relative imports to new directory depth; most files unchanged except path fixes.
State exports
packages/stream_feeds/lib/src/state.dart
Exported state/insertion_action.dart.
Tests
packages/stream_feeds/test/state/feed_test.dart, packages/stream_feeds/test/test_utils/fakes.dart
Added comprehensive OnNewActivity tests and updated test fakes to accept userId; added filter imports for tests.
Sample app
sample_app/lib/screens/user_feed/user_feed_screen.dart
Stories feed now passes a custom onNewActivity callback that returns InsertionAction.addToEnd.
Changelog
packages/stream_feeds/CHANGELOG.md
Documented behavioral change and new onNewActivity API.

Sequence Diagram(s)

sequenceDiagram
    participant WS as WebSocket Event
    participant Handler as FeedEventHandler
    participant Callback as onNewActivity Callback
    participant State as FeedState
    participant List as Activity List

    WS->>Handler: ActivityAddedEvent
    Handler->>Handler: extract query, activity, currentUserId
    Handler->>Callback: onNewActivity(query, activity, currentUserId)
    activate Callback
    Callback-->>Handler: InsertionAction (ignore | addToStart | addToEnd)
    deactivate Callback

    alt ignore
        Handler->>Handler: skip insertion
    else addToStart
        Handler->>State: onActivityAdded(activity, insertionAction: addToStart)
        State->>List: insert at index 0
    else addToEnd
        Handler->>State: onActivityAdded(activity, insertionAction: addToEnd)
        State->>List: append to end
    end
Loading

Estimated code review effort

🎯 3 (Moderate) | ⏱️ ~20 minutes

  • Areas to focus:
    • packages/stream_feeds/lib/src/state/event/handler/feed_event_handler.dart — verify callback integration and removal of prior filter short-circuit.
    • packages/stream_feeds/lib/src/state/feed_state.dart — confirm insert index calculation, especially addToEnd behavior.
    • API threading in feeds_client.dart and feeds_client_impl.dart — ensure defaults preserved and parameter propagation is consistent.
    • packages/stream_feeds/lib/src/state/event/on_activity_added.dart — review defaultOnNewActivity edge-cases.
    • Spot-check adjusted import paths in a few handler files for correctness.

Suggested reviewers

  • Brazol

Poem

🐰 A little rabbit hops with glee and cheer,
"Where shall this new activity appear?"
Ignore, to start, or gently to the end,
The callback decides — a helpful friend. 🥕

Pre-merge checks and finishing touches

✅ Passed checks (5 passed)
Check name Status Explanation
Title check ✅ Passed The title 'feat(llc): add onNewActivity callback to Feed' accurately and concisely describes the main feature addition in the changeset.
Description check ✅ Passed The PR description clearly explains the feature, callback behavior, default implementation, and includes the linked issue reference FLU-348, though some template sections are not completed.
Linked Issues check ✅ Passed The implementation fully addresses FLU-348 objectives: provides onNewActivity handler, supports activity skipping via ignore, allows insertion from current user with filter matching, and uses InsertionAction enum instead of boolean flags.
Out of Scope Changes check ✅ Passed All changes are directly related to implementing the onNewActivity callback feature; import path reorganizations and dependency updates support the feature implementation with no unrelated modifications.
Docstring Coverage ✅ Passed No functions found in the changed files to evaluate docstring coverage. Skipping docstring coverage check.

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.

Copy link

@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: 0

Caution

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

⚠️ Outside diff range comments (1)
packages/stream_feeds/lib/src/feeds_client.dart (1)

800-834: OnNewActivity typedef and defaultOnNewActivity function are not exported in the public API.

The OnNewActivity typedef is used in the public feed() and feedFromId() method signatures in feeds_client.dart, but it's not exported through state.dart. The file state/on_activity_added.dart is missing from the export list in packages/stream_feeds/lib/src/state.dart. Additionally, defaultOnNewActivity is marked @internal and should not be part of the public API. Add the export to state.dart:

export 'state/on_activity_added.dart';
🧹 Nitpick comments (5)
packages/stream_feeds/lib/src/state/insertion_action.dart (1)

1-13: Consider adding barrel file annotation.

The enum is well-designed and clearly documented. However, since this is part of the public API (used by the OnNewActivity callback), consider marking it with @includeInBarrelFile annotation if it should be exported through the barrel file mechanism.

Based on coding guidelines, public APIs should be marked with @includeInBarrelFile annotation.

packages/stream_feeds/lib/src/utils/filter.dart (1)

9-15: Consider narrowing the extension scope.

While the extension is well-implemented with proper null-handling, extending all objects (T extends Object) is quite broad and could lead to API pollution. Consider whether this extension could be more narrowly scoped to specific types that actually need filter matching (e.g., ActivityData, CommentData) rather than all objects.

If the current generic approach is intentional for reusability, this is acceptable. However, more targeted extensions would be clearer and less intrusive to the global namespace.

packages/stream_feeds/lib/src/state/event/on_activity_added.dart (1)

8-71: OnNewActivity contract and default behavior align with requirements

The typedef and defaultOnNewActivity implement the intended “add-if-from-current-user-and-matching-filter” default, giving consumers full control via InsertionAction. As a tiny clean‑up, you could flatten the nested if without changing behavior:

-  if (activity.user.id == currentUserId) {
-    if (activity.matches(query.activityFilter)) {
-      return InsertionAction.addToStart;
-    }
-  }
-
-  return InsertionAction.ignore;
+  if (activity.user.id == currentUserId &&
+      activity.matches(query.activityFilter)) {
+    return InsertionAction.addToStart;
+  }
+
+  return InsertionAction.ignore;
packages/stream_feeds/lib/src/state/feed_state.dart (1)

23-27: onActivityAdded now cleanly supports configurable insertion

The InsertionAction parameter plus insertAt computation and early return on ignore give a simple, extensible way to control placement while preserving the old default. Using upsert(..., insertAt: (_) => insertAt) is a good fit to avoid duplicating list manipulation logic.

If this method is a primary extension point, consider expanding its doc comment to briefly describe how insertionAction influences ordering and how it relates to OnNewActivity, so future maintainers don’t have to chase the call chain.

Also applies to: 111-133

packages/stream_feeds/lib/src/state/event/handler/feed_event_handler.dart (1)

3-18: FeedEventHandler correctly delegates ActivityAdded behavior to OnNewActivity

Wiring onNewActivity into the constructor and using it exclusively for ActivityAddedEvent (while keeping matchesQueryFilter for other events) cleanly hands off insertion decisions to the callback and matches the new tests’ expectations. The sequence of:

  1. compute InsertionAction,
  2. call state.onActivityAdded(...),
  3. optionally enrich via withUpdatedFeedCapabilities(...)
    is straightforward and keeps capability updates orthogonal to insertion policy.

One nuance worth keeping in mind (and which your tests already model) is that custom onNewActivity implementations are now solely responsible for honoring query.activityFilter for added activities; the previous automatic filter check no longer runs for this branch.

Also applies to: 22-34, 48-58

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