Skip to content

Commit

Permalink
Optimize event handling structure
Browse files Browse the repository at this point in the history
  • Loading branch information
seabeya committed Jun 8, 2024
1 parent 79f11ac commit a904310
Show file tree
Hide file tree
Showing 3 changed files with 34 additions and 36 deletions.
2 changes: 1 addition & 1 deletion src/app/logs/page.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,7 @@ export default function Page() {
<>
<ItemTabs activeTab={selectedItem} handleTabClick={handleTabClick} />
{selectedItem !== '' ? (
<Logs item={selectedItem} />
<Logs target={selectedItem} />
) : (
<p className="text-center text-sm text-txt-low xl:text-base">Please select an item to view.</p>
)}
Expand Down
39 changes: 11 additions & 28 deletions src/components/sections/Logs.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -2,19 +2,21 @@ import { useEffect, useState } from 'react';
import { Virtuoso } from 'react-virtuoso';
import clsx from 'clsx';

import { useSpyStore } from '@/store';
import { useItemsStore, useSpyStore } from '@/store';
import { MessageData } from '@/types';
import { eventOptions } from '@/consts';
import Chat2Print from '@/lib/Chat2Print';
import SectionArea from '@/components/shared/SectionArea';
import LogsInfo from '@/components/LogsInfo';
import Log from '@/components/Log';

type LogsProps = {
item: string;
target: string;
};

export default function Logs({ item }: LogsProps) {
export default function Logs({ target }: LogsProps) {
const Spy = useSpyStore.getState().spy;
const Events = Spy.mode === 'users' ? eventOptions : useItemsStore.getState().events;

const [messageData, setMessageData] = useState<MessageData[]>([]);

Expand All @@ -24,30 +26,16 @@ export default function Logs({ item }: LogsProps) {
// Get existing data from indexedDB:
(async () => {
try {
setMessageData(await Spy.idb.getAllFromIndex('logs', Spy.idbIndex, item));
setMessageData(await Spy.idb.getAllFromIndex('logs', Spy.idbIndex, target));
} catch (_) {
console.log('Something went wrong while fetching data from IndexedDB. Please refresh the page and try again.');
}
})();

// Listening to new messages:
const handle = new Chat2Print(setMessageData, item, Spy.idbIndex);
const handle = new Chat2Print(setMessageData, target, Spy.idbIndex);

const handleMessage = handle.onMessage.bind(handle);
const handleSubscription = handle.onSubscription.bind(handle);
const handleResub = handle.onResub.bind(handle);
const handleCheer = handle.onCheer.bind(handle);
const handleSubgift = handle.onSubgift.bind(handle);
const handleSubmysterygift = handle.onSubmysterygift.bind(handle);

if (Spy.mode === 'users') {
Spy.tmiClient.on('message', handleMessage);
}
Spy.tmiClient.on('subscription', handleSubscription);
Spy.tmiClient.on('resub', handleResub);
Spy.tmiClient.on('cheer', handleCheer);
Spy.tmiClient.on('subgift', handleSubgift);
Spy.tmiClient.on('submysterygift', handleSubmysterygift);
const eventHandlerMap = Spy.setListeners(handle, Events);

// 200ms delay before showing the data:
setIsVisible(false);
Expand All @@ -56,18 +44,13 @@ export default function Logs({ item }: LogsProps) {
}, 200);

return () => {
Spy.tmiClient.removeListener('message', handleMessage);
Spy.tmiClient.removeListener('subscription', handleSubscription);
Spy.tmiClient.removeListener('resub', handleResub);
Spy.tmiClient.removeListener('cheer', handleCheer);
Spy.tmiClient.removeListener('subgift', handleSubgift);
Spy.tmiClient.removeListener('submysterygift', handleSubmysterygift);
Spy.unsetListeners(eventHandlerMap);
setMessageData(() => []);
clearTimeout(timeoutId);
};

// eslint-disable-next-line react-hooks/exhaustive-deps
}, [item]);
}, [target]);

return (
<SectionArea title="Chat Logs">
Expand All @@ -84,7 +67,7 @@ export default function Logs({ item }: LogsProps) {
<i></i>
<i></i>
</div>
<LogsInfo title="Target" data={item} clickable />
<LogsInfo title="Target" data={target} clickable />
<LogsInfo title="Count" data={messageData.length} />
</div>
<div className="relative rounded-b border border-brdr bg-neutral-900 p-1">
Expand Down
29 changes: 22 additions & 7 deletions src/lib/Spy.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import tmi from 'tmi.js';
import tmi, { Events } from 'tmi.js';
import { deleteDB, openDB, IDBPDatabase } from 'idb';

import { DBIndex, Event, Mode } from '@/types';
Expand Down Expand Up @@ -53,32 +53,47 @@ export default class Spy {
}

public setListeners(handler: Chat2Db | Chat2Log, events: readonly Event[]) {
const eventHandlerMap = new Map<keyof Events, any>();

for (const event of events) {
switch (event) {
case 'chat':
this.tmiClient.on('message', handler.onMessage.bind(handler));
eventHandlerMap.set('message', handler.onMessage.bind(handler));
this.tmiClient.on('message', eventHandlerMap.get('message'));
break;
case 'sub':
this.tmiClient.on('subscription', handler.onSubscription.bind(handler));
eventHandlerMap.set('subscription', handler.onSubscription.bind(handler));
this.tmiClient.on('subscription', eventHandlerMap.get('subscription'));
break;
case 'resub':
this.tmiClient.on('resub', handler.onResub.bind(handler));
eventHandlerMap.set('resub', handler.onResub.bind(handler));
this.tmiClient.on('resub', eventHandlerMap.get('resub'));
break;
case 'cheer':
this.tmiClient.on('cheer', handler.onCheer.bind(handler));
eventHandlerMap.set('cheer', handler.onCheer.bind(handler));
this.tmiClient.on('cheer', eventHandlerMap.get('cheer'));
break;
case 'subgift':
this.tmiClient.on('subgift', handler.onSubgift.bind(handler));
this.tmiClient.on('submysterygift', handler.onSubmysterygift.bind(handler));
eventHandlerMap.set('subgift', handler.onSubgift.bind(handler));
this.tmiClient.on('subgift', eventHandlerMap.get('subgift'));
eventHandlerMap.set('submysterygift', handler.onSubmysterygift.bind(handler));
this.tmiClient.on('submysterygift', eventHandlerMap.get('submysterygift'));
break;
}
}
return eventHandlerMap;
}

public async start() {
await this.tmiClient.connect();
}

public unsetListeners(eventMap: Map<keyof Events, () => void>) {
eventMap.forEach((value, key) => {
this.tmiClient.removeListener(key, value);
});
}

public async stop() {
this.tmiClient.removeAllListeners();
await this.tmiClient.disconnect();
Expand Down

0 comments on commit a904310

Please sign in to comment.