Skip to content

Commit f7581e5

Browse files
Use reserved keys approach instead
1 parent 8ec89ec commit f7581e5

File tree

4 files changed

+36
-49
lines changed

4 files changed

+36
-49
lines changed

src/client.ts

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -269,7 +269,6 @@ export class StreamChat<StreamChatGenerics extends ExtendableGenerics = DefaultG
269269
defaultWSTimeoutWithFallback: number;
270270
defaultWSTimeout: number;
271271
private nextRequestAbortController: AbortController | null = null;
272-
public readonly customPropertyKeys: NonNullable<StreamChatOptions['customPropertyKeys']>;
273272

274273
/**
275274
* Initialize a client
@@ -363,7 +362,6 @@ export class StreamChat<StreamChatGenerics extends ExtendableGenerics = DefaultG
363362
this.defaultWSTimeout = 15 * 1000;
364363

365364
this.axiosInstance.defaults.paramsSerializer = axiosParamsSerializer;
366-
this.customPropertyKeys = options?.customPropertyKeys ?? { thread: [] };
367365

368366
/**
369367
* logger function should accept 3 parameters:

src/thread.ts

Lines changed: 34 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -68,19 +68,42 @@ export type ThreadReadState<SCG extends ExtendableGenerics = DefaultGenerics> =
6868
const DEFAULT_PAGE_LIMIT = 50;
6969
const DEFAULT_SORT: { created_at: AscDesc }[] = [{ created_at: -1 }];
7070
const MARK_AS_READ_THROTTLE_TIMEOUT = 1000;
71+
const THREAD_RESERVED_KEYS = [
72+
'channel',
73+
'channel_cid',
74+
'created_at',
75+
'created_by_user_id',
76+
'parent_message_id',
77+
'title',
78+
'updated_at',
79+
'latest_replies',
80+
'active_participant_count',
81+
'deleted_at',
82+
'last_message_at',
83+
'participant_count',
84+
'reply_count',
85+
'read',
86+
'thread_participants',
87+
'created_by',
88+
'parent_message',
89+
] as const;
7190

7291
// TODO: remove this once we move to API v2
73-
const constructCustomDataObject = <SCG extends ExtendableGenerics>(
74-
customPropertyKeys: (keyof ThreadResponseCustomData)[],
75-
threadData: ThreadResponse<SCG>,
76-
) =>
77-
customPropertyKeys.reduce<ThreadResponseCustomData>((custom, key) => {
78-
if (threadData[key]) {
79-
custom[key] = threadData[key];
92+
const constructCustomDataObject = <SCG extends ExtendableGenerics>(threadData: ThreadResponse<SCG>) => {
93+
const custom: ThreadResponseCustomData = {};
94+
95+
for (const key in threadData) {
96+
if (THREAD_RESERVED_KEYS.includes(key as keyof ThreadResponse<SCG>)) {
97+
continue;
8098
}
8199

82-
return custom;
83-
}, {});
100+
const customKey = key as keyof ThreadResponseCustomData;
101+
102+
custom[customKey] = threadData[customKey];
103+
}
104+
105+
return custom;
106+
};
84107

85108
export class Thread<SCG extends ExtendableGenerics = DefaultGenerics> {
86109
public readonly state: StateStore<ThreadState<SCG>>;
@@ -122,7 +145,7 @@ export class Thread<SCG extends ExtendableGenerics = DefaultGenerics> {
122145
replyCount: threadData.reply_count ?? 0,
123146
updatedAt: threadData.updated_at ? new Date(threadData.updated_at) : null,
124147
title: threadData.title,
125-
custom: constructCustomDataObject(client.customPropertyKeys.thread, threadData),
148+
custom: constructCustomDataObject<SCG>(threadData),
126149
});
127150

128151
this.id = threadData.parent_message_id;
@@ -230,7 +253,7 @@ export class Thread<SCG extends ExtendableGenerics = DefaultGenerics> {
230253
updatedAt: new Date(threadData.updated_at),
231254
deletedAt: threadData.deleted_at ? new Date(threadData.deleted_at) : null,
232255
// TODO: use threadData.custom once we move to API v2
233-
custom: constructCustomDataObject(this.client.customPropertyKeys.thread, threadData),
256+
custom: constructCustomDataObject<SCG>(threadData),
234257
});
235258
}).unsubscribe;
236259
};

src/types.ts

Lines changed: 1 addition & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -534,6 +534,7 @@ export interface ThreadResponse<SCG extends ExtendableGenerics = DefaultGenerics
534534
parent_message_id: string;
535535
title: string;
536536
updated_at: string;
537+
active_participant_count?: number;
537538
created_by?: UserResponse<SCG>;
538539
deleted_at?: string;
539540
last_message_at?: string;
@@ -1174,17 +1175,6 @@ export type StreamChatOptions = AxiosRequestConfig & {
11741175
*/
11751176
baseURL?: string;
11761177
browser?: boolean;
1177-
/**
1178-
* To access your custom data from `StateStore` you'll need to declare your custom property names for each feature.
1179-
* At the moment this is only needed for the Thread class. To get full type support make sure to merge interface
1180-
* declarations too.
1181-
*/
1182-
customPropertyKeys?: {
1183-
/**
1184-
* Interface declaration for custom object properties: `ThreadResponseCustomData`
1185-
*/
1186-
thread: (keyof ThreadResponseCustomData)[];
1187-
};
11881178
device?: BaseDeviceFields;
11891179
enableInsights?: boolean;
11901180
/** experimental feature, please contact support if you want this feature enabled for you */

test/unit/threads.test.ts

Lines changed: 1 addition & 25 deletions
Original file line numberDiff line numberDiff line change
@@ -596,34 +596,10 @@ describe('Threads 2.0', () => {
596596
expect(stateAfter.title).to.eq('B');
597597
});
598598

599-
it('ignores custom data when keys are missing from "StreamChat.customPropertyKeys.thread"', () => {
600-
const customKey = uuidv4();
601-
const thread = createTestThread({ [customKey]: 1 });
602-
thread.registerSubscriptions();
603-
604-
const stateBefore = thread.state.getLatestValue();
605-
606-
expect(stateBefore.custom).to.not.have.property(customKey);
607-
608-
client.dispatchEvent({
609-
type: 'thread.updated',
610-
thread: generateThreadResponse(channelResponse, generateMsg({ id: parentMessageResponse.id }), {
611-
[customKey]: 2,
612-
}),
613-
});
614-
615-
const stateAfter = thread.state.getLatestValue();
616-
617-
expect(stateAfter.custom).to.not.have.property(customKey);
618-
});
619-
620-
it('properly handles custom data when keys are defined in "StreamChat.customPropertyKeys.thread"', () => {
599+
it('properly handles custom data', () => {
621600
const customKey1 = uuidv4();
622601
const customKey2 = uuidv4();
623602

624-
// @ts-expect-error keys should be declared within `ThreadResponseCustomData` interface through interface merging
625-
client.customPropertyKeys.thread = [customKey1, customKey2];
626-
627603
const thread = createTestThread({ [customKey1]: 1, [customKey2]: { key: 1 } });
628604
thread.registerSubscriptions();
629605

0 commit comments

Comments
 (0)