Skip to content

refactor: sync notifications with BroadcastChannel - #3552

Open
Antreesy wants to merge 2 commits into
masterfrom
perf/noid/tab-sync-web-locks
Open

Antreesy wants to merge 2 commits into
masterfrom
perf/noid/tab-sync-web-locks

Conversation

@Antreesy

Copy link
Copy Markdown
Collaborator

Fixes notifications data storage and exchanges between multiple tabs:

  • HTTPS only:
    • Web Locks API defines a leader tab, that does the interval fetching;
    • Data is shared with BroadcastChannel, any tab can do it;
    • BrowserStorage no longer holds plain notifications and related logic, keys cleaned up on logout and page refresh (TODO remove by NC 37)
    • Only the leader polls, fetches on notify_push, registers web push, and shows browser notifications
    • A new follower 'request' from leader tab the last actual data
      Webpush only:
    • All tabs listen to the service worker, because it sends a push to any tab (last activated, might not be a leader, still broadcasts)

Known issues:

  • HTTP only: every tab is the leader and polls separately. Acceptable load in insecure context;
  • Polling only: not visible leader tab with interval can be throttled by browser;
  • Actions: notifications dismiss sends GET request to update self and other tabs;
  • Polling interval might not be aligned between tabs. Not part of this PR, but a bew value can also be broadcasted
  • No vitest to write tests

🤖 AI (if applicable)

  • The content of this PR was partly or fully generated using AI (ClaudeCode:claude-opus-5-5)

Assisted-by: ClaudeCode:claude-opus-5-5
Signed-off-by: Maksim Sukharev <antreesy.web@gmail.com>
Only one tab per browser polls, handles notify_push and registers web push.
Other tabs receive the data over a BroadcastChannel and do not fetch on load.
Without Web Locks (insecure context) every tab polls on its own.
Notification data is no longer cached in localStorage.

Assisted-by: ClaudeCode:claude-opus-5-5
Signed-off-by: Maksim Sukharev <antreesy.web@gmail.com>
Comment thread src/NotificationsApp.vue
handleNetworkOnline() {
this._fetch()
if (this.isLeader) {
this._fetch()

@Antreesy Antreesy Oct 30, 2026 •

Copy link
Copy Markdown
Collaborator Author

Choose a reason for hiding this comment

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

could steal the leadership

Comment thread src/NotificationsApp.vue
@@ -355,7 +364,6 @@ export default {
})
}

Copy link
Copy Markdown
Collaborator Author

Choose a reason for hiding this comment

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

could steal the leadership

onData(event.data)
}
navigator.locks.request(name, () => {
isLeader.value = true

@Antreesy Antreesy Oct 30, 2026 •

Copy link
Copy Markdown
Collaborator Author

Choose a reason for hiding this comment

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

  • should generate a console.debug
  • should handle the stealing, downgrade leadership and request again
  • should broadcast polling interval between all windows

Comment thread src/main.js
import './styles/styles.scss'
import '@nextcloud/dialogs/style.css'

// TODO: remove in v37. Notifications were cached in the browser storage before v36

Copy link
Copy Markdown
Collaborator Author

Choose a reason for hiding this comment

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

v39

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

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant