import { getDateSeparators } from '../utils/getDateSeparators'; import { getGroupStyles } from '../utils/getGroupStyles'; import { getReadStates } from '../utils/getReadStates'; import { useChatContext } from '../../../contexts/chatContext/ChatContext'; import { ChannelContextValue, useChannelContext, } from '../../../contexts/channelContext/ChannelContext'; import { usePaginatedMessageListContext } from '../../../contexts/paginatedMessageListContext/PaginatedMessageListContext'; import { useThreadContext } from '../../../contexts/threadContext/ThreadContext'; import type { ChannelState, MessageResponse } from 'stream-chat'; import type { DefaultAttachmentType, DefaultChannelType, DefaultCommandType, DefaultEventType, DefaultMessageType, DefaultReactionType, DefaultUserType, UnknownType, } from '../../../types/types'; export type UseMessageListParams = { inverted?: boolean; noGroupByUser?: boolean; threadList?: boolean; }; export type GroupType = 'bottom' | 'middle' | 'single' | 'top'; export type MessagesWithStylesReadByAndDateSeparator< At extends UnknownType = DefaultAttachmentType, Ch extends UnknownType = DefaultChannelType, Co extends string = DefaultCommandType, Me extends UnknownType = DefaultMessageType, Re extends UnknownType = DefaultReactionType, Us extends UnknownType = DefaultUserType, > = MessageResponse & { groupStyles: GroupType[]; readBy: boolean | number; dateSeparator?: Date; }; export type MessageType< At extends UnknownType = DefaultAttachmentType, Ch extends UnknownType = DefaultChannelType, Co extends string = DefaultCommandType, Ev extends UnknownType = DefaultEventType, Me extends UnknownType = DefaultMessageType, Re extends UnknownType = DefaultReactionType, Us extends UnknownType = DefaultUserType, > = | ReturnType['formatMessage']> | MessagesWithStylesReadByAndDateSeparator; // Type guards to check MessageType export const isMessageWithStylesReadByAndDateSeparator = < At extends UnknownType = DefaultAttachmentType, Ch extends UnknownType = DefaultChannelType, Co extends string = DefaultCommandType, Ev extends UnknownType = DefaultEventType, Me extends UnknownType = DefaultMessageType, Re extends UnknownType = DefaultReactionType, Us extends UnknownType = DefaultUserType, >( message: MessageType, ): message is MessagesWithStylesReadByAndDateSeparator => (message as MessagesWithStylesReadByAndDateSeparator).readBy !== undefined; export const useMessageList = < At extends UnknownType = DefaultAttachmentType, Ch extends UnknownType = DefaultChannelType, Co extends string = DefaultCommandType, Ev extends UnknownType = DefaultEventType, Me extends UnknownType = DefaultMessageType, Re extends UnknownType = DefaultReactionType, Us extends UnknownType = DefaultUserType, >( params: UseMessageListParams, ) => { const { inverted, noGroupByUser, threadList } = params; const { client } = useChatContext(); const { hideDateSeparators, maxTimeBetweenGroupedMessages, read } = useChannelContext(); const { messages } = usePaginatedMessageListContext(); const { threadMessages } = useThreadContext(); const messageList = threadList ? threadMessages : messages; const readList: ChannelContextValue['read'] | undefined = threadList ? undefined : read; const dateSeparators = getDateSeparators({ hideDateSeparators, messages: messageList, userId: client.userID, }); const messageGroupStyles = getGroupStyles({ dateSeparators, hideDateSeparators, maxTimeBetweenGroupedMessages, messages: messageList, noGroupByUser, userId: client.userID, }); const readData = getReadStates(client.userID, messageList, readList); const messagesWithStylesReadByAndDateSeparator = messageList .filter((msg) => !msg.deleted_at || msg.user?.id === client.userID) .map((msg) => ({ ...msg, dateSeparator: dateSeparators[msg.id] || undefined, groupStyles: messageGroupStyles[msg.id] || ['single'], readBy: msg.id ? readData[msg.id] || false : false, })); return ( inverted ? messagesWithStylesReadByAndDateSeparator.reverse() : messagesWithStylesReadByAndDateSeparator ) as MessageType[]; };