paginate open streams #252

Merged
talksik merged 4 commits from paginate-open-streams into main 2026-06-09 17:43:27 +00:00
talksik commented 2026-06-09 17:11:08 +00:00 (Migrated from github.com)
  • paginate for open and closed streams
  • fix: add platform abstraction for deeplink (#251)
  • cleanup

Summary by CodeRabbit

  • Bug Fixes

    • More reliable deep-link navigation with improved error handling and cleanup.
    • Status filter query parameter is now consistently preserved when switching views.
  • New Features

    • Unified pagination for stream lists, providing more consistent “load more” behavior and smoother loading across filters.
- **paginate for open and closed streams** - **fix: add platform abstraction for deeplink (#251)** - **cleanup** <!-- This is an auto-generated comment: release notes by coderabbit.ai --> ## Summary by CodeRabbit * **Bug Fixes** * More reliable deep-link navigation with improved error handling and cleanup. * Status filter query parameter is now consistently preserved when switching views. * **New Features** * Unified pagination for stream lists, providing more consistent “load more” behavior and smoother loading across filters. <!-- end of auto-generated comment: release notes by coderabbit.ai -->
coderabbitai[bot] commented 2026-06-09 17:11:28 +00:00 (Migrated from github.com)

Review Change Stack

No actionable comments were generated in the recent review. 🎉

ℹ️ Recent review info
⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Pro Plus

Run ID: 4ab5069d-93dd-41b7-9c58-fcb43e4241c4

📥 Commits

Reviewing files that changed from the base of the PR and between 0604b260d2 and 89d78246d3.

📒 Files selected for processing (1)
  • js/desktop/src/App.tsx
🚧 Files skipped from review as they are similar to previous changes (1)
  • js/desktop/src/App.tsx

📝 Walkthrough

Walkthrough

Adds a portable platform.deepLink API (getPending, onNavigate) with Electron and web implementations; App uses it to fetch pending deep links and subscribe to navigation with error logging. Unifies stream pagination to a single limit state for both statuses. NetworkRoot now always writes the status query parameter.

Changes

Platform and feature updates

Layer / File(s) Summary
Platform deepLink interface contract
js/desktop/src/lib/platform/types.ts
Platform interface extended with deepLink capability providing getPending(): Promise<string | null> and onNavigate(callback): () => void.
Platform implementations for deepLink
js/desktop/src/lib/platform/electron.ts, js/desktop/src/lib/platform/web.ts
Electron wires getPending and onNavigate to window.electronDeepLink methods; web implementation stubs getPending to resolve null and onNavigate to return a no-op unsubscribe.
Deep-link navigation listener via platform abstraction
js/desktop/src/App.tsx
DeepLinkNavigationListener now calls platform.deepLink.getPending() and navigates only when a path exists, logs errors via logError, and subscribes via platform.deepLink.onNavigate() with cleanup.
Stream pagination refactoring to unified limit model
js/desktop/src/hooks/use-stream-particles.ts
Replaces closed-tab-specific pagination constants and gating with shared INITIAL_PAGE_SIZE / PAGE_INCREMENT and a single limit state; canLoadMore uses streams.length >= limit and loadMore increments limit.
Network status tab query parameter handling
js/desktop/src/features/network-root.tsx
setStatusTab now always sets the status query parameter (including open) instead of deleting it; two inline layout comments were removed.

Sequence Diagram

sequenceDiagram
  participant App as App (DeepLinkNavigationListener)
  participant Platform as platform.deepLink
  participant Electron as window.electronDeepLink

  App->>Platform: getPending()
  Platform->>Electron: getPending()
  Electron-->>Platform: Promise<string|null>
  Platform-->>App: pending path or null
  alt pending path exists
    App->>App: navigate(pendingPath)
  end
  App->>Platform: onNavigate(callback)
  Platform->>Electron: onNavigate(callback)
  Electron-->>Platform: unsubscribe function
  Platform-->>App: unsubscribe function

Estimated code review effort

🎯 3 (Moderate) | ⏱️ ~20 minutes

Possibly related PRs

  • flowy-live/llink#251: Modifies deep-link flow in App.tsx and related platform API usage; overlaps with the platform.deepLink consumption.
  • flowy-live/llink#246: Adds Electron-side electronDeepLink IPC/preload/main routing that complements the renderer changes in this PR.

Poem

🐰 I hopped between platforms, brave and spry,
Deep-links now whisper where they lie.
Streams stretch longer with a single goal,
Query strings set, the route feels whole.
🥕

🚥 Pre-merge checks | 4 | 1

Failed checks (1 warning)

Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 25.00% which is insufficient. The required threshold is 80.00%. Write docstrings for the functions missing them to satisfy the coverage threshold.
Passed checks (4 passed)
Check name Status Explanation
Description Check Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check Passed The title 'paginate open streams' directly describes the main feature added in this PR—unified pagination for both open and closed streams via the use-stream-particles hook refactor.
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 docstrings
  • Create stacked PR
  • Commit on current branch
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch paginate-open-streams

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

<!-- This is an auto-generated comment: summarize by coderabbit.ai --> <!-- review_stack_entry_start --> [![Review Change Stack](https://storage.googleapis.com/coderabbit_public_assets/review-stack-in-coderabbit-ui.svg)](https://app.coderabbit.ai/change-stack/flowy-live/llink/pull/252?utm_source=github_walkthrough&utm_medium=github&utm_campaign=change_stack) <!-- review_stack_entry_end --> No actionable comments were generated in the recent review. 🎉 <details> <summary>ℹ️ Recent review info</summary> <details> <summary>⚙️ Run configuration</summary> **Configuration used**: defaults **Review profile**: CHILL **Plan**: Pro Plus **Run ID**: `4ab5069d-93dd-41b7-9c58-fcb43e4241c4` </details> <details> <summary>📥 Commits</summary> Reviewing files that changed from the base of the PR and between 0604b260d21f5b9dc539e3400d7aceb97e8940e7 and 89d78246d3cb7d515aefecfff3c895915d2885b9. </details> <details> <summary>📒 Files selected for processing (1)</summary> * `js/desktop/src/App.tsx` </details> <details> <summary>🚧 Files skipped from review as they are similar to previous changes (1)</summary> * js/desktop/src/App.tsx </details> </details> --- <!-- walkthrough_start --> <details> <summary>📝 Walkthrough</summary> ## Walkthrough Adds a portable platform.deepLink API (getPending, onNavigate) with Electron and web implementations; App uses it to fetch pending deep links and subscribe to navigation with error logging. Unifies stream pagination to a single limit state for both statuses. NetworkRoot now always writes the `status` query parameter. ## Changes **Platform and feature updates** | Layer / File(s) | Summary | |---|---| | **Platform deepLink interface contract** <br> `js/desktop/src/lib/platform/types.ts` | `Platform` interface extended with `deepLink` capability providing `getPending(): Promise<string \| null>` and `onNavigate(callback): () => void`. | | **Platform implementations for deepLink** <br> `js/desktop/src/lib/platform/electron.ts`, `js/desktop/src/lib/platform/web.ts` | Electron wires `getPending` and `onNavigate` to `window.electronDeepLink` methods; web implementation stubs `getPending` to resolve `null` and `onNavigate` to return a no-op unsubscribe. | | **Deep-link navigation listener via platform abstraction** <br> `js/desktop/src/App.tsx` | `DeepLinkNavigationListener` now calls `platform.deepLink.getPending()` and navigates only when a path exists, logs errors via `logError`, and subscribes via `platform.deepLink.onNavigate()` with cleanup. | | **Stream pagination refactoring to unified limit model** <br> `js/desktop/src/hooks/use-stream-particles.ts` | Replaces closed-tab-specific pagination constants and gating with shared `INITIAL_PAGE_SIZE` / `PAGE_INCREMENT` and a single `limit` state; `canLoadMore` uses `streams.length >= limit` and `loadMore` increments `limit`. | | **Network status tab query parameter handling** <br> `js/desktop/src/features/network-root.tsx` | `setStatusTab` now always sets the `status` query parameter (including `open`) instead of deleting it; two inline layout comments were removed. | ## Sequence Diagram ```mermaid sequenceDiagram participant App as App (DeepLinkNavigationListener) participant Platform as platform.deepLink participant Electron as window.electronDeepLink App->>Platform: getPending() Platform->>Electron: getPending() Electron-->>Platform: Promise<string|null> Platform-->>App: pending path or null alt pending path exists App->>App: navigate(pendingPath) end App->>Platform: onNavigate(callback) Platform->>Electron: onNavigate(callback) Electron-->>Platform: unsubscribe function Platform-->>App: unsubscribe function ``` ## Estimated code review effort 🎯 3 (Moderate) | ⏱️ ~20 minutes ## Possibly related PRs - [flowy-live/llink#251](https://github.com/flowy-live/llink/pull/251): Modifies deep-link flow in `App.tsx` and related platform API usage; overlaps with the platform.deepLink consumption. - [flowy-live/llink#246](https://github.com/flowy-live/llink/pull/246): Adds Electron-side `electronDeepLink` IPC/preload/main routing that complements the renderer changes in this PR. ## Poem > 🐰 I hopped between platforms, brave and spry, > Deep-links now whisper where they lie. > Streams stretch longer with a single goal, > Query strings set, the route feels whole. > 🥕✨ </details> <!-- walkthrough_end --> <!-- pre_merge_checks_walkthrough_start --> <details> <summary>🚥 Pre-merge checks | ✅ 4 | ❌ 1</summary> ### ❌ Failed checks (1 warning) | Check name | Status | Explanation | Resolution | | :----------------: | :--------- | :------------------------------------------------------------------------------------ | :--------------------------------------------------------------------------------- | | Docstring Coverage | ⚠️ Warning | Docstring coverage is 25.00% which is insufficient. The required threshold is 80.00%. | Write docstrings for the functions missing them to satisfy the coverage threshold. | <details> <summary>✅ Passed checks (4 passed)</summary> | Check name | Status | Explanation | | :------------------------: | :------- | :------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | | Description Check | ✅ Passed | Check skipped - CodeRabbit’s high-level summary is enabled. | | Title check | ✅ Passed | The title 'paginate open streams' directly describes the main feature added in this PR—unified pagination for both open and closed streams via the use-stream-particles hook refactor. | | 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. | </details> <sub>✏️ Tip: You can configure your own custom pre-merge checks in the settings.</sub> </details> <!-- pre_merge_checks_walkthrough_end --> <!-- finishing_touch_checkbox_start --> <details> <summary>✨ Finishing Touches</summary> <details> <summary>📝 Generate docstrings</summary> - [ ] <!-- {"checkboxId": "7962f53c-55bc-4827-bfbf-6a18da830691"} --> Create stacked PR - [ ] <!-- {"checkboxId": "3e1879ae-f29b-4d0d-8e06-d12b7ba33d98"} --> Commit on current branch </details> <details> <summary>🧪 Generate unit tests (beta)</summary> - [ ] <!-- {"checkboxId": "f47ac10b-58cc-4372-a567-0e02b2c3d479", "radioGroupId": "utg-output-choice-group-unknown_comment_id"} --> Create PR with unit tests - [ ] <!-- {"checkboxId": "6ba7b810-9dad-11d1-80b4-00c04fd430c8", "radioGroupId": "utg-output-choice-group-unknown_comment_id"} --> Commit unit tests in branch `paginate-open-streams` </details> </details> <!-- finishing_touch_checkbox_end --> <!-- tips_start --> --- <sub>Comment `@coderabbitai help` to get the list of available commands and usage tips.</sub> <!-- tips_end --> <!-- internal state start --> <!-- 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 --> <!-- internal state end -->
coderabbitai[bot] (Migrated from github.com) reviewed 2026-06-09 17:15:44 +00:00
coderabbitai[bot] (Migrated from github.com) left a comment

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 `@js/desktop/src/App.tsx`:
- Around line 59-66: The call to logError inside the deep link handler
(platform.deepLink.getPending().catch(...)) is missing its import and will fail;
add an import for logError from the desktop errors module (import { logError }
from '`@/lib/errors`';) at the top of js/desktop/src/App.tsx so the catch handler
inside the DeepLinkNavigationListener / platform.deepLink.getPending() block can
call logError correctly.

In `@js/desktop/src/hooks/use-stream-particles.ts`:
- Line 53: The pagination limit (state variables limit and setLimit initialized
from INITIAL_PAGE_SIZE in use-stream-particles.ts) isn't reset when the
filter/status changes, causing over-fetching; add an effect that watches the
status value and calls setLimit(INITIAL_PAGE_SIZE) whenever status changes so
pagination starts fresh on tab switches (keep existing useState for limit, just
add a useEffect targeting status to reset it).
🪄 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: defaults

Review profile: CHILL

Plan: Pro Plus

Run ID: 83437b28-ff74-41ed-8b53-30374668f0be

📥 Commits

Reviewing files that changed from the base of the PR and between f38835ceee and 0604b260d2.

📒 Files selected for processing (6)
  • js/desktop/src/App.tsx
  • js/desktop/src/features/network-root.tsx
  • js/desktop/src/hooks/use-stream-particles.ts
  • js/desktop/src/lib/platform/electron.ts
  • js/desktop/src/lib/platform/types.ts
  • js/desktop/src/lib/platform/web.ts
**Actionable comments posted: 2** <details> <summary>🤖 Prompt for all review comments with AI agents</summary> ``` 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 `@js/desktop/src/App.tsx`: - Around line 59-66: The call to logError inside the deep link handler (platform.deepLink.getPending().catch(...)) is missing its import and will fail; add an import for logError from the desktop errors module (import { logError } from '`@/lib/errors`';) at the top of js/desktop/src/App.tsx so the catch handler inside the DeepLinkNavigationListener / platform.deepLink.getPending() block can call logError correctly. In `@js/desktop/src/hooks/use-stream-particles.ts`: - Line 53: The pagination limit (state variables limit and setLimit initialized from INITIAL_PAGE_SIZE in use-stream-particles.ts) isn't reset when the filter/status changes, causing over-fetching; add an effect that watches the status value and calls setLimit(INITIAL_PAGE_SIZE) whenever status changes so pagination starts fresh on tab switches (keep existing useState for limit, just add a useEffect targeting status to reset it). ``` </details> <details> <summary>🪄 Autofix (Beta)</summary> Fix all unresolved CodeRabbit comments on this PR: - [ ] <!-- {"checkboxId": "4b0d0e0a-96d7-4f10-b296-3a18ea78f0b9"} --> Push a commit to this branch (recommended) - [ ] <!-- {"checkboxId": "ff5b1114-7d8c-49e6-8ac1-43f82af23a33"} --> Create a new PR with the fixes </details> --- <details> <summary>ℹ️ Review info</summary> <details> <summary>⚙️ Run configuration</summary> **Configuration used**: defaults **Review profile**: CHILL **Plan**: Pro Plus **Run ID**: `83437b28-ff74-41ed-8b53-30374668f0be` </details> <details> <summary>📥 Commits</summary> Reviewing files that changed from the base of the PR and between f38835ceeefe5bd1afebe4d063140b0cd4807142 and 0604b260d21f5b9dc539e3400d7aceb97e8940e7. </details> <details> <summary>📒 Files selected for processing (6)</summary> * `js/desktop/src/App.tsx` * `js/desktop/src/features/network-root.tsx` * `js/desktop/src/hooks/use-stream-particles.ts` * `js/desktop/src/lib/platform/electron.ts` * `js/desktop/src/lib/platform/types.ts` * `js/desktop/src/lib/platform/web.ts` </details> </details> <!-- This is an auto-generated comment by CodeRabbit for review status -->
coderabbitai[bot] (Migrated from github.com) commented 2026-06-09 17:15:43 +00:00

⚠️ Potential issue | 🔴 Critical

🧩 Analysis chain

🏁 Script executed:

#!/bin/bash
# Description: Find logError definition and check if it's globally available

# Search for logError exports
echo "=== Searching for logError exports ==="
rg -n --type=ts --type=tsx 'export.*logError' js/

# Search for logError declarations
echo -e "\n=== Searching for logError declarations ==="
rg -n --type=ts --type=tsx 'function logError|const logError|let logError' js/

# Check if logError is used elsewhere in the codebase
echo -e "\n=== Other usages of logError ==="
rg -n --type=ts --type=tsx 'logError\(' js/ -A1 -B1

Repository: flowy-live/llink

Length of output: 280


🏁 Script executed:

#!/bin/bash
set -euo pipefail

echo "=== Inspect js/desktop/src/App.tsx (imports + deepLink catch) ==="
sed -n '1,120p' js/desktop/src/App.tsx | nl -ba | sed -n '1,120p'

echo -e "\n=== Find logError usage in App.tsx ==="
rg -n "logError\(" js/desktop/src/App.tsx || true

echo -e "\n=== Find logError definitions across js/ ==="
rg -n "export\s+(function|const|let)\s+logError|function\s+logError|const\s+logError|let\s+logError" js/ || true

echo -e "\n=== Find logError imports across js/ ==="
rg -n "import\s+\{[^}]*\blogError\b[^}]*\}\s+from|from\s+['\"][^'\"]+['\"];\s*$" js/ || true

echo -e "\n=== Find all logError(...) callsites across js/ ==="
rg -n "logError\(" js/ -S || true

Repository: flowy-live/llink

Length of output: 187


🏁 Script executed:

#!/bin/bash
set -euo pipefail

echo "=== Check target file exists ==="
ls -la js/desktop/src/App.tsx || true

echo -e "\n=== App.tsx imports + deepLink block (line-numbered) ==="
# Use cat -n since nl isn't available
cat -n js/desktop/src/App.tsx | sed -n '1,140p'

echo -e "\n=== Find logError usage in App.tsx ==="
rg -n "logError\s*\(" js/desktop/src/App.tsx || true

echo -e "\n=== Find logError imports in App.tsx ==="
rg -n "import\s+\{[^}]*\blogError\b[^}]*\}\s+from" js/desktop/src/App.tsx || true

echo -e "\n=== Find logError definitions/exports across js/ ==="
rg -n "export\s+(function|const|let)\s+logError|function\s+logError|const\s+logError|let\s+logError" js/ || true

echo -e "\n=== Find all logError(...) callsites across js/ ==="
rg -n "logError\s*\(" js/ || true

Repository: flowy-live/llink

Length of output: 9928


🏁 Script executed:

#!/bin/bash
set -euo pipefail

echo "=== Inspect js/desktop/src/lib/errors.ts around logError ==="
sed -n '1,140p' js/desktop/src/lib/errors.ts | cat -n

echo -e "\n=== Check for barrel exports (desktop src/lib index) ==="
for f in js/desktop/src/lib/index.ts js/desktop/src/lib/index.tsx js/desktop/src/lib.ts js/desktop/src/lib/index.js js/desktop/src/lib/index.ts; do
  if [ -f "$f" ]; then
    echo "--- $f ---"
    sed -n '1,200p' "$f" | cat -n
  fi
done

echo -e "\n=== Search for re-export of logError in desktop lib ==="
rg -n "export\s+\*\s+from|export\s+\{[^}]*\blogError\b[^}]*\}" js/desktop/src/lib/ || true

echo -e "\n=== Search for logError exports outside lib/errors.ts (desktop) ==="
rg -n "export\s+function\s+logError|export\s+\{\s*logError\s*\}" js/desktop/src/ || true

Repository: flowy-live/llink

Length of output: 4013


🏁 Script executed:

#!/bin/bash
set -euo pipefail

echo -e "=== logError import usages in desktop ==="
rg -n "import\s+\{[^}]*\blogError\b[^}]*\}\s+from" js/desktop/src || true

echo -e "\n=== Possible global declarations ==="
rg -n "declare\s+(const|function)\s+logError|globalThis\.logError|window\.logError" js/ || true

echo -e "\n=== Does App.tsx import '`@/lib/errors`' or similar? ==="
rg -n "from\s+['\"]`@/lib/`(errors|error|logger)['\"]" js/desktop/src/App.tsx || true

echo -e "\n=== Any re-export barrel that could make logError available without local import? ==="
rg -n "export\s+\*\s+from\s+['\"][^'\"]*errors['\"]|export\s+\{\s*logError\s*\}" js/desktop/src/lib js/desktop/src || true

Repository: flowy-live/llink

Length of output: 942


🏁 Script executed:

#!/bin/bash
set -euo pipefail
rg -n "declare\s+(var|const|let|function)\s+logError|globalThis\[['\"]logError['\"]\]|globalThis\.(logError)|window\[['\"]logError['\"]\]|window\.(logError)" js/ || true

Repository: flowy-live/llink

Length of output: 42


🏁 Script executed:

#!/bin/bash
set -euo pipefail
rg -n "declare\s+(var|const|let|function)\s+logError|globalThis\.(logError)|window\.(logError)|global\s+logError|logError:\s*\(.*\)\s*=>" . || true

Repository: flowy-live/llink

Length of output: 42


Fix missing logError import in DeepLinkNavigationListener

platform.deepLink
  .getPending()
  .then((path) => {
    if (path) navigate(path);
  })
  .catch((err) => {
    logError(err, { scope: 'deepLink.getPending' });
  });

js/desktop/src/App.tsx (line 65) calls logError, but the file has no import. logError is exported from @/lib/errors (js/desktop/src/lib/errors.ts), and other desktop files import it from there—so this call will fail at runtime (and/or typecheck).

Add:

  • import { logError } from '@/lib/errors';
🤖 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 `@js/desktop/src/App.tsx` around lines 59 - 66, The call to logError inside the
deep link handler (platform.deepLink.getPending().catch(...)) is missing its
import and will fail; add an import for logError from the desktop errors module
(import { logError } from '`@/lib/errors`';) at the top of js/desktop/src/App.tsx
so the catch handler inside the DeepLinkNavigationListener /
platform.deepLink.getPending() block can call logError correctly.

Addressed in commit 89d7824

_⚠️ Potential issue_ | _🔴 Critical_ <details> <summary>🧩 Analysis chain</summary> 🏁 Script executed: ```shell #!/bin/bash # Description: Find logError definition and check if it's globally available # Search for logError exports echo "=== Searching for logError exports ===" rg -n --type=ts --type=tsx 'export.*logError' js/ # Search for logError declarations echo -e "\n=== Searching for logError declarations ===" rg -n --type=ts --type=tsx 'function logError|const logError|let logError' js/ # Check if logError is used elsewhere in the codebase echo -e "\n=== Other usages of logError ===" rg -n --type=ts --type=tsx 'logError\(' js/ -A1 -B1 ``` Repository: flowy-live/llink Length of output: 280 --- 🏁 Script executed: ```shell #!/bin/bash set -euo pipefail echo "=== Inspect js/desktop/src/App.tsx (imports + deepLink catch) ===" sed -n '1,120p' js/desktop/src/App.tsx | nl -ba | sed -n '1,120p' echo -e "\n=== Find logError usage in App.tsx ===" rg -n "logError\(" js/desktop/src/App.tsx || true echo -e "\n=== Find logError definitions across js/ ===" rg -n "export\s+(function|const|let)\s+logError|function\s+logError|const\s+logError|let\s+logError" js/ || true echo -e "\n=== Find logError imports across js/ ===" rg -n "import\s+\{[^}]*\blogError\b[^}]*\}\s+from|from\s+['\"][^'\"]+['\"];\s*$" js/ || true echo -e "\n=== Find all logError(...) callsites across js/ ===" rg -n "logError\(" js/ -S || true ``` Repository: flowy-live/llink Length of output: 187 --- 🏁 Script executed: ```shell #!/bin/bash set -euo pipefail echo "=== Check target file exists ===" ls -la js/desktop/src/App.tsx || true echo -e "\n=== App.tsx imports + deepLink block (line-numbered) ===" # Use cat -n since nl isn't available cat -n js/desktop/src/App.tsx | sed -n '1,140p' echo -e "\n=== Find logError usage in App.tsx ===" rg -n "logError\s*\(" js/desktop/src/App.tsx || true echo -e "\n=== Find logError imports in App.tsx ===" rg -n "import\s+\{[^}]*\blogError\b[^}]*\}\s+from" js/desktop/src/App.tsx || true echo -e "\n=== Find logError definitions/exports across js/ ===" rg -n "export\s+(function|const|let)\s+logError|function\s+logError|const\s+logError|let\s+logError" js/ || true echo -e "\n=== Find all logError(...) callsites across js/ ===" rg -n "logError\s*\(" js/ || true ``` Repository: flowy-live/llink Length of output: 9928 --- 🏁 Script executed: ```shell #!/bin/bash set -euo pipefail echo "=== Inspect js/desktop/src/lib/errors.ts around logError ===" sed -n '1,140p' js/desktop/src/lib/errors.ts | cat -n echo -e "\n=== Check for barrel exports (desktop src/lib index) ===" for f in js/desktop/src/lib/index.ts js/desktop/src/lib/index.tsx js/desktop/src/lib.ts js/desktop/src/lib/index.js js/desktop/src/lib/index.ts; do if [ -f "$f" ]; then echo "--- $f ---" sed -n '1,200p' "$f" | cat -n fi done echo -e "\n=== Search for re-export of logError in desktop lib ===" rg -n "export\s+\*\s+from|export\s+\{[^}]*\blogError\b[^}]*\}" js/desktop/src/lib/ || true echo -e "\n=== Search for logError exports outside lib/errors.ts (desktop) ===" rg -n "export\s+function\s+logError|export\s+\{\s*logError\s*\}" js/desktop/src/ || true ``` Repository: flowy-live/llink Length of output: 4013 --- 🏁 Script executed: ```shell #!/bin/bash set -euo pipefail echo -e "=== logError import usages in desktop ===" rg -n "import\s+\{[^}]*\blogError\b[^}]*\}\s+from" js/desktop/src || true echo -e "\n=== Possible global declarations ===" rg -n "declare\s+(const|function)\s+logError|globalThis\.logError|window\.logError" js/ || true echo -e "\n=== Does App.tsx import '`@/lib/errors`' or similar? ===" rg -n "from\s+['\"]`@/lib/`(errors|error|logger)['\"]" js/desktop/src/App.tsx || true echo -e "\n=== Any re-export barrel that could make logError available without local import? ===" rg -n "export\s+\*\s+from\s+['\"][^'\"]*errors['\"]|export\s+\{\s*logError\s*\}" js/desktop/src/lib js/desktop/src || true ``` Repository: flowy-live/llink Length of output: 942 --- 🏁 Script executed: ```shell #!/bin/bash set -euo pipefail rg -n "declare\s+(var|const|let|function)\s+logError|globalThis\[['\"]logError['\"]\]|globalThis\.(logError)|window\[['\"]logError['\"]\]|window\.(logError)" js/ || true ``` Repository: flowy-live/llink Length of output: 42 --- 🏁 Script executed: ```shell #!/bin/bash set -euo pipefail rg -n "declare\s+(var|const|let|function)\s+logError|globalThis\.(logError)|window\.(logError)|global\s+logError|logError:\s*\(.*\)\s*=>" . || true ``` Repository: flowy-live/llink Length of output: 42 --- </details> **Fix missing `logError` import in `DeepLinkNavigationListener`** ```ts platform.deepLink .getPending() .then((path) => { if (path) navigate(path); }) .catch((err) => { logError(err, { scope: 'deepLink.getPending' }); }); ``` `js/desktop/src/App.tsx` (line 65) calls `logError`, but the file has no import. `logError` is exported from `@/lib/errors` (`js/desktop/src/lib/errors.ts`), and other desktop files import it from there—so this call will fail at runtime (and/or typecheck). Add: - `import { logError } from '`@/lib/errors`';` <details> <summary>🤖 Prompt for AI Agents</summary> ``` Verify each finding against current code. Fix only still-valid issues, skip the rest with a brief reason, keep changes minimal, and validate. In `@js/desktop/src/App.tsx` around lines 59 - 66, The call to logError inside the deep link handler (platform.deepLink.getPending().catch(...)) is missing its import and will fail; add an import for logError from the desktop errors module (import { logError } from '`@/lib/errors`';) at the top of js/desktop/src/App.tsx so the catch handler inside the DeepLinkNavigationListener / platform.deepLink.getPending() block can call logError correctly. ``` </details> <!-- fingerprinting:phantom:poseidon:puma --> <!-- cr-comment:v1:c9a314090a6b41810a7fe1e2 --> <!-- This is an auto-generated comment by CodeRabbit --> ✅ Addressed in commit 89d7824
coderabbitai[bot] (Migrated from github.com) commented 2026-06-09 17:15:43 +00:00

⚠️ Potential issue | 🟠 Major | Quick win

Pagination limit does not reset when status changes.

When the user switches between the "open" and "closed" tabs, the limit state persists. If a user loads several pages of closed streams (e.g., limit reaches 60), then switches to the open tab, the hook will immediately query for 60 open streams instead of starting fresh at 12. This causes unnecessary over-fetching and changes the previous behavior that reset pagination on tab switch.

🛠️ Proposed fix to reset limit on status change
+import { useCallback, useEffect, useMemo, useState } from 'react';
-import { useCallback, useMemo, useState } from 'react';

Then add a reset effect after the useState:

  const [limit, setLimit] = useState(INITIAL_PAGE_SIZE);

+  // Reset pagination when switching between open/closed tabs
+  useEffect(() => {
+    setLimit(INITIAL_PAGE_SIZE);
+  }, [status]);
+
📝 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.

  const [limit, setLimit] = useState(INITIAL_PAGE_SIZE);

  // Reset pagination when switching between open/closed tabs
  useEffect(() => {
    setLimit(INITIAL_PAGE_SIZE);
  }, [status]);
import { useCallback, useEffect, useMemo, useState } from 'react';
🤖 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 `@js/desktop/src/hooks/use-stream-particles.ts` at line 53, The pagination
limit (state variables limit and setLimit initialized from INITIAL_PAGE_SIZE in
use-stream-particles.ts) isn't reset when the filter/status changes, causing
over-fetching; add an effect that watches the status value and calls
setLimit(INITIAL_PAGE_SIZE) whenever status changes so pagination starts fresh
on tab switches (keep existing useState for limit, just add a useEffect
targeting status to reset it).
_⚠️ Potential issue_ | _🟠 Major_ | _⚡ Quick win_ **Pagination `limit` does not reset when `status` changes.** When the user switches between the "open" and "closed" tabs, the `limit` state persists. If a user loads several pages of closed streams (e.g., limit reaches 60), then switches to the open tab, the hook will immediately query for 60 open streams instead of starting fresh at 12. This causes unnecessary over-fetching and changes the previous behavior that reset pagination on tab switch. <details> <summary>🛠️ Proposed fix to reset limit on status change</summary> ```diff +import { useCallback, useEffect, useMemo, useState } from 'react'; -import { useCallback, useMemo, useState } from 'react'; ``` Then add a reset effect after the `useState`: ```diff const [limit, setLimit] = useState(INITIAL_PAGE_SIZE); + // Reset pagination when switching between open/closed tabs + useEffect(() => { + setLimit(INITIAL_PAGE_SIZE); + }, [status]); + ``` </details> <!-- suggestion_start --> <details> <summary>📝 Committable suggestion</summary> > ‼️ **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. ```suggestion const [limit, setLimit] = useState(INITIAL_PAGE_SIZE); // Reset pagination when switching between open/closed tabs useEffect(() => { setLimit(INITIAL_PAGE_SIZE); }, [status]); ``` ```suggestion import { useCallback, useEffect, useMemo, useState } from 'react'; ``` </details> <!-- suggestion_end --> <details> <summary>🤖 Prompt for AI Agents</summary> ``` Verify each finding against current code. Fix only still-valid issues, skip the rest with a brief reason, keep changes minimal, and validate. In `@js/desktop/src/hooks/use-stream-particles.ts` at line 53, The pagination limit (state variables limit and setLimit initialized from INITIAL_PAGE_SIZE in use-stream-particles.ts) isn't reset when the filter/status changes, causing over-fetching; add an effect that watches the status value and calls setLimit(INITIAL_PAGE_SIZE) whenever status changes so pagination starts fresh on tab switches (keep existing useState for limit, just add a useEffect targeting status to reset it). ``` </details> <!-- fingerprinting:phantom:medusa:ocelot --> <!-- cr-comment:v1:210709595e4896f04c075821 --> <!-- This is an auto-generated comment by CodeRabbit -->
Sign in to join this conversation.