@convokitapp/vue-ui 0.5.0 → 0.6.0
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.
- package/CHANGELOG.md +40 -0
- package/PARITY.md +22 -0
- package/README.md +61 -1
- package/dist/index.cjs +298 -43
- package/dist/index.cjs.map +1 -1
- package/dist/index.css +46 -1
- package/dist/index.css.map +1 -1
- package/dist/index.d.cts +98 -18
- package/dist/index.d.ts +98 -18
- package/dist/index.js +297 -43
- package/dist/index.js.map +1 -1
- package/package.json +3 -3
package/dist/index.d.ts
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { Conversation as Conversation$1, MessageListOptions, Message, SendMessageInput, MarkConversationReadOptions, RealtimeConnectionHandlers, RealtimeSubscription, MessageEvent, MessageDeletedEvent, ReadEvent, TypingEvent, ReadPosition, MessageMedia, ConvoKitClient } from '@convokitapp/sdk';
|
|
1
|
+
import { Conversation as Conversation$1, InboxPage, MessageListOptions, Message, SendMessageInput, MarkConversationReadOptions, RealtimeConnectionHandlers, RealtimeSubscription, MessageEvent, MessageDeletedEvent, ReadEvent, TypingEvent, ReadPosition, InboxSummary, MessageMedia, ConvoKitClient, InboxEntry } from '@convokitapp/sdk';
|
|
2
2
|
import * as vue from 'vue';
|
|
3
3
|
import { CSSProperties, HTMLAttributes, Ref, VNodeChild, PropType, MaybeRefOrGetter, TextareaHTMLAttributes } from 'vue';
|
|
4
4
|
|
|
@@ -11,6 +11,15 @@ interface ConvoKitUiClient {
|
|
|
11
11
|
offset: number;
|
|
12
12
|
archived: boolean;
|
|
13
13
|
}): Promise<Conversation$1[]>;
|
|
14
|
+
/** Activity-ordered inbox pages with a preview, unread count and read state per row (core 0.6). Pass the previous
|
|
15
|
+
* `nextCursor` back as `cursor` (null for the head). Adapters without it, and custom page loaders, use the legacy
|
|
16
|
+
* `getConversations` path without summaries; a 404 from this endpoint falls back to that path for the store's life.
|
|
17
|
+
*/
|
|
18
|
+
listInbox?(options: {
|
|
19
|
+
limit: number;
|
|
20
|
+
cursor: string | null;
|
|
21
|
+
archived: boolean;
|
|
22
|
+
}): Promise<InboxPage>;
|
|
14
23
|
getConversation(conversationId: string): Promise<Conversation$1>;
|
|
15
24
|
/** Newest first, with a paired value cursor; never derive an offset from rendered rows. */
|
|
16
25
|
getMessages(options: MessageListOptions): Promise<Message[]>;
|
|
@@ -29,6 +38,10 @@ interface ConvoKitUiClient {
|
|
|
29
38
|
onConnectionEvent(handlers: RealtimeConnectionHandlers): RealtimeSubscription;
|
|
30
39
|
/** Notify on inbox mutations AND on initial subscription/reconnect. No room data in the signal. */
|
|
31
40
|
onInboxChanged(handler: () => void, onError?: (error: Error) => void): RealtimeSubscription;
|
|
41
|
+
/** Message inserts/edits and read-position advances in the caller's rooms; never fires on join/rejoin. The list
|
|
42
|
+
* store throttles these (`activityRefreshWindowMs`); room stores ignore them.
|
|
43
|
+
*/
|
|
44
|
+
onInboxActivity?(handler: () => void, onError?: (error: Error) => void): RealtimeSubscription;
|
|
32
45
|
onMessage(conversationId: string, handler: (event: MessageEvent) => void, onError?: (error: Error) => void): RealtimeSubscription;
|
|
33
46
|
onMessageDeleted(conversationId: string, handler: (event: MessageDeletedEvent) => void, onError?: (error: Error) => void): RealtimeSubscription;
|
|
34
47
|
onReadReceipt(conversationId: string, handler: (event: ReadEvent) => void, onError?: (error: Error) => void): RealtimeSubscription;
|
|
@@ -51,6 +64,10 @@ interface ConversationPageRequest {
|
|
|
51
64
|
type ConversationPageLoader = (request: ConversationPageRequest) => Promise<Conversation$1[]>;
|
|
52
65
|
interface ConversationListState {
|
|
53
66
|
conversations: Readonly<Ref<Conversation$1[]>>;
|
|
67
|
+
/** Per-room preview, unread count and read state by conversation ID; empty on the legacy `getConversations` path. */
|
|
68
|
+
summaries: Readonly<Ref<ReadonlyMap<string, InboxSummary>>>;
|
|
69
|
+
/** The bound session's user; `''` without a session, on the legacy path and after disposal. */
|
|
70
|
+
currentUserId: Readonly<Ref<string>>;
|
|
54
71
|
filter: Readonly<Ref<ConversationFilter>>;
|
|
55
72
|
isInitialLoading: Readonly<Ref<boolean>>;
|
|
56
73
|
isLoadingMore: Readonly<Ref<boolean>>;
|
|
@@ -89,6 +106,10 @@ interface ConversationItemSlotProps {
|
|
|
89
106
|
index: number;
|
|
90
107
|
selected: boolean;
|
|
91
108
|
select: () => void;
|
|
109
|
+
/** Present when the list carries an inbox summary for this row (0.6.0). */
|
|
110
|
+
summary?: InboxSummary;
|
|
111
|
+
/** Present when the list knows the viewer (0.6.0); compare with `summary.latestMessage.senderId`. */
|
|
112
|
+
currentUserId?: string;
|
|
92
113
|
}
|
|
93
114
|
interface MessageSlotProps {
|
|
94
115
|
message: Message;
|
|
@@ -979,6 +1000,8 @@ interface UseConversationListOptions {
|
|
|
979
1000
|
initialFilter?: ConversationFilter;
|
|
980
1001
|
pageSize?: number;
|
|
981
1002
|
autoLoad?: boolean;
|
|
1003
|
+
/** Max-wait window (ms) that coalesces `inbox_activity` signals into one refresh; default 500, 0 = immediate. */
|
|
1004
|
+
activityRefreshWindowMs?: number;
|
|
982
1005
|
}
|
|
983
1006
|
interface ConversationListController extends ConversationListState {
|
|
984
1007
|
loadInitial(): Promise<void>;
|
|
@@ -992,6 +1015,10 @@ declare function useConversationList(options: UseConversationListOptions): Conve
|
|
|
992
1015
|
|
|
993
1016
|
interface ConversationListViewProps extends ConvoKitAppearanceProps {
|
|
994
1017
|
conversations: readonly Conversation$1[];
|
|
1018
|
+
/** Inbox summaries by conversation ID (0.6.0). Rows with one show a preview, time and unread badge. */
|
|
1019
|
+
summaries?: ReadonlyMap<string, InboxSummary>;
|
|
1020
|
+
/** The viewer; a preview from them reads `You: …`. Absent → no prefix. */
|
|
1021
|
+
currentUserId?: string;
|
|
995
1022
|
selectedConversationId?: string;
|
|
996
1023
|
onConversationSelect?: (conversation: Conversation$1) => void;
|
|
997
1024
|
onRefresh?: () => void | Promise<void>;
|
|
@@ -1012,6 +1039,14 @@ declare const ConversationListView: vue.DefineComponent<vue.ExtractPropTypes<{
|
|
|
1012
1039
|
readonly type: PropType<readonly Conversation$1[]>;
|
|
1013
1040
|
readonly required: true;
|
|
1014
1041
|
};
|
|
1042
|
+
readonly summaries: {
|
|
1043
|
+
readonly type: PropType<ReadonlyMap<string, InboxSummary>>;
|
|
1044
|
+
readonly default: undefined;
|
|
1045
|
+
};
|
|
1046
|
+
readonly currentUserId: {
|
|
1047
|
+
readonly type: StringConstructor;
|
|
1048
|
+
readonly default: undefined;
|
|
1049
|
+
};
|
|
1015
1050
|
readonly selectedConversationId: {
|
|
1016
1051
|
readonly type: StringConstructor;
|
|
1017
1052
|
readonly default: undefined;
|
|
@@ -1083,6 +1118,14 @@ declare const ConversationListView: vue.DefineComponent<vue.ExtractPropTypes<{
|
|
|
1083
1118
|
readonly type: PropType<readonly Conversation$1[]>;
|
|
1084
1119
|
readonly required: true;
|
|
1085
1120
|
};
|
|
1121
|
+
readonly summaries: {
|
|
1122
|
+
readonly type: PropType<ReadonlyMap<string, InboxSummary>>;
|
|
1123
|
+
readonly default: undefined;
|
|
1124
|
+
};
|
|
1125
|
+
readonly currentUserId: {
|
|
1126
|
+
readonly type: StringConstructor;
|
|
1127
|
+
readonly default: undefined;
|
|
1128
|
+
};
|
|
1086
1129
|
readonly selectedConversationId: {
|
|
1087
1130
|
readonly type: StringConstructor;
|
|
1088
1131
|
readonly default: undefined;
|
|
@@ -1149,6 +1192,7 @@ declare const ConversationListView: vue.DefineComponent<vue.ExtractPropTypes<{
|
|
|
1149
1192
|
"onLoad-more"?: () => any;
|
|
1150
1193
|
}>, {
|
|
1151
1194
|
readonly isInitialLoading: boolean;
|
|
1195
|
+
readonly currentUserId: string;
|
|
1152
1196
|
readonly scrollElement: Ref<HTMLElement | null, HTMLElement | null>;
|
|
1153
1197
|
readonly paginationThreshold: number;
|
|
1154
1198
|
readonly classNames: Partial<Record<ConvoKitUiPart, string>>;
|
|
@@ -1156,6 +1200,7 @@ declare const ConversationListView: vue.DefineComponent<vue.ExtractPropTypes<{
|
|
|
1156
1200
|
readonly density: ConvoKitUiDensity;
|
|
1157
1201
|
readonly unstyled: boolean;
|
|
1158
1202
|
readonly onRefresh: () => void | Promise<void>;
|
|
1203
|
+
readonly summaries: ReadonlyMap<string, InboxSummary>;
|
|
1159
1204
|
readonly isLoadingMore: boolean;
|
|
1160
1205
|
readonly hasMore: boolean;
|
|
1161
1206
|
readonly selectedConversationId: string;
|
|
@@ -1193,10 +1238,22 @@ declare const ConversationList: vue.DefineComponent<vue.ExtractPropTypes<{
|
|
|
1193
1238
|
type: BooleanConstructor;
|
|
1194
1239
|
default: boolean;
|
|
1195
1240
|
};
|
|
1241
|
+
activityRefreshWindowMs: {
|
|
1242
|
+
type: NumberConstructor;
|
|
1243
|
+
default: undefined;
|
|
1244
|
+
};
|
|
1196
1245
|
onControllerChange: {
|
|
1197
1246
|
type: PropType<(controller: ConversationListController) => void>;
|
|
1198
1247
|
default: undefined;
|
|
1199
1248
|
};
|
|
1249
|
+
summaries: {
|
|
1250
|
+
readonly type: PropType<ReadonlyMap<string, InboxSummary>>;
|
|
1251
|
+
readonly default: undefined;
|
|
1252
|
+
};
|
|
1253
|
+
currentUserId: {
|
|
1254
|
+
readonly type: StringConstructor;
|
|
1255
|
+
readonly default: undefined;
|
|
1256
|
+
};
|
|
1200
1257
|
selectedConversationId: {
|
|
1201
1258
|
readonly type: StringConstructor;
|
|
1202
1259
|
readonly default: undefined;
|
|
@@ -1284,10 +1341,22 @@ declare const ConversationList: vue.DefineComponent<vue.ExtractPropTypes<{
|
|
|
1284
1341
|
type: BooleanConstructor;
|
|
1285
1342
|
default: boolean;
|
|
1286
1343
|
};
|
|
1344
|
+
activityRefreshWindowMs: {
|
|
1345
|
+
type: NumberConstructor;
|
|
1346
|
+
default: undefined;
|
|
1347
|
+
};
|
|
1287
1348
|
onControllerChange: {
|
|
1288
1349
|
type: PropType<(controller: ConversationListController) => void>;
|
|
1289
1350
|
default: undefined;
|
|
1290
1351
|
};
|
|
1352
|
+
summaries: {
|
|
1353
|
+
readonly type: PropType<ReadonlyMap<string, InboxSummary>>;
|
|
1354
|
+
readonly default: undefined;
|
|
1355
|
+
};
|
|
1356
|
+
currentUserId: {
|
|
1357
|
+
readonly type: StringConstructor;
|
|
1358
|
+
readonly default: undefined;
|
|
1359
|
+
};
|
|
1291
1360
|
selectedConversationId: {
|
|
1292
1361
|
readonly type: StringConstructor;
|
|
1293
1362
|
readonly default: undefined;
|
|
@@ -1353,6 +1422,7 @@ declare const ConversationList: vue.DefineComponent<vue.ExtractPropTypes<{
|
|
|
1353
1422
|
"onConversation-select"?: (...args: any[]) => any;
|
|
1354
1423
|
}>, {
|
|
1355
1424
|
isInitialLoading: boolean;
|
|
1425
|
+
currentUserId: string;
|
|
1356
1426
|
scrollElement: Ref<HTMLElement | null, HTMLElement | null>;
|
|
1357
1427
|
paginationThreshold: number;
|
|
1358
1428
|
classNames: Partial<Record<ConvoKitUiPart, string>>;
|
|
@@ -1363,6 +1433,7 @@ declare const ConversationList: vue.DefineComponent<vue.ExtractPropTypes<{
|
|
|
1363
1433
|
autoLoad: boolean;
|
|
1364
1434
|
onControllerChange: (controller: ConversationListController) => void;
|
|
1365
1435
|
conversations: readonly Conversation$1[];
|
|
1436
|
+
summaries: ReadonlyMap<string, InboxSummary>;
|
|
1366
1437
|
isLoadingMore: boolean;
|
|
1367
1438
|
hasMore: boolean;
|
|
1368
1439
|
selectedConversationId: string;
|
|
@@ -1372,8 +1443,29 @@ declare const ConversationList: vue.DefineComponent<vue.ExtractPropTypes<{
|
|
|
1372
1443
|
pageLoader: ConversationPageLoader;
|
|
1373
1444
|
initialFilter: ConversationFilter;
|
|
1374
1445
|
pageSize: number;
|
|
1446
|
+
activityRefreshWindowMs: number;
|
|
1375
1447
|
}, {}, {}, {}, string, vue.ComponentProvideOptions, true, {}, any>;
|
|
1376
1448
|
|
|
1449
|
+
/** Whether a message is an optimistic row awaiting server acknowledgement. */
|
|
1450
|
+
declare function isConvoKitPendingMessage(message: Message): boolean;
|
|
1451
|
+
declare function matchesConversation(conversation: Conversation$1, filter: ConversationFilter): boolean;
|
|
1452
|
+
declare function applyConversationFilter(conversations: readonly Conversation$1[], filter: ConversationFilter): Conversation$1[];
|
|
1453
|
+
declare function mergeConversations(current: readonly Conversation$1[], incoming: readonly Conversation$1[]): Conversation$1[];
|
|
1454
|
+
/** Merge inbox pages by conversation ID: a later entry replaces an earlier one (its room moved), and the result is
|
|
1455
|
+
* re-ordered by `(activityAt desc, id desc)`. Server order is authoritative within a page; this is the rule applied
|
|
1456
|
+
* whenever pages are combined (load more, refresh).
|
|
1457
|
+
*/
|
|
1458
|
+
declare function mergeInboxEntries(current: readonly InboxEntry[], incoming: readonly InboxEntry[]): InboxEntry[];
|
|
1459
|
+
/** Device-zone clock time, shared by message rows and inbox rows. */
|
|
1460
|
+
declare function formatMessageTime(date: Date): string;
|
|
1461
|
+
declare function mergeMessages(current: readonly Message[], incoming: readonly Message[]): Message[];
|
|
1462
|
+
/** Readers of a message under the unified rule: a user's read position (createdAt, id) wins when present,
|
|
1463
|
+
* otherwise the acknowledgement time is compared with createdAt (legacy participants, empty-room acknowledgements).
|
|
1464
|
+
* The sender and pending rows never have readers.
|
|
1465
|
+
*/
|
|
1466
|
+
declare function readerIdsFor(message: Message, readAtByUserId: ReadonlyMap<string, Date>, readPositionByUserId?: ReadonlyMap<string, ReadPosition>): ReadonlySet<string>;
|
|
1467
|
+
declare function formatFileSize(size: number | undefined): string | null;
|
|
1468
|
+
|
|
1377
1469
|
interface MessageListViewProps extends ConvoKitAppearanceProps {
|
|
1378
1470
|
conversation: Conversation$1;
|
|
1379
1471
|
messages: readonly Message[];
|
|
@@ -1397,7 +1489,6 @@ interface MessageListViewProps extends ConvoKitAppearanceProps {
|
|
|
1397
1489
|
class?: unknown;
|
|
1398
1490
|
style?: unknown;
|
|
1399
1491
|
}
|
|
1400
|
-
declare function defaultFormatTime(date: Date): string;
|
|
1401
1492
|
/** Controlled message history with read receipts, structured media, and older-page loading. */
|
|
1402
1493
|
declare const MessageListView: vue.DefineComponent<vue.ExtractPropTypes<{
|
|
1403
1494
|
conversation: {
|
|
@@ -1462,7 +1553,7 @@ declare const MessageListView: vue.DefineComponent<vue.ExtractPropTypes<{
|
|
|
1462
1553
|
};
|
|
1463
1554
|
formatTime: {
|
|
1464
1555
|
type: PropType<(date: Date) => string>;
|
|
1465
|
-
default: typeof
|
|
1556
|
+
default: typeof formatMessageTime;
|
|
1466
1557
|
};
|
|
1467
1558
|
imageLoading: {
|
|
1468
1559
|
type: PropType<"eager" | "lazy">;
|
|
@@ -1549,7 +1640,7 @@ declare const MessageListView: vue.DefineComponent<vue.ExtractPropTypes<{
|
|
|
1549
1640
|
};
|
|
1550
1641
|
formatTime: {
|
|
1551
1642
|
type: PropType<(date: Date) => string>;
|
|
1552
|
-
default: typeof
|
|
1643
|
+
default: typeof formatMessageTime;
|
|
1553
1644
|
};
|
|
1554
1645
|
imageLoading: {
|
|
1555
1646
|
type: PropType<"eager" | "lazy">;
|
|
@@ -1606,6 +1697,8 @@ interface ConvoKitTheme {
|
|
|
1606
1697
|
incomingBubble: string;
|
|
1607
1698
|
outgoingBubble: string;
|
|
1608
1699
|
outgoingText: string;
|
|
1700
|
+
/** Unread badge background (0.6.0); its label uses `outgoingText`. Defaults to the primary color. */
|
|
1701
|
+
badge: string;
|
|
1609
1702
|
radius: string;
|
|
1610
1703
|
avatarSize: string;
|
|
1611
1704
|
fontFamily: string;
|
|
@@ -1646,17 +1739,4 @@ declare const ConvoKitThemeProvider: vue.DefineComponent<vue.ExtractPropTypes<{
|
|
|
1646
1739
|
}, {}, {}, {}, string, vue.ComponentProvideOptions, true, {}, any>;
|
|
1647
1740
|
declare function useConvoKitTheme(): Readonly<Ref<ConvoKitTheme>>;
|
|
1648
1741
|
|
|
1649
|
-
|
|
1650
|
-
declare function isConvoKitPendingMessage(message: Message): boolean;
|
|
1651
|
-
declare function matchesConversation(conversation: Conversation$1, filter: ConversationFilter): boolean;
|
|
1652
|
-
declare function applyConversationFilter(conversations: readonly Conversation$1[], filter: ConversationFilter): Conversation$1[];
|
|
1653
|
-
declare function mergeConversations(current: readonly Conversation$1[], incoming: readonly Conversation$1[]): Conversation$1[];
|
|
1654
|
-
declare function mergeMessages(current: readonly Message[], incoming: readonly Message[]): Message[];
|
|
1655
|
-
/** Readers of a message under the unified rule: a user's read position (createdAt, id) wins when present,
|
|
1656
|
-
* otherwise the acknowledgement time is compared with createdAt (legacy participants, empty-room acknowledgements).
|
|
1657
|
-
* The sender and pending rows never have readers.
|
|
1658
|
-
*/
|
|
1659
|
-
declare function readerIdsFor(message: Message, readAtByUserId: ReadonlyMap<string, Date>, readPositionByUserId?: ReadonlyMap<string, ReadPosition>): ReadonlySet<string>;
|
|
1660
|
-
declare function formatFileSize(size: number | undefined): string | null;
|
|
1661
|
-
|
|
1662
|
-
export { type BaseViewProps, type ComposerSlotProps, Conversation, type ConversationController, type ConversationFilter, type ConversationItemSlotProps, ConversationList, type ConversationListController, type ConversationListProps, type ConversationListState, ConversationListView, type ConversationListViewProps, type ConversationPageLoader, type ConversationPageRequest, type ConversationProps, type ConversationState, ConversationView, type ConversationViewProps, type ConvoKitAppearanceProps, ConvoKitAvatar, type ConvoKitTheme, ConvoKitThemeProvider, type ConvoKitUiClient, type ConvoKitUiDensity, type ConvoKitUiPart, type ErrorSlot, type ErrorSlotProps, type MediaSlotProps, MessageListView, type MessageListViewProps, type MessageSlotProps, type ReadReceiptSlotProps, type ScrollOptions, type StateSlot, type TypingSlotProps, type UseConversationListOptions, type UseConversationOptions, applyConversationFilter, createConvoKitUiClient, defaultConvoKitTheme, defaultReadersResolver, formatFileSize, isConvoKitPendingMessage, matchesConversation, mergeConversations, mergeMessages, readerIdsFor, useConversation, useConversationList, useConvoKitTheme };
|
|
1742
|
+
export { type BaseViewProps, type ComposerSlotProps, Conversation, type ConversationController, type ConversationFilter, type ConversationItemSlotProps, ConversationList, type ConversationListController, type ConversationListProps, type ConversationListState, ConversationListView, type ConversationListViewProps, type ConversationPageLoader, type ConversationPageRequest, type ConversationProps, type ConversationState, ConversationView, type ConversationViewProps, type ConvoKitAppearanceProps, ConvoKitAvatar, type ConvoKitTheme, ConvoKitThemeProvider, type ConvoKitUiClient, type ConvoKitUiDensity, type ConvoKitUiPart, type ErrorSlot, type ErrorSlotProps, type MediaSlotProps, MessageListView, type MessageListViewProps, type MessageSlotProps, type ReadReceiptSlotProps, type ScrollOptions, type StateSlot, type TypingSlotProps, type UseConversationListOptions, type UseConversationOptions, applyConversationFilter, createConvoKitUiClient, defaultConvoKitTheme, defaultReadersResolver, formatFileSize, isConvoKitPendingMessage, matchesConversation, mergeConversations, mergeInboxEntries, mergeMessages, readerIdsFor, useConversation, useConversationList, useConvoKitTheme };
|