feat: add store methods for deleted user cleanup

Add removeRequestsForUser (socialStore), removeUser (discoverStore), and
clearTypingForUser (chatStore) to support isDeleted cleanup in the
user_updated WS handler.
This commit is contained in:
Jannis Braun
2026-04-03 04:22:03 +02:00
parent 9d4b759cb4
commit 0f381c75db
3 changed files with 32 additions and 0 deletions
+16
View File
@@ -64,6 +64,7 @@ interface ChatState {
onMarkUnread: (channelId: string, messageId: string) => void; onMarkUnread: (channelId: string, messageId: string) => void;
removeChannelStates: (channelIds: Set<string>) => void; removeChannelStates: (channelIds: Set<string>) => void;
updateUserInMessages: (user: { id: string; [key: string]: any }) => void; updateUserInMessages: (user: { id: string; [key: string]: any }) => void;
clearTypingForUser: (userId: string) => void;
} }
/** Find which channel a message belongs to by scanning the message cache. */ /** Find which channel a message belongs to by scanning the message cache. */
@@ -727,4 +728,19 @@ export const useChatStore = create<ChatState>((set, get) => ({
return changed ? { messages: newMessages } : {}; return changed ? { messages: newMessages } : {};
}); });
}, },
clearTypingForUser: (userId: string) => {
set((state) => {
const newTyping = new Map(state.typingUsers);
let changed = false;
for (const [channelId, users] of newTyping) {
const filtered = users.filter(t => t.userId !== userId);
if (filtered.length !== users.length) {
newTyping.set(channelId, filtered);
changed = true;
}
}
return changed ? { typingUsers: newTyping } : state;
});
},
})); }));
+8
View File
@@ -20,6 +20,7 @@ interface DiscoverState {
fetchUsers: (query?: string) => Promise<void>; fetchUsers: (query?: string) => Promise<void>;
setSearchQuery: (q: string) => void; setSearchQuery: (q: string) => void;
updateRelationship: (userId: string, origin: string, relationship: DiscoverUser['relationship'], requestId?: string) => void; updateRelationship: (userId: string, origin: string, relationship: DiscoverUser['relationship'], requestId?: string) => void;
removeUser: (userId: string) => void;
reset: () => void; reset: () => void;
} }
@@ -111,6 +112,13 @@ export const useDiscoverStore = create<DiscoverState>((set) => ({
})); }));
}, },
removeUser: (userId: string) => {
set((state) => ({
users: state.users.filter(u => u.id !== userId),
total: Math.max(0, state.total - state.users.filter(u => u.id === userId).length),
}));
},
reset: () => set({ reset: () => set({
users: [], users: [],
searchQuery: '', searchQuery: '',
+8
View File
@@ -56,6 +56,7 @@ interface SocialState {
updateFriendProfile: (user: User) => void; updateFriendProfile: (user: User) => void;
removeFriendLocally: (userId: string, origin: string) => void; removeFriendLocally: (userId: string, origin: string) => void;
removeRequestById: (requestId: string, origin: string) => void; removeRequestById: (requestId: string, origin: string) => void;
removeRequestsForUser: (userId: string) => void;
reset: () => void; reset: () => void;
} }
@@ -326,6 +327,13 @@ export const useSocialStore = create<SocialState>((set, get) => ({
})); }));
}, },
// Called when a user is deleted — remove all pending requests involving them
removeRequestsForUser: (userId: string) => {
set((state) => ({
requests: state.requests.filter(r => r.fromId !== userId && r.toId !== userId),
}));
},
// Called from WS handler on presence_update to keep friend status live // Called from WS handler on presence_update to keep friend status live
updateFriendPresence: (userId: string, status: string) => { updateFriendPresence: (userId: string, status: string) => {
set((state) => ({ set((state) => ({