@webinex/chatify 2.0.0-alpha12 → 2.0.0-alpha14

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (144) hide show
  1. package/dist/{Chatify-CwAfN1wu.js → Chatify-CP2jgo8d.js} +191 -118
  2. package/dist/Chatify-CP2jgo8d.js.map +1 -0
  3. package/dist/Chatify.css +28 -0
  4. package/dist/audit.js +3 -2
  5. package/dist/audit.js.map +1 -1
  6. package/dist/index.js +1 -1
  7. package/dist/types/audit/index.d.ts +17 -15
  8. package/dist/types/core/api/api.d.ts +146 -0
  9. package/dist/types/ui/Chat/ChatContext.d.ts +2 -0
  10. package/dist/types/ui/Chat/ChatPanel.d.ts +7 -0
  11. package/dist/types/ui/Chat/ChatView.d.ts +4 -2
  12. package/dist/types/ui/ChatGroup/ChatGroupContext.d.ts +4 -1
  13. package/dist/types/ui/ChatGroup/ChatGroupPanel.d.ts +21 -2
  14. package/dist/types/ui/Conversation/Conversation.d.ts +1 -0
  15. package/dist/types/ui/Conversation/ConversationContext.d.ts +1 -0
  16. package/dist/types/ui/Conversation/ConversationHeader.d.ts +4 -1
  17. package/dist/types/ui/localizer.d.ts +4 -1
  18. package/dist/types/ui/useCompact.d.ts +4 -0
  19. package/package.json +81 -81
  20. package/src/audit/AuditChatList.tsx +25 -25
  21. package/src/audit/AuditConversationPanel.tsx +49 -48
  22. package/src/audit/AuditPanel.tsx +76 -76
  23. package/src/audit/AuditPanelCustomizeValue.ts +11 -11
  24. package/src/audit/AuditSearch.tsx +89 -89
  25. package/src/audit/AuditSearchValue.tsx +42 -42
  26. package/src/audit/auditApi.tsx +113 -113
  27. package/src/audit/index.d.ts +18 -18
  28. package/src/audit/index.tsx +28 -28
  29. package/src/audit/styles.scss +72 -72
  30. package/src/core/api/api.ts +675 -669
  31. package/src/core/api/baseApi.ts +38 -38
  32. package/src/core/api/index.ts +1 -1
  33. package/src/core/client.ts +298 -298
  34. package/src/core/constants.ts +1 -1
  35. package/src/core/debounce.ts +90 -90
  36. package/src/core/index.ts +4 -4
  37. package/src/core/types.tsx +182 -182
  38. package/src/index.ts +2 -2
  39. package/src/styles/aside.scss +34 -26
  40. package/src/styles/chat-list.scss +138 -138
  41. package/src/styles/chat.scss +11 -11
  42. package/src/styles/conversation.scss +199 -200
  43. package/src/styles/index.scss +227 -220
  44. package/src/styles/input.scss +148 -148
  45. package/src/styles/keyframes.scss +14 -14
  46. package/src/styles/members.scss +30 -13
  47. package/src/styles/mixins.scss +38 -25
  48. package/src/styles/variables.scss +13 -13
  49. package/src/ui/Chat/ChatContext.tsx +32 -30
  50. package/src/ui/Chat/ChatEditableHeaderName.tsx +63 -63
  51. package/src/ui/Chat/ChatHeaderActions.tsx +19 -19
  52. package/src/ui/Chat/ChatPanel.tsx +46 -30
  53. package/src/ui/Chat/ChatView.tsx +122 -115
  54. package/src/ui/Chat/Members/ChatMembersButton.tsx +9 -9
  55. package/src/ui/Chat/Members/ChatMembersPanel.tsx +128 -112
  56. package/src/ui/Chat/Members/ChatMembersPreview.tsx +25 -25
  57. package/src/ui/Chat/Members/index.ts +13 -13
  58. package/src/ui/Chat/index.ts +6 -6
  59. package/src/ui/ChatGroup/AutoReply/AutoReplyButton.tsx +21 -21
  60. package/src/ui/ChatGroup/AutoReply/AutoReplyForm.tsx +50 -50
  61. package/src/ui/ChatGroup/AutoReply/AutoReplyPanel.tsx +94 -94
  62. package/src/ui/ChatGroup/AutoReply/AutoReplyPeriodInput.tsx +22 -22
  63. package/src/ui/ChatGroup/AutoReply/AutoReplyTextInput.tsx +22 -22
  64. package/src/ui/ChatGroup/AutoReply/index.ts +19 -19
  65. package/src/ui/ChatGroup/ChatGroupContext.tsx +63 -61
  66. package/src/ui/ChatGroup/ChatGroupPanel.tsx +110 -75
  67. package/src/ui/ChatGroup/Create/CreateChatButton.tsx +15 -15
  68. package/src/ui/ChatGroup/Create/CreateChatForm.tsx +36 -36
  69. package/src/ui/ChatGroup/Create/CreateChatMemberInput.tsx +65 -65
  70. package/src/ui/ChatGroup/Create/CreateChatNameInput.tsx +25 -25
  71. package/src/ui/ChatGroup/Create/CreateChatPanel.tsx +45 -45
  72. package/src/ui/ChatGroup/Create/index.ts +19 -19
  73. package/src/ui/ChatGroup/Layout/ChatGroupActions.tsx +15 -15
  74. package/src/ui/ChatGroup/Layout/ChatGroupAside.tsx +12 -12
  75. package/src/ui/ChatGroup/Layout/ChatGroupBody.tsx +17 -10
  76. package/src/ui/ChatGroup/Layout/ChatGroupFooter.tsx +3 -3
  77. package/src/ui/ChatGroup/Layout/ChatGroupHeader.tsx +5 -5
  78. package/src/ui/ChatGroup/Layout/ChatGroupMain.tsx +21 -19
  79. package/src/ui/ChatGroup/Layout/index.ts +22 -22
  80. package/src/ui/ChatGroup/List/ChatListPanel.tsx +28 -28
  81. package/src/ui/ChatGroup/List/index.ts +8 -8
  82. package/src/ui/ChatGroup/index.ts +6 -6
  83. package/src/ui/Chatify.tsx +15 -15
  84. package/src/ui/Conversation/Conversation.tsx +96 -92
  85. package/src/ui/Conversation/ConversationActions.tsx +12 -12
  86. package/src/ui/Conversation/ConversationBody.tsx +28 -28
  87. package/src/ui/Conversation/ConversationContext.ts +31 -30
  88. package/src/ui/Conversation/ConversationHeader.tsx +35 -19
  89. package/src/ui/Conversation/ConversationName.tsx +7 -7
  90. package/src/ui/Conversation/InputBox/InputBox.tsx +126 -126
  91. package/src/ui/Conversation/InputBox/InputBoxFile.tsx +38 -38
  92. package/src/ui/Conversation/InputBox/InputBoxFileList.tsx +21 -21
  93. package/src/ui/Conversation/InputBox/InputFilesBox.tsx +78 -78
  94. package/src/ui/Conversation/InputBox/InputSubmitButtonBox.tsx +26 -26
  95. package/src/ui/Conversation/InputBox/InputTextBox.tsx +63 -61
  96. package/src/ui/Conversation/InputBox/index.ts +23 -23
  97. package/src/ui/Conversation/Message/MessageAuthor.tsx +13 -13
  98. package/src/ui/Conversation/Message/MessageBox.tsx +20 -20
  99. package/src/ui/Conversation/Message/MessageContent.tsx +15 -15
  100. package/src/ui/Conversation/Message/MessageFile.tsx +54 -54
  101. package/src/ui/Conversation/Message/MessageFileList.tsx +14 -14
  102. package/src/ui/Conversation/Message/MessageInfoBox.tsx +28 -28
  103. package/src/ui/Conversation/Message/MessageRow.tsx +28 -28
  104. package/src/ui/Conversation/Message/MessageText.tsx +7 -7
  105. package/src/ui/Conversation/Message/index.ts +28 -28
  106. package/src/ui/Conversation/NextObserver/NextMessagesObserver.tsx +47 -47
  107. package/src/ui/Conversation/NextObserver/index.ts +1 -1
  108. package/src/ui/Conversation/ReadObserver/MessageReadObserver.tsx +49 -49
  109. package/src/ui/Conversation/ReadObserver/index.ts +1 -1
  110. package/src/ui/Conversation/SendingMessage/SendingMessageBox.tsx +16 -16
  111. package/src/ui/Conversation/SendingMessage/SendingMessageContent.tsx +13 -13
  112. package/src/ui/Conversation/SendingMessage/SendingMessageInfoBox.tsx +13 -13
  113. package/src/ui/Conversation/SendingMessage/SendingMessageText.tsx +7 -7
  114. package/src/ui/Conversation/SendingMessage/index.ts +16 -16
  115. package/src/ui/Conversation/SystemMessage/SystemMessageBox.tsx +20 -20
  116. package/src/ui/Conversation/SystemMessage/SystemMessageRow.tsx +28 -28
  117. package/src/ui/Conversation/SystemMessage/index.ts +10 -10
  118. package/src/ui/Conversation/index.ts +13 -13
  119. package/src/ui/Thread/ThreadActions.tsx +22 -22
  120. package/src/ui/Thread/ThreadContext.ts +13 -13
  121. package/src/ui/Thread/ThreadPanel.tsx +128 -127
  122. package/src/ui/Thread/index.tsx +3 -3
  123. package/src/ui/color.ts +20 -20
  124. package/src/ui/common/Avatar.tsx +20 -20
  125. package/src/ui/common/ChatList/ChatList.tsx +83 -84
  126. package/src/ui/common/ChatList/ChatListItemAvatar.tsx +22 -22
  127. package/src/ui/common/ChatList/ChatListItemBox.tsx +32 -32
  128. package/src/ui/common/ChatList/ChatListItemLastMessage.tsx +15 -15
  129. package/src/ui/common/ChatList/ChatListItemLastMessageAuthor.tsx +15 -15
  130. package/src/ui/common/ChatList/ChatListItemLastMessageContent.tsx +21 -21
  131. package/src/ui/common/ChatList/ChatListItemLastMessageSentAt.tsx +22 -22
  132. package/src/ui/common/ChatList/ChatListItemName.tsx +8 -8
  133. package/src/ui/common/ChatList/ChatListItemUnreadCount.tsx +12 -12
  134. package/src/ui/common/ChatList/ChatListValue.ts +9 -9
  135. package/src/ui/common/ChatList/index.ts +32 -32
  136. package/src/ui/common/Icon.tsx +48 -48
  137. package/src/ui/common/MessageSkeleton.tsx +20 -20
  138. package/src/ui/common/index.ts +14 -14
  139. package/src/ui/customize.tsx +51 -51
  140. package/src/ui/index.ts +11 -11
  141. package/src/ui/localizer.tsx +148 -137
  142. package/src/ui/useCompact.tsx +32 -0
  143. package/src/ui/useFormatter.tsx +17 -17
  144. package/dist/Chatify-CwAfN1wu.js.map +0 -1
