Skip to content

Commit 76c802e

Browse files
authored
Merge pull request #102 from openai/fix-multiple-on-thread-change-invocations
Fix multiple on[Event] invocations from chatkit-react
2 parents 37f6435 + 2e44907 commit 76c802e

File tree

2 files changed

+39
-24
lines changed

2 files changed

+39
-24
lines changed

.changeset/honest-spies-whisper.md

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
---
2+
'@openai/chatkit-react': patch
3+
---
4+
5+
Fix event handlers registered multiple times

packages/chatkit-react/src/ChatKit.tsx

Lines changed: 34 additions & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -17,6 +17,21 @@ declare module 'react' {
1717
}
1818
}
1919

20+
const EVENT_HANDLER_MAP: {
21+
[K in keyof ChatKitEvents]: ToEventHandlerKey<K>;
22+
} = {
23+
'chatkit.error': 'onError',
24+
'chatkit.response.end': 'onResponseEnd',
25+
'chatkit.response.start': 'onResponseStart',
26+
'chatkit.log': 'onLog',
27+
'chatkit.thread.change': 'onThreadChange',
28+
'chatkit.thread.load.start': 'onThreadLoadStart',
29+
'chatkit.thread.load.end': 'onThreadLoadEnd',
30+
'chatkit.ready': 'onReady',
31+
};
32+
33+
const EVENT_NAMES = Object.keys(EVENT_HANDLER_MAP) as (keyof ChatKitEvents)[];
34+
2035
export const ChatKit = React.forwardRef<OpenAIChatKit, ChatKitProps>(
2136
function ChatKit({ control, ...htmlProps }, forwardedRef) {
2237
const ref = React.useRef<OpenAIChatKit | null>(null);
@@ -42,6 +57,25 @@ export const ChatKit = React.forwardRef<OpenAIChatKit, ChatKitProps>(
4257
};
4358
}, [control.options]);
4459

60+
React.useEffect(() => {
61+
const el = ref.current;
62+
if (!el) return;
63+
64+
const controller = new AbortController();
65+
for (const eventName of EVENT_NAMES) {
66+
el.addEventListener(eventName, (e) => {
67+
const handlerName = EVENT_HANDLER_MAP[eventName];
68+
const handler = control.handlers[handlerName];
69+
if (typeof handler === 'function') {
70+
handler(e.detail as any);
71+
}
72+
});
73+
}
74+
return () => {
75+
controller.abort();
76+
};
77+
}, [control.handlers]);
78+
4579
return (
4680
<openai-chatkit
4781
ref={(chatKit) => {
@@ -58,30 +92,6 @@ export const ChatKit = React.forwardRef<OpenAIChatKit, ChatKitProps>(
5892
if (!ref.current) {
5993
return;
6094
}
61-
62-
const events: {
63-
[K in keyof ChatKitEvents]: ToEventHandlerKey<K>;
64-
} = {
65-
'chatkit.error': 'onError',
66-
'chatkit.response.end': 'onResponseEnd',
67-
'chatkit.response.start': 'onResponseStart',
68-
'chatkit.log': 'onLog',
69-
'chatkit.thread.change': 'onThreadChange',
70-
'chatkit.thread.load.start': 'onThreadLoadStart',
71-
'chatkit.thread.load.end': 'onThreadLoadEnd',
72-
'chatkit.ready': 'onReady',
73-
};
74-
75-
const eventNames = Object.keys(events) as (keyof ChatKitEvents)[];
76-
77-
for (const event of eventNames) {
78-
ref.current.addEventListener(event, (e) => {
79-
const handler = control.handlers[events[event]];
80-
if (typeof handler === 'function') {
81-
handler(e.detail as any);
82-
}
83-
});
84-
}
8595
}}
8696
{...htmlProps}
8797
/>

0 commit comments

Comments
 (0)