frigate/web/src/hooks
Josh Hawkins 192aba901a
Some checks are pending
CI / AMD64 Build (push) Waiting to run
CI / ARM Build (push) Waiting to run
CI / Jetson Jetpack 6 (push) Waiting to run
CI / AMD64 Extra Build (push) Blocked by required conditions
CI / ARM Extra Build (push) Blocked by required conditions
CI / Synaptics Build (push) Blocked by required conditions
CI / Assemble and push default build (push) Blocked by required conditions
Replace react-tracked and react-use-websocket with useSyncExternalStore (#22386)
* refactor websockets to remove react-tracked

react 19 removed useReducer eager bailout, which broke react-tracked.

react-tracked works by wrapping state in a JavaScript Proxy. When a component reads state.someField, the proxy records that access. On the next state update, it compares only the fields each component actually touched and skips re-renders if those fields are unchanged. Under the hood, this relies on useReducer — and in React 18, useReducer had an "eager bail-out" that short-circuited rendering when the new state was === to the old state. React 19 removed that optimization, so every dispatch now schedules a render regardless, and the proxy comparison runs too late to prevent it.

useSyncExternalStore is a React primitive (added in 18, stable in 19) designed for exactly this pattern: subscribing to an external store:

useSyncExternalStore(
  subscribe,   // (listener) => unsubscribe — called when the store changes
  getSnapshot  // () => value — returns the current value for this subscriber
)

React calls getSnapshot during render and compares the result with Object.is. If the value is the same reference, the component bails out — no re-render. The key difference from react-tracked is that this bail-out is built into React's reconciler, not bolted on via proxy tricks and useReducer.

The per-topic subscription model makes this efficient. Instead of one global store where every subscriber has to check if their fields changed, each useWs("some/topic", ...) call subscribes only to that topic's listener set. When a message arrives for front_door/detect/state, only components subscribed to that exact topic get their listener fired → React calls their getSnapshot → Object.is compares the value → bail-out if unchanged. Components watching back_yard/detect/state are never even notified.

* remove react-tracked and react-use-websocket

* refactor usePolygonStates to use ws topic subscription

* fix TimeAgo refresh interval always returning 1s due to unit mismatch (seconds vs milliseconds)

older events now correctly refresh every minute/hour instead of every second

* simplify

* clean up

* don't resend onconnect

* clean up

* remove patch
2026-03-11 09:02:51 -05:00
..
resize-observer.ts Update frontend to React 19 (#22275) 2026-03-05 07:42:38 -07:00
use-allowed-cameras.ts Debug replay (#22212) 2026-03-04 10:07:34 -06:00
use-api-filter.ts Fixes (#19406) 2025-08-06 22:09:43 -05:00
use-camera-activity.ts Improve motion review and add motion search (#22253) 2026-03-05 17:53:48 -06:00
use-camera-friendly-name.ts Rename nickname to friendly_name (#19782) 2025-08-26 15:29:52 -05:00
use-camera-live-mode.ts Miscellaneous Fixes (0.17 Beta) (#21320) 2025-12-16 22:35:43 -06:00
use-camera-previews.ts Fix fetching of generated preview video (#13498) 2024-09-02 09:18:58 -05:00
use-config-override.ts Full UI configuration (#22151) 2026-02-27 08:55:36 -07:00
use-config-schema.ts Full UI configuration (#22151) 2026-02-27 08:55:36 -07:00
use-contextmenu.ts Face UI cleanup (#17472) 2025-03-31 16:49:56 -05:00
use-date-locale.ts Add languages (#21870) 2026-02-03 13:29:52 -06:00
use-date-utils.ts Improve timezone handling (#18257) 2025-05-15 17:13:32 -05:00
use-deep-memo.ts Add status bar provider (#11066) 2024-04-22 08:20:23 -06:00
use-deferred-stream-metadata.ts Update frontend to React 19 (#22275) 2026-03-05 07:42:38 -07:00
use-doc-domain.ts feat: document locale url (#18409) 2025-05-28 06:10:45 -06:00
use-draggable-element.ts Update frontend to React 19 (#22275) 2026-03-05 07:42:38 -07:00
use-event-segment-utils.ts Review card refactor (#20813) 2025-11-05 09:48:47 -06:00
use-fullscreen.ts Update frontend to React 19 (#22275) 2026-03-05 07:42:38 -07:00
use-global-mutate.ts Regenerate genai tracked object descriptions (#13930) 2024-09-24 08:14:51 -06:00
use-history-back.ts Miscellaneous Fixes (#21063) 2025-11-27 07:58:35 -06:00
use-image-loaded.ts Update frontend to React 19 (#22275) 2026-03-05 07:42:38 -07:00
use-is-admin.ts UI viewer role (#16978) 2025-03-08 10:01:08 -06:00
use-is-custom-role.ts Enhance user roles to limit camera access (#20024) 2025-09-12 05:19:29 -06:00
use-keyboard-listener.tsx Make keyboard shortcuts consistent (#20326) 2025-10-02 07:21:37 -06:00
use-motion-segment-utils.ts No recordings indicator on History timeline (#20715) 2025-10-29 08:39:07 -06:00
use-mouse-listener.ts Implement scroll lock for previews (#10180) 2024-03-01 17:34:41 -07:00
use-navigation.ts Add GenAI Backend Streaming and Chat (#22152) 2026-02-27 09:07:30 -07:00
use-optimistic-state.ts Fix optimistic state (#11556) 2024-05-27 07:59:26 -05:00
use-overlay-state.tsx Frontend fixes (#22294) 2026-03-06 13:41:15 -07:00
use-persistence.ts Ensure that persisted state is kept in sync (#12596) 2024-07-24 11:17:32 -06:00
use-polygon-states.ts Replace react-tracked and react-use-websocket with useSyncExternalStore (#22386) 2026-03-11 09:02:51 -05:00
use-press.ts Explore bulk actions (#15307) 2024-12-02 11:12:55 -07:00
use-session-persistence.ts Persist live view muted/unmuted for session only (#12727) 2024-08-09 06:46:39 -06:00
use-stats.ts Debug replay (#22212) 2026-03-04 10:07:34 -06:00
use-suggestions.ts Add ability to filter search by time range (#13946) 2024-09-25 10:05:40 -06:00
use-tap-utils.ts Scrolling fixes and motion timeline changes (#10295) 2024-03-06 14:35:10 -07:00
use-timeline-utils.ts Update frontend to React 19 (#22275) 2026-03-05 07:42:38 -07:00
use-timeline-zoom.ts Update frontend to React 19 (#22275) 2026-03-05 07:42:38 -07:00
use-user-interaction.ts Update frontend to React 19 (#22275) 2026-03-05 07:42:38 -07:00
use-user-persistence.ts Frontend fixes (#22309) 2026-03-07 06:43:00 -07:00
use-video-dimensions.ts Update frontend to React 19 (#22275) 2026-03-05 07:42:38 -07:00
use-ws-message-buffer.ts Debug replay (#22212) 2026-03-04 10:07:34 -06:00
use-zone-friendly-name.ts Add zones friend name (#20761) 2025-11-07 08:02:06 -06:00