@@ -1,25 +1,25 @@
1
- import { ChatList, customize } from '@webinex/chatify';
2
- import { Empty, Skeleton } from 'antd';
3
- import { AuditChatListItem } from './auditApi';
4
-
5
- export interface AuditChatListProps {
6
- items: AuditChatListItem[];
7
- loading: boolean;
8
- selected: string | null;
9
- onSelect: (id: string) => void;
10
- top?: number;
11
- }
12
-
13
- export const AuditChatList = customize('AuditChatList', (props: AuditChatListProps) => {
14
- const { items, selected, onSelect, loading, top } = props;
15
-
16
- if (loading) {
17
- return <Skeleton />;
18
- }
19
-
20
- if (items.length === 0) {
21
- return <Empty />;
22
- }
23
-
24
- return <ChatList items={items} selected={selected} onSelect={onSelect} noRead top={top} />;
25
- });
1
+ import { ChatList, customize } from '@webinex/chatify';
2
+ import { Empty, Skeleton } from 'antd';
3
+ import { AuditChatListItem } from './auditApi';
4
+
5
+ export interface AuditChatListProps {
6
+ items: AuditChatListItem[];
7
+ loading: boolean;
8
+ selected: string | null;
9
+ onSelect: (id: string) => void;
10
+ top?: number;
11
+ }
12
+
13
+ export const AuditChatList = customize('AuditChatList', (props: AuditChatListProps) => {
14
+ const { items, selected, onSelect, loading, top } = props;
15
+
16
+ if (loading) {
17
+ return <Skeleton />;
18
+ }
19
+
20
+ if (items.length === 0) {
21
+ return <Empty />;
22
+ }
23
+
24
+ return <ChatList items={items} selected={selected} onSelect={onSelect} noRead top={top} />;
25
+ });
@@ -1,48 +1,49 @@
1
- import { Conversation, customize } from '@webinex/chatify';
2
- import { auditApi } from './auditApi';
3
- import { useMemo } from 'react';
4
-
5
- export interface AuditConversationPanelProps {
6
- id: string;
7
- onClose?: () => void;
8
-
9
- /**
10
- * Number of messages to load per page.
11
- * @default 20
12
- */
13
- pageSize?: number;
14
- }
15
-
16
- export const AuditConversationPanel = customize(
17
- 'AuditConversationPanel',
18
- (props: AuditConversationPanelProps) => {
19
- const { id, onClose, pageSize = 20 } = props;
20
- const { data: chat } = auditApi.useGetAuditChatQuery({ id });
21
-
22
- const {
23
- data: messageSegments,
24
- isFetchingNextPage,
25
- fetchNextPage,
26
- hasNextPage,
27
- } = auditApi.useGetAuditChatMessagesInfiniteInfiniteQuery(
28
- { id },
29
- { initialPageParam: { skip: 0, take: pageSize } },
30
- );
31
-
32
- const messages = useMemo(() => messageSegments?.pages.flatMap((x) => x.items) ?? [], [messageSegments]);
33
-
34
- if (!chat) return null;
35
-
36
- return (
37
- <Conversation
38
- value={{ active: false, id, lastReadMessageId: null, name: chat.name }}
39
- nextLoading={isFetchingNextPage}
40
- onNext={fetchNextPage}
41
- hasMore={!isFetchingNextPage && hasNextPage}
42
- messages={messages}
43
- noReadTracking
44
- onClose={onClose}
45
- />
46
- );
47
- },
48
- );
1
+ import { Conversation, customize } from '@webinex/chatify';
2
+ import { auditApi } from './auditApi';
3
+ import { useMemo } from 'react';
4
+
5
+ export interface AuditConversationPanelProps {
6
+ id: string;
7
+ onClose?: () => void;
8
+
9
+ /**
10
+ * Number of messages to load per page.
11
+ * @default 20
12
+ */
13
+ pageSize?: number;
14
+ }
15
+
16
+ export const AuditConversationPanel = customize(
17
+ 'AuditConversationPanel',
18
+ (props: AuditConversationPanelProps) => {
19
+ const { id, onClose, pageSize = 20 } = props;
20
+ const { data: chat } = auditApi.useGetAuditChatQuery({ id });
21
+
22
+ const {
23
+ data: messageSegments,
24
+ isFetchingNextPage,
25
+ fetchNextPage,
26
+ hasNextPage,
27
+ } = auditApi.useGetAuditChatMessagesInfiniteInfiniteQuery(
28
+ { id },
29
+ { initialPageParam: { skip: 0, take: pageSize } },
30
+ );
31
+
32
+ const messages = useMemo(() => messageSegments?.pages.flatMap((x) => x.items) ?? [], [messageSegments]);
33
+
34
+ if (!chat) return null;
35
+
36
+ return (
37
+ <Conversation
38
+ value={{ active: false, id, lastReadMessageId: null, name: chat.name }}
39
+ nextLoading={isFetchingNextPage}
40
+ onNext={fetchNextPage}
41
+ hasMore={!isFetchingNextPage && hasNextPage}
42
+ messages={messages}
43
+ noReadTracking
44
+ onClose={onClose}
45
+ compact={false}
46
+ />
47
+ );
48
+ },
49
+ );
@@ -1,76 +1,76 @@
1
- import classNames from 'classnames';
2
- import { AuditSearch } from './AuditSearch';
3
- import { useCallback, useEffect, useMemo, useState } from 'react';
4
- import { AuditSearchUtil } from './AuditSearchValue';
5
- import { auditApi } from './auditApi';
6
- import { AuditChatList } from './AuditChatList';
7
- import { CustomizeContext, defaultLocalizer, Localizer, LocalizerContext } from '@webinex/chatify';
8
- import { AuditConversationPanel } from './AuditConversationPanel';
9
- import { AuditPanelCustomizeValue } from './AuditPanelCustomizeValue';
10
-
11
- export interface AuditPanelProps {
12
- className?: string;
13
- style?: React.CSSProperties;
14
- localizer?: Localizer;
15
- customize?: AuditPanelCustomizeValue;
16
-
17
- /**
18
- * Maximum number of chats to load.
19
- * @default 100
20
- */
21
- max?: number;
22
- }
23
-
24
- function useData(props: AuditPanelProps, values: string[]) {
25
- const { max } = props;
26
- const query = useMemo(() => AuditSearchUtil.queryOf(values), [values]);
27
-
28
- const { currentData: chats, isLoading } = auditApi.useGetAuditChatListQuery(
29
- {
30
- ...query!,
31
- pagingRule: { skip: 0, take: max! },
32
- includeTotal: true,
33
- },
34
- { skip: !query },
35
- );
36
-
37
- return useMemo(() => ({ chats: chats?.items ?? [], isLoading }), [chats, isLoading]);
38
- }
39
-
40
- const EMPTY = Object.freeze({} as AuditPanelCustomizeValue);
41
-
42
- export function AuditPanel(props: AuditPanelProps) {
43
- props = { max: 100, customize: EMPTY, ...props };
44
- const { className, style, localizer = defaultLocalizer, customize = EMPTY, max } = props;
45
- const [values, setValues] = useState<string[]>([]);
46
- const { chats, isLoading } = useData(props, values);
47
-
48
- const [selectedId, setSelectedId] = useState<string | null>(null);
49
- const resetSelected = useCallback(() => setSelectedId(null), []);
50
-
51
- useEffect(() => {
52
- if (chats.every((x) => x.id !== selectedId)) {
53
- setSelectedId(null);
54
- }
55
- }, [chats, selectedId]);
56
-
57
- return (
58
- <CustomizeContext.Provider value={customize}>
59
- <LocalizerContext.Provider value={localizer}>
60
- <div className={classNames(className, 'wxchtf-audit-panel')} style={style}>
61
- <AuditSearch onSearch={setValues} />
62
- <div className={classNames('wxchtf-audit-body', { '--conversation-opened': !!selectedId })}>
63
- <AuditChatList
64
- items={chats}
65
- loading={isLoading}
66
- selected={selectedId}
67
- onSelect={setSelectedId}
68
- top={Math.min(chats.length, max!)}
69
- />
70
- {selectedId && <AuditConversationPanel id={selectedId} onClose={resetSelected} />}
71
- </div>
72
- </div>
73
- </LocalizerContext.Provider>
74
- </CustomizeContext.Provider>
75
- );
76
- }
1
+ import classNames from 'classnames';
2
+ import { AuditSearch } from './AuditSearch';
3
+ import { useCallback, useEffect, useMemo, useState } from 'react';
4
+ import { AuditSearchUtil } from './AuditSearchValue';
5
+ import { auditApi } from './auditApi';
6
+ import { AuditChatList } from './AuditChatList';
7
+ import { CustomizeContext, defaultLocalizer, Localizer, LocalizerContext } from '@webinex/chatify';
8
+ import { AuditConversationPanel } from './AuditConversationPanel';
9
+ import { AuditPanelCustomizeValue } from './AuditPanelCustomizeValue';
10
+
11
+ export interface AuditPanelProps {
12
+ className?: string;
13
+ style?: React.CSSProperties;
14
+ localizer?: Localizer;
15
+ customize?: AuditPanelCustomizeValue;
16
+
17
+ /**
18
+ * Maximum number of chats to load.
19
+ * @default 100
20
+ */
21
+ max?: number;
22
+ }
23
+
24
+ function useData(props: AuditPanelProps, values: string[]) {
25
+ const { max } = props;
26
+ const query = useMemo(() => AuditSearchUtil.queryOf(values), [values]);
27
+
28
+ const { currentData: chats, isLoading } = auditApi.useGetAuditChatListQuery(
29
+ {
30
+ ...query!,
31
+ pagingRule: { skip: 0, take: max! },
32
+ includeTotal: true,
33
+ },
34
+ { skip: !query },
35
+ );
36
+
37
+ return useMemo(() => ({ chats: chats?.items ?? [], isLoading }), [chats, isLoading]);
38
+ }
39
+
40
+ const EMPTY = Object.freeze({} as AuditPanelCustomizeValue);
41
+
42
+ export function AuditPanel(props: AuditPanelProps) {
43
+ props = { max: 100, customize: EMPTY, ...props };
44
+ const { className, style, localizer = defaultLocalizer, customize = EMPTY, max } = props;
45
+ const [values, setValues] = useState<string[]>([]);
46
+ const { chats, isLoading } = useData(props, values);
47
+
48
+ const [selectedId, setSelectedId] = useState<string | null>(null);
49
+ const resetSelected = useCallback(() => setSelectedId(null), []);
50
+
51
+ useEffect(() => {
52
+ if (chats.every((x) => x.id !== selectedId)) {
53
+ setSelectedId(null);
54
+ }
55
+ }, [chats, selectedId]);
56
+
57
+ return (
58
+ <CustomizeContext.Provider value={customize}>
59
+ <LocalizerContext.Provider value={localizer}>
60
+ <div className={classNames(className, 'wxchtf-audit-panel')} style={style}>
61
+ <AuditSearch onSearch={setValues} />
62
+ <div className={classNames('wxchtf-audit-body', { '--conversation-opened': !!selectedId })}>
63
+ <AuditChatList
64
+ items={chats}
65
+ loading={isLoading}
66
+ selected={selectedId}
67
+ onSelect={setSelectedId}
68
+ top={Math.min(chats.length, max!)}
69
+ />
70
+ {selectedId && <AuditConversationPanel id={selectedId} onClose={resetSelected} />}
71
+ </div>
72
+ </div>
73
+ </LocalizerContext.Provider>
74
+ </CustomizeContext.Provider>
75
+ );
76
+ }
@@ -1,11 +1,11 @@
1
- import { ChatListCustomizeValue, ConversationCustomizeValue } from '@webinex/chatify';
2
- import { AuditConversationPanel } from './AuditConversationPanel';
3
- import { AuditChatList } from './AuditChatList';
4
- import { AuditSearch } from './AuditSearch';
5
-
6
- export type AuditPanelCustomizeValue = ConversationCustomizeValue &
7
- ChatListCustomizeValue & {
8
- AuditConversationPanel?: typeof AuditConversationPanel.Component;
9
- AuditChatList?: typeof AuditChatList.Component;
10
- AuditSearch?: typeof AuditSearch.Component;
11
- };
1
+ import { ChatListCustomizeValue, ConversationCustomizeValue } from '@webinex/chatify';
2
+ import { AuditConversationPanel } from './AuditConversationPanel';
3
+ import { AuditChatList } from './AuditChatList';
4
+ import { AuditSearch } from './AuditSearch';
5
+
6
+ export type AuditPanelCustomizeValue = ConversationCustomizeValue &
7
+ ChatListCustomizeValue & {
8
+ AuditConversationPanel?: typeof AuditConversationPanel.Component;
9
+ AuditChatList?: typeof AuditChatList.Component;
10
+ AuditSearch?: typeof AuditSearch.Component;
11
+ };
@@ -1,89 +1,89 @@
1
- import { Account, chatifyApi, customize, Localizer, useLocalizer } from '@webinex/chatify';
2
- import { Select } from 'antd';
3
- import classNames from 'classnames';
4
- import { useEffect, useMemo, useState } from 'react';
5
- import { AuditSearchUtil } from './AuditSearchValue';
6
-
7
- export interface AuditSearchProps {
8
- className?: string;
9
- onSearch?: (values: string[]) => void;
10
- }
11
-
12
- type Value = { label: JSX.Element; value: string };
13
-
14
- function* mapOptions(localizer: Localizer, accounts: Account[] | undefined, searchValue: string) {
15
- if (searchValue.length === 0) return;
16
-
17
- if (searchValue.length > 0)
18
- yield {
19
- label: localizer.audit.textSearchOption(searchValue),
20
- value: AuditSearchUtil.TEXT_PREFIX + searchValue,
21
- };
22
-
23
- for (const account of accounts?.filter((x) =>
24
- x.name.toLocaleLowerCase().includes(searchValue.toLocaleLowerCase()),
25
- ) ?? []) {
26
- yield {
27
- label: localizer.audit.memberSearchOption(account),
28
- value: AuditSearchUtil.MEMBER_PREFIX + account.id,
29
- };
30
- }
31
- }
32
-
33
- function useOptions(accounts: Account[] | undefined, searchValue: string) {
34
- const localizer = useLocalizer();
35
- return useMemo(
36
- () => Array.from(mapOptions(localizer, accounts, searchValue)),
37
- [localizer, accounts, searchValue],
38
- );
39
- }
40
-
41
- export const AuditSearch = customize('AuditSearch', (props: AuditSearchProps) => {
42
- const { className, onSearch } = props;
43
- const [searchValue, setSearchValue] = useState('');
44
- const [values, setValues] = useState<Value[]>([]);
45
- const { data: accounts, isLoading } = chatifyApi.useGetAccountListQuery({});
46
- const options = useOptions(accounts, searchValue);
47
- const localizer = useLocalizer();
48
-
49
- useEffect(() => {
50
- onSearch?.(values.map((x) => x.value));
51
- }, [onSearch, values]);
52
-
53
- return (
54
- <div className={classNames('wxchtf-search', className)}>
55
- <Select<string[], Value>
56
- allowClear
57
- className="wxchtf-search-select"
58
- mode="multiple"
59
- value={values.map((x) => x.value)}
60
- options={options.length > 0 ? options : values}
61
- searchValue={searchValue}
62
- onSearch={setSearchValue}
63
- onSelect={(_, option) => {
64
- setValues((prev) => {
65
- if (AuditSearchUtil.isSearchByText(option.value)) {
66
- prev = prev.filter((x) => !AuditSearchUtil.isSearchByText(x.value));
67
- }
68
-
69
- return [...prev, option];
70
- });
71
- setSearchValue('');
72
- }}
73
- onDeselect={(_, option) => {
74
- setValues((prev) => prev.filter((x) => x.value !== option.value));
75
- setSearchValue('');
76
- }}
77
- filterOption={false}
78
- onDropdownVisibleChange={() => setSearchValue('')}
79
- disabled={isLoading}
80
- loading={isLoading}
81
- placeholder={localizer.audit.searchPlaceholder}
82
- notFoundContent={
83
- searchValue.length === 0 ? localizer.audit.noInputBlurb : localizer.audit.noChatFound
84
- }
85
- size="large"
86
- />
87
- </div>
88
- );
89
- });
1
+ import { Account, chatifyApi, customize, Localizer, useLocalizer } from '@webinex/chatify';
2
+ import { Select } from 'antd';
3
+ import classNames from 'classnames';
4
+ import { useEffect, useMemo, useState } from 'react';
5
+ import { AuditSearchUtil } from './AuditSearchValue';
6
+
7
+ export interface AuditSearchProps {
8
+ className?: string;
9
+ onSearch?: (values: string[]) => void;
10
+ }
11
+
12
+ type Value = { label: JSX.Element; value: string };
13
+
14
+ function* mapOptions(localizer: Localizer, accounts: Account[] | undefined, searchValue: string) {
15
+ if (searchValue.length === 0) return;
16
+
17
+ if (searchValue.length > 0)
18
+ yield {
19
+ label: localizer.audit.textSearchOption(searchValue),
20
+ value: AuditSearchUtil.TEXT_PREFIX + searchValue,
21
+ };
22
+
23
+ for (const account of accounts?.filter((x) =>
24
+ x.name.toLocaleLowerCase().includes(searchValue.toLocaleLowerCase()),
25
+ ) ?? []) {
26
+ yield {
27
+ label: localizer.audit.memberSearchOption(account),
28
+ value: AuditSearchUtil.MEMBER_PREFIX + account.id,
29
+ };
30
+ }
31
+ }
32
+
33
+ function useOptions(accounts: Account[] | undefined, searchValue: string) {
34
+ const localizer = useLocalizer();
35
+ return useMemo(
36
+ () => Array.from(mapOptions(localizer, accounts, searchValue)),
37
+ [localizer, accounts, searchValue],
38
+ );
39
+ }
40
+
41
+ export const AuditSearch = customize('AuditSearch', (props: AuditSearchProps) => {
42
+ const { className, onSearch } = props;
43
+ const [searchValue, setSearchValue] = useState('');
44
+ const [values, setValues] = useState<Value[]>([]);
45
+ const { data: accounts, isLoading } = chatifyApi.useGetAccountListQuery({});
46
+ const options = useOptions(accounts, searchValue);
47
+ const localizer = useLocalizer();
48
+
49
+ useEffect(() => {
50
+ onSearch?.(values.map((x) => x.value));
51
+ }, [onSearch, values]);
52
+
53
+ return (
54
+ <div className={classNames('wxchtf-search', className)}>
55
+ <Select<string[], Value>
56
+ allowClear
57
+ className="wxchtf-search-select"
58
+ mode="multiple"
59
+ value={values.map((x) => x.value)}
60
+ options={options.length > 0 ? options : values}
61
+ searchValue={searchValue}
62
+ onSearch={setSearchValue}
63
+ onSelect={(_, option) => {
64
+ setValues((prev) => {
65
+ if (AuditSearchUtil.isSearchByText(option.value)) {
66
+ prev = prev.filter((x) => !AuditSearchUtil.isSearchByText(x.value));
67
+ }
68
+
69
+ return [...prev, option];
70
+ });
71
+ setSearchValue('');
72
+ }}
73
+ onDeselect={(_, option) => {
74
+ setValues((prev) => prev.filter((x) => x.value !== option.value));
75
+ setSearchValue('');
76
+ }}
77
+ filterOption={false}
78
+ onDropdownVisibleChange={() => setSearchValue('')}
79
+ disabled={isLoading}
80
+ loading={isLoading}
81
+ placeholder={localizer.audit.searchPlaceholder}
82
+ notFoundContent={
83
+ searchValue.length === 0 ? localizer.audit.noInputBlurb : localizer.audit.noChatFound
84
+ }
85
+ size="large"
86
+ />
87
+ </div>
88
+ );
89
+ });
@@ -1,42 +1,42 @@
1
- import { GetAuditChatListQueryArgs } from './auditApi';
2
-
3
- export interface AuditSearchOption {
4
- label: JSX.Element;
5
- value: string;
6
- }
7
-
8
- const MEMBER_PREFIX = 'member://';
9
- const TEXT_PREFIX = 'text://';
10
-
11
- function queryOf(
12
- values: string[],
13
- ): Pick<GetAuditChatListQueryArgs, 'containsOneOfMembers' | 'searchString'> | null {
14
- let containsOneOfMembers: string[] | null = values
15
- .filter(AuditSearchUtil.isSearchByMember)
16
- .map((v) => v.slice(MEMBER_PREFIX.length));
17
-
18
- containsOneOfMembers = containsOneOfMembers.length > 0 ? containsOneOfMembers : null;
19
-
20
- const searchStringValues = values
21
- .filter(AuditSearchUtil.isSearchByText)
22
- .map((v) => v.slice(TEXT_PREFIX.length));
23
-
24
- const searchString = searchStringValues.length > 0 ? searchStringValues.join(' ') : null;
25
-
26
- if (!containsOneOfMembers && !searchString) {
27
- return null;
28
- }
29
-
30
- return {
31
- containsOneOfMembers,
32
- searchString,
33
- };
34
- }
35
-
36
- export const AuditSearchUtil = Object.freeze({
37
- MEMBER_PREFIX,
38
- TEXT_PREFIX,
39
- isSearchByMember: (value: string) => value.startsWith(MEMBER_PREFIX),
40
- isSearchByText: (value: string) => value.startsWith(TEXT_PREFIX),
41
- queryOf,
42
- });
1
+ import { GetAuditChatListQueryArgs } from './auditApi';
2
+
3
+ export interface AuditSearchOption {
4
+ label: JSX.Element;
5
+ value: string;
6
+ }
7
+
8
+ const MEMBER_PREFIX = 'member://';
9
+ const TEXT_PREFIX = 'text://';
10
+
11
+ function queryOf(
12
+ values: string[],
13
+ ): Pick<GetAuditChatListQueryArgs, 'containsOneOfMembers' | 'searchString'> | null {
14
+ let containsOneOfMembers: string[] | null = values
15
+ .filter(AuditSearchUtil.isSearchByMember)
16
+ .map((v) => v.slice(MEMBER_PREFIX.length));
17
+
18
+ containsOneOfMembers = containsOneOfMembers.length > 0 ? containsOneOfMembers : null;
19
+
20
+ const searchStringValues = values
21
+ .filter(AuditSearchUtil.isSearchByText)
22
+ .map((v) => v.slice(TEXT_PREFIX.length));
23
+
24
+ const searchString = searchStringValues.length > 0 ? searchStringValues.join(' ') : null;
25
+
26
+ if (!containsOneOfMembers && !searchString) {
27
+ return null;
28
+ }
29
+
30
+ return {
31
+ containsOneOfMembers,
32
+ searchString,
33
+ };
34
+ }
35
+
36
+ export const AuditSearchUtil = Object.freeze({
37
+ MEMBER_PREFIX,
38
+ TEXT_PREFIX,
39
+ isSearchByMember: (value: string) => value.startsWith(MEMBER_PREFIX),
40
+ isSearchByText: (value: string) => value.startsWith(TEXT_PREFIX),
41
+ queryOf,
42
+ });