fix(room): ensure WS connect before subscribe; reactions load for IDB path

- setup() now awaits client.connect() before subscribeRoom and loadMore,
  ensuring the connection is truly open so WS is used for both
- subscribeRoom / reactionListBatch: already WS-first via RoomWsClient.request()
- IDB paths (initial + loadMore) now call thisLoadReactions to batch-fetch
  reactions via WS with HTTP fallback, fixing the missing reactions bug
This commit is contained in:
ZhenYi 2026-04-17 21:44:45 +08:00
parent 50f9cc40fe
commit 44c9f2c772

View File

@ -241,19 +241,19 @@ export function RoomProvider({
if (!activeRoomId || !client) return; if (!activeRoomId || !client) return;
const setup = async () => { const setup = async () => {
if (client.getStatus() !== 'open') { // Ensure WS is open before subscribing. connect() is idempotent — if already
// connecting/open, it returns immediately. While connecting, messages load from
// IDB (instant) and reactions batch-fetch via WS-first request().
await client.connect(); await client.connect();
} // Guard: room may have changed while we were waiting for connect.
// Re-check: activeRoomId may have changed while we were waiting for connect. if (activeRoomIdRef.current !== activeRoomId) return;
// Use activeRoomIdRef to get the *current* room, not the stale closure value. // subscribeRoom is WS-first with HTTP fallback; failure is non-fatal.
const roomId = activeRoomIdRef.current; client.subscribeRoom(activeRoomId).catch(() => {});
if (!roomId) return; // loadMore checks IDB first (no WS needed), then batch-fetches reactions
await client.subscribeRoom(roomId); // via WS with HTTP fallback. Safe to call without awaiting.
// loadMoreRef.current is null on first mount (set later in render order).
// Call loadMore directly to ensure initial message fetch always runs.
loadMore(null); loadMore(null);
}; };
setup(); setup().catch(() => {});
return () => { return () => {
client.unsubscribeRoom(activeRoomId).catch(() => {}); client.unsubscribeRoom(activeRoomId).catch(() => {});