///
import React from "react";
import { ReactNode, FC, Component, ReactElement } from "react";
import { UUIDMetadataObject, ChannelMetadataObject, ObjectCustom, FetchMessagesResponse, BaseObjectsEvent, FileEvent, MessageActionEvent, PresenceEvent, SignalEvent, StatusEvent, FetchMessagesParameters, HereNowParameters, HereNowResponse, GetUUIDMetadataParameters, SubscribeParameters, GetAllMetadataParameters, GetChannelMembersParameters, GetMembershipsParametersv2, UriFileInput } from "pubnub";
import { ImageStyle, TextStyle, ViewStyle, Animated, TextInputProps, NativeScrollEvent, NativeSyntheticEvent } from "react-native";
type Themes = "light" | "dark" | "support" | "support-dark" | "event" | "event-dark";
type ChannelEntity = ChannelMetadataObject;
type UserEntity = UUIDMetadataObject;
type ChannelEntityWithMembership = ChannelEntity & {
membership?: ObjectCustom;
};
type UserEntityWithMembership = UserEntity & {
membership?: ObjectCustom;
};
interface MessageEnvelope {
channel?: string;
message: MessagePayload | FilePayload;
timetoken: string | number;
messageType?: string | number;
publisher?: string;
uuid?: string;
meta?: {
[key: string]: unknown;
};
actions?: {
[type: string]: {
[value: string]: Array<{
uuid: string;
actionTimetoken: string | number;
}>;
};
};
}
interface MessagePayload {
id: string;
type?: string;
text?: string;
sender?: UUIDMetadataObject;
attachments?: Array;
createdAt?: string;
[key: string]: unknown;
}
interface FilePayload {
message?: MessagePayload;
file: FileAttachment;
}
interface FileAttachment {
id: string;
name: string;
url?: string;
}
interface ImageAttachment {
type: "image";
image: {
source: string;
};
}
interface LinkAttachment {
type: "link";
description?: string;
title?: string;
icon?: {
source: string;
};
image: {
source: string;
};
provider?: {
name: string;
url: string;
};
}
interface RetryOptions {
maxRetries: number;
timeout: number;
exponentialFactor: number;
}
interface ProperFetchMessagesResponse extends FetchMessagesResponse {
error: boolean;
error_message: string;
status: number;
more?: {
max: number;
start: string;
url: string;
};
}
interface CommonChannelListProps {
children?: ReactNode;
/** Option to pass a list of channels, including metadata, to render on the list. */
channels: ChannelEntity[] | string[];
/** Channels are sorted alphabetically by default, you can override that by providing a sorter function */
sort?: (a: ChannelEntity, b: ChannelEntity) => -1 | 0 | 1;
/** Option to provide an extra actions renderer to add custom action buttons to each channel. */
extraActionsRenderer?: (channel: ChannelEntity) => JSX.Element;
/** Option to provide a custom channel renderer to override default themes and CSS variables. */
channelRenderer?: (channel: ChannelEntity) => JSX.Element;
/** Callback run when a user clicked one of the channels. Can be used to switch the current channel. */
onChannelSwitched?: (channel: ChannelEntity) => unknown;
}
/**
* Renders an interactive list of channels.
*
* It can represent all channels of the application, only
* channels joined by the current user, all channels available to be joined, or whatever else is
* passed into it. A common pattern in chat applications is to render two instances of the
* component - one visible all the time to show joined channels, and another one hidden inside a
* modal with channels available to join. Make sure to handle the onChannelSwitched event to switch
* the current channel passed to the Chat provider.
*/
declare const useChannelListCore: (props: CommonChannelListProps) => {
channelFromString: (channel: ChannelEntity | string) => ChannelEntity | {
id: string;
name: string;
};
channelSorter: (a: ChannelEntity, b: ChannelEntity) => number;
isChannelActive: (ch: ChannelEntity) => boolean;
switchChannel: (channel: ChannelEntity) => void;
theme: "" | Themes;
};
interface ChatProps {
children?: ReactNode;
/** General theme to be used by the components.
* Exact looks can be tweaked later on with the use of CSS variables. */
theme?: Themes;
/** Current channel to display the messages and members from. */
currentChannel: string;
/** Array of channels to subscribe to get events. Allows up to 50 channels. Setting this option will disable the auto subscription when switching the current channel. */
channels?: string[];
/** Array of channel groups to subscribe to get events. Allows up to 50 channel groups. Setting this option will disable the auto subscription when switching the current channel group. */
channelGroups?: string[];
/** Option to disable presence events when set to "false." OccupancyIndicator and MemberList components will only work with memberships in that case. */
enablePresence?: boolean;
/** Option to provide an external list of user metadata. It's used to display information about senders on MessageList and TypingIndicator. */
users?: UserEntity[];
/** Pass a callback function that will be called to get a User metadata in case it's not passed to the users option */
getUser?: (userId: string) => UserEntity | Promise;
/** Option to define a timeout in seconds for typing indicators to hide after the last typed character. */
typingIndicatorTimeout?: number;
/** Options for automatic retries on errors. */
retryOptions?: RetryOptions;
/** Callback run on new messages. */
onMessage?: (message: MessageEnvelope) => unknown;
/** Callback run on signals. */
onSignal?: (message: SignalEvent) => unknown;
/** Callback run on message actions. */
onMessageAction?: (event: MessageActionEvent) => unknown;
/** Callback run on presence events. */
onPresence?: (event: PresenceEvent) => unknown;
/** Callback run on object events. */
onUser?: (event: BaseObjectsEvent) => unknown;
/** Callback run on object events. */
onChannel?: (event: BaseObjectsEvent) => unknown;
/** Callback run on object events. */
onMembership?: (event: BaseObjectsEvent) => unknown;
/** Callback run on file events. */
onFile?: (event: FileEvent) => unknown;
/** Callback run on status events. */
onStatus?: (event: StatusEvent) => unknown;
/** Callback run on any type of errors raised by the components. */
onError?: (error: Error) => unknown;
}
/**
* Chat provider is used to configure various common options and feed the components with data.
* It expects at least a "current" channel to display within components.
*
* Chat itself is supposed to be wrapped with a PubNubProvider component that is a part of the
* PubNub React SDK. You should use it to pre-configure your PubNub instance. Please see Getting
* Started page for details.
*/
declare class Chat extends Component {
constructor(props: ChatProps);
static defaultProps: {
channels: any[];
channelGroups: any[];
theme: "light";
enablePresence: boolean;
typingIndicatorTimeout: number;
users: any[];
retryOptions: {
maxRetries: number;
timeout: number;
exponentialFactor: number;
};
onError: () => void;
};
static getDerivedStateFromError(error: Error): {
error: Error;
};
componentDidCatch(error: Error): void;
render(): JSX.Element;
}
/**
*
* Internal Chat wrapper with all business logic
*
*/
declare const ChatInternal: FC;
declare const getNameInitials: (name: string) => string;
declare const getPredefinedColor: (uuid: string) => string;
declare const usePrevious: (value: T) => T;
declare function isFilePayload(message: MessagePayload | FilePayload): message is FilePayload;
interface MessagesByChannel {
[channel: string]: MessageEnvelope[];
}
type HookReturnValue = [
MessagesByChannel,
() => Promise,
Error
];
declare const useMessages: (options: FetchMessagesParameters) => HookReturnValue;
type ChannelsOccupancy = HereNowResponse["channels"];
type HookReturnValue$0 = [
ChannelsOccupancy,
() => void,
number,
Error,
boolean
];
declare const usePresence: (options?: HereNowParameters) => HookReturnValue$0;
declare const useUser: (options?: GetUUIDMetadataParameters) => [
UserEntity,
Error,
boolean
];
declare const useSubscribe: (options?: SubscribeParameters) => (() => void);
type HookReturnValue$1 = [
UserEntity[],
() => void,
number,
Error,
boolean
];
declare const useUsers: (options?: GetAllMetadataParameters) => HookReturnValue$1;
type HookReturnValue$2 = [
ChannelEntity[],
() => void,
number,
Error,
boolean
];
declare const useChannels: (options?: GetAllMetadataParameters) => HookReturnValue$2;
type HookReturnValue$3 = [
UserEntityWithMembership[],
() => void,
() => void,
number,
Error,
boolean
];
declare const useChannelMembers: (options: GetChannelMembersParameters) => HookReturnValue$3;
type HookReturnValue$4 = [
ChannelEntityWithMembership[],
() => void,
() => void,
number,
Error,
boolean
];
declare const useUserMemberships: (options?: GetMembershipsParametersv2) => HookReturnValue$4;
interface CommonMemberListProps {
children?: ReactNode;
/** Option to pass a list of members, including metadata, to render on the list. */
members: UserEntity[] | string[];
/** Option to pass a list of present member IDs to mark them with a presence indicator. */
presentMembers?: string[];
/** This text will be added after current user's name */
selfText?: string;
/** Members are sorted by presence and alphabetically by default, you can override that by providing a sorter function */
sort?: (a: UserEntity, b: UserEntity) => -1 | 0 | 1;
/** Provide extra actions renderer to add custom action buttons to each member */
extraActionsRenderer?: (member: UserEntity) => JSX.Element;
/** Option to provide a custom user renderer to override themes and CSS variables. */
memberRenderer?: (member: UserEntity) => JSX.Element;
/** A callback run when user clicked one of the members. */
onMemberClicked?: (member: UserEntity) => unknown;
}
/**
* Renders a list of members.
*
* It can represent all users of the application, only members of
* the current channel, users currently subscribed/present on the channel, or whatever else is passed
* into it. Custom memberRenderer can be used to modify how the users are rendered. For example
* you can add presence indicators.
*/
declare const useMemberListCore: (props: CommonMemberListProps) => {
clickMember: (member: UserEntity) => void;
isOwnMember: (uuid: string) => boolean;
isPresentMember: (uuid: string) => boolean;
memberFromString: (member: UserEntity | string) => UserEntity | {
id: string;
name: string;
};
memberSorter: (a: any, b: any) => any;
theme: "" | Themes;
};
interface CommonMessageInputProps {
/** Option to set a placeholder message to display in the text window. */
placeholder?: string;
/** Option to set a draft message to display in the text window. */
draftMessage?: string;
/** Option to attach sender data directly to each message. Enable it for high-throughput environments.
* This is an alternative to providing a full list of users directly into the Chat provider. */
senderInfo?: boolean;
/** Option to enable/disable firing the typing events when a user is typing a message. */
typingIndicator?: boolean;
/** Option to enable/disable the internal file upload capability. */
fileUpload?: "image" | "all";
/** Option to disable the input from composing and sending messages. */
disabled?: boolean;
/** Custom UI component to override default display for the Send button. */
sendButton?: JSX.Element | string;
/** Option to move action buttons (eg. file upload icon) to the right of the text input. */
actionsAfterInput?: boolean;
/** Callback to modify message content before sending it. This only works for text messages, not files. */
onBeforeSend?: (value: MessagePayload) => MessagePayload;
/** Callback for extra actions after sending a message. */
onSend?: (value: MessagePayload | File | UriFileInput) => void;
/** Option to provide an extra actions renderer to add custom action buttons to the input. */
extraActionsRenderer?: () => JSX.Element;
/** Callback to render custom file preview JSX Element */
filePreviewRenderer?: (file: File | UriFileInput) => JSX.Element | null;
}
/**
* Allows users to compose messages using text and emojis
* and automatically publish them on PubNub channels upon sending.
*/
declare const useMessageInputCore: (props: CommonMessageInputProps) => {
clearInput: () => void;
file: File | UriFileInput;
setFile: import("react").Dispatch>;
isValidInputText: () => boolean;
loader: boolean;
onError: (error: Error) => unknown;
sendMessage: () => Promise;
setText: import("react").Dispatch>;
text: string;
theme: "" | Themes;
startTypingIndicator: () => Promise;
stopTypingIndicator: () => Promise;
};
interface MessageRendererProps {
isOwn: boolean;
message: MessageEnvelope;
time: string;
editedText: string;
user?: UserEntity;
}
interface CommonMessageListProps {
children?: ReactNode;
/** Set this option to a non-zero value to enable fetching messages from the History API. This feature uses the infinite scrolling pattern and takes a maximum value of 25. */
fetchMessages?: number;
/** Option to enable rendering reactions that were added to messages. Make sure to also set up reactionsPicker when this option is enabled. */
enableReactions?: boolean;
/** Option to provide custom welcome messages to replace the default ones. Set to "false" to disable it. */
welcomeMessages?: false | MessageEnvelope | MessageEnvelope[];
/** Option to provide an extra actions renderer to add custom action buttons to each message. */
extraActionsRenderer?: (message: MessageEnvelope) => JSX.Element;
/** Option to provide a custom message item renderer if themes and CSS variables aren't enough. */
messageRenderer?: (props: MessageRendererProps) => JSX.Element;
/** Option to provide a custom message bubble renderer if themes and CSS variables aren't enough. */
bubbleRenderer?: (props: MessageRendererProps) => JSX.Element;
/** Option to provide a custom file renderer to change how images and other files are shown. */
fileRenderer?: (file: FileAttachment) => JSX.Element;
/** This option only works when you use either `messageRenderer` or `bubbleRenderer`. It allows you to apply one of the custom renderers only to the messages selected by the filter. */
filter?: (message: MessageEnvelope) => boolean;
/** Enable this to render deleted messages instead of filtering them out. They can be then customized with one of the renderers. */
renderDeleted?: boolean;
}
/**
* Fetches historical messages using the scrolling pagination pattern and subscribes to the current
* channel to stay up to date with new messages.
*
* It also displays data in an interactive list, including
* user names, avatars, the time when a message was sent, and attachments (links, images) and allows to react to
* messages with emojis and to show those reactions immediately.
*/
declare const useMessageListCore: (props: CommonMessageListProps) => {
addReaction: (reaction: string, messageTimetoken: string | number) => Promise;
channel: string;
emojiPickerShown: boolean;
fetchHistory: () => Promise;
fetchingMessages: boolean;
getTime: (timestamp: number) => string;
getUser: (uuid: string) => UserEntity;
isOwnMessage: (uuid: string) => boolean;
messages: MessageEnvelope[];
onError: (error: Error) => unknown;
paginationEnd: boolean;
prevChannel: string;
prevMessages: MessageEnvelope[];
pubnub: import("pubnub");
reactingToMessage: any;
removeReaction: (reaction: string, messageTimetoken: any, actionTimetoken: any) => Promise;
scrolledBottom: boolean;
setEmojiPickerShown: import("react").Dispatch>;
setReactingToMessage: import("react").Dispatch;
setScrolledBottom: import("react").Dispatch>;
setUnreadMessages: import("react").Dispatch>;
theme: "" | Themes;
unreadMessages: number;
users: UserEntity[];
initMessagesLoaded: {};
setInitMessagesLoaded: import("react").Dispatch>;
};
declare const ThemeAtom: import("jotai").PrimitiveAtom<"" | Themes> & {
init: "" | Themes;
};
declare const CurrentChannelAtom: import("jotai").PrimitiveAtom & {
init: string;
};
declare const SubscribeChannelsAtom: import("jotai").PrimitiveAtom & {
init: string[];
};
declare const SubscribeChannelGroupsAtom: import("jotai").PrimitiveAtom & {
init: string[];
};
declare const UsersMetaAtom: import("jotai").PrimitiveAtom & {
init: UserEntity[];
};
declare const MessagesAtom: import("jotai").PrimitiveAtom<{
[channel: string]: MessageEnvelope[];
}> & {
init: {
[channel: string]: MessageEnvelope[];
};
};
declare const PaginationAtom: import("jotai").PrimitiveAtom<{
[channel: string]: boolean;
}> & {
init: {
[channel: string]: boolean;
};
};
declare const TypingIndicatorAtom: import("jotai").PrimitiveAtom<{}> & {
init: {};
};
declare const TypingIndicatorTimeoutAtom: import("jotai").PrimitiveAtom & {
init: number;
};
declare const RetryFunctionAtom: import("jotai").PrimitiveAtom<{
function: (fn: () => Promise) => Promise;
}> & {
init: {
function: (fn: () => Promise) => Promise;
};
};
declare const ErrorFunctionAtom: import("jotai").PrimitiveAtom<{
function: (error: Error) => unknown;
}> & {
init: {
function: (error: Error) => unknown;
};
};
declare const MissingUserCallbackAtom: import("jotai").PrimitiveAtom<{
function?: (userId: string) => UserEntity | Promise;
}> & {
init: {
function?: (userId: string) => UserEntity | Promise;
};
};
declare const RequestMissingUserAtom: import("jotai").WritableAtom>;
declare const CurrentChannelMessagesAtom: import("jotai").WritableAtom;
declare const CurrentChannelPaginationAtom: import("jotai").WritableAtom;
declare const CurrentChannelTypingIndicatorAtom: import("jotai").WritableAtom;
interface CommonTypingIndicatorProps {
/** Option to put a typing indicator inside the MessageList component to render indicators as messages. */
showAsMessage?: boolean;
}
/** Subscribes to events generated by MessageInput to display information about users that are
* currently typing messages.
*
* It can be displayed as a text denoting the user's name, or in a form similar to
* a message that can be renderer inside MessageList.
*/
declare const useTypingIndicatorCore: (props: CommonTypingIndicatorProps) => {
activeUUIDs: any[];
getIndicationString: () => string;
theme: "" | Themes;
users: UserEntity[];
};
interface ChannelListStyle {
channelListWrapper?: ViewStyle;
channelList?: ViewStyle;
channel?: ViewStyle;
channelActive?: ViewStyle;
channelPressed?: ViewStyle;
channelTitle?: ViewStyle;
channelName?: TextStyle;
channelDescription?: TextStyle;
channelThumb?: ImageStyle;
channelActions?: ViewStyle;
}
declare const _default: (theme: Themes) => ChannelListStyle;
type ChannelListProps = CommonChannelListProps & {
/** Callback run when a user long pressed one of the channels. Can be used for extra actions menu. */
onChannelLongPressed?: (channel: ChannelEntity) => unknown;
/** Options to provide custom StyleSheet for the component. It will be merged with the default styles. */
style?: ChannelListStyle;
};
/**
* Renders an interactive list of channels.
*
* It can represent all channels of the application, only
* channels joined by the current user, all channels available to be joined, or whatever else is
* passed into it. A common pattern in chat applications is to render two instances of the
* component - one visible all the time to show joined channels, and another one hidden inside a
* modal with channels available to join. Make sure to handle the onChannelSwitched event to switch
* the current channel passed to the Chat provider.
*/
declare const ChannelList: FC;
interface UseStyleProps {
theme: Themes | "";
createDefaultStyle: (theme: Themes | "") => T;
customStyle?: T;
}
declare const useStyle: (props: UseStyleProps) => T;
declare const useRotation: (shouldRun?: boolean) => Animated.AnimatedInterpolation;
interface MemberListStyle {
memberListWrapper?: ViewStyle;
memberList?: ViewStyle;
member?: ViewStyle;
memberPressed?: ViewStyle;
memberTitle?: ViewStyle;
memberName?: TextStyle;
memberDescription?: TextStyle;
memberThumb?: ViewStyle;
memberThumbImage?: ImageStyle;
memberThumbText?: TextStyle;
memberActions?: ViewStyle;
memberPresence?: ViewStyle;
}
declare const _default: (theme: Themes) => MemberListStyle;
type MemberListProps = CommonMemberListProps & {
/** Callback run when a user long pressed one of the members. Can be used for extra actions menu. */
onMemberLongPressed?: (member: UserEntity) => unknown;
/** Options to provide custom StyleSheet for the component. It will be merged with the default styles. */
style?: MemberListStyle;
};
/**
* Renders a list of members.
*
* It can represent all users of the application, only members of
* the current channel, users currently subscribed/present on the channel, or whatever else is passed
* into it. Custom memberRenderer can be used to modify how the users are rendered. For example
* you can add presence indicators.
*/
declare const MemberList: FC;
interface MessageInputStyle {
messageInputWrapper?: ViewStyle;
messageInputContent?: ViewStyle;
messageInput?: ViewStyle;
messageInputPlaceholder?: TextStyle;
messageInputFileLabel?: ViewStyle;
messageInputRemoveFileLabel?: ViewStyle;
sendButton?: ViewStyle;
sendButtonActive?: ViewStyle;
icon?: ImageStyle;
extraActions?: ViewStyle;
fileUploadModalContent?: ViewStyle;
fileUploadModalSheetContainer?: ViewStyle;
fileUploadModalSheetContent?: ViewStyle;
fileUploadModalSheetContentHeaderContainer?: ViewStyle;
fileUploadModalSheetContentHeaderText?: ViewStyle;
fileUploadModalSheetContentCloseIconContainer?: ViewStyle;
fileUploadModalSheetContentCloseIcon?: ImageStyle;
fileUploadModalSheetContentButton?: ViewStyle;
fileUploadModalSheetContentButtonIcon?: ImageStyle;
fileUploadModalSheetContentTextStyle?: ViewStyle;
filePreviewContainer?: ViewStyle;
filePreviewText?: TextStyle;
}
declare const _default: (theme: Themes) => MessageInputStyle;
type MessageInputProps = CommonMessageInputProps & {
/** Options to provide custom StyleSheet for the component. It will be merged with the default styles. */
style?: MessageInputStyle;
fileModalRenderer?: (params: {
pickPhoto: () => Promise;
pickDocument: () => Promise;
modalVisible: boolean;
setModalVisible: React.Dispatch>;
}) => JSX.Element;
onChange?: (newText: string) => void;
sendMessageOnSubmitEditing?: boolean;
} & Omit;
/**
* Allows users to compose messages using text and emojis
* and automatically publish them on PubNub channels upon sending.
*/
declare const MessageInput: FC;
interface MessageListStyle {
messageList?: ViewStyle;
messageListScroller?: ViewStyle;
message?: ViewStyle;
messagePressed?: ViewStyle;
messageOwn?: ViewStyle;
messageAvatar?: ViewStyle;
messageOwnAvatar?: ViewStyle;
messageAvatarImage?: ImageStyle;
messageAvatarText?: ViewStyle;
messageMain?: ViewStyle;
messageOwnMain?: ViewStyle;
messageTitle?: ViewStyle;
messageOwnTitle?: ViewStyle;
messageAuthor?: TextStyle;
messageTime?: TextStyle;
messageBubble?: TextStyle;
reactionWrapper?: ViewStyle;
reaction?: ViewStyle;
reactionActive?: ViewStyle;
reactionText?: TextStyle;
spinner?: ImageStyle;
spinnerWrapper?: ViewStyle;
unread?: ViewStyle;
unreadText?: TextStyle;
imageFile?: ImageStyle;
fileNameText?: TextStyle;
downloadIconStyle?: ImageStyle;
fileDownloadContainer?: ViewStyle;
downloadedSuccessBanner?: ViewStyle;
downloadedSuccessBannerContent?: ViewStyle;
downloadedSuccessBannerText?: TextStyle;
downloadingInProgressIconContainer?: ViewStyle;
}
declare const _default: (theme: Themes) => MessageListStyle;
interface EmojiPickerElementProps {
onEmojiSelected?: ({ emoji }: {
emoji: string;
}) => void;
onClose?: () => void;
open?: boolean;
}
type MessageListProps = CommonMessageListProps & {
/** Option to pass in a component that will be used for picking message reactions. For more details, refer to the Message Reactions section in the docs. */
reactionsPicker?: ReactElement;
/** Callback run on a list scroll. */
onScroll?: (event: NativeSyntheticEvent) => void;
/** Options to provide custom StyleSheet for the component. It will be merged with the default styles. */
style?: MessageListStyle;
};
/**
* Fetches historical messages using the scrolling pagination pattern and subscribes to the current
* channel to stay up to date with new messages.
*
* It also displays data in an interactive list, including
* user names, avatars, the time when a message was sent, and attachments (links, images) and allows to react to
* messages with emojis and to show those reactions immediately.
*/
declare const MessageList: FC;
interface TypingIndicatorStyle {
typingIndicator?: TextStyle;
}
declare const _default: (theme: Themes) => TypingIndicatorStyle;
type TypingIndicatorProps = CommonTypingIndicatorProps & {
/** Options to provide custom StyleSheet for the component. It will be merged with the default styles. */
style?: TypingIndicatorStyle & MessageListStyle;
};
/** Subscribes to events generated by MessageInput to display information about users that are
* currently typing messages.
*
* It can be displayed as a text denoting the user's name, or in a form similar to
* a message that can be renderer inside MessageList.
*/
declare const TypingIndicator: FC;
export { CommonChannelListProps, useChannelListCore, ChatProps, Chat, ChatInternal, getNameInitials, getPredefinedColor, usePrevious, isFilePayload, useMessages, usePresence, useUser, useSubscribe, useUsers, useChannels, useChannelMembers, useUserMemberships, CommonMemberListProps, useMemberListCore, CommonMessageInputProps, useMessageInputCore, MessageRendererProps, CommonMessageListProps, useMessageListCore, ThemeAtom, CurrentChannelAtom, SubscribeChannelsAtom, SubscribeChannelGroupsAtom, UsersMetaAtom, MessagesAtom, PaginationAtom, TypingIndicatorAtom, TypingIndicatorTimeoutAtom, RetryFunctionAtom, ErrorFunctionAtom, MissingUserCallbackAtom, RequestMissingUserAtom, CurrentChannelMessagesAtom, CurrentChannelPaginationAtom, CurrentChannelTypingIndicatorAtom, Themes, ChannelEntity, UserEntity, ChannelEntityWithMembership, UserEntityWithMembership, MessageEnvelope, MessagePayload, FilePayload, FileAttachment, ImageAttachment, LinkAttachment, RetryOptions, ProperFetchMessagesResponse, CommonTypingIndicatorProps, useTypingIndicatorCore, ChannelListProps, ChannelList, ChannelListStyle, _default, UseStyleProps, useStyle, useRotation, MemberListProps, MemberList, MemberListStyle, MessageInputProps, MessageInput, MessageInputStyle, MessageListProps, MessageList, MessageListStyle, EmojiPickerElementProps, TypingIndicatorProps, TypingIndicator, TypingIndicatorStyle };