Skip to content
This repository has been archived by the owner on Apr 24, 2024. It is now read-only.

Commit

Permalink
Implement event handler binder
Browse files Browse the repository at this point in the history
  • Loading branch information
aronson committed Oct 21, 2023
1 parent 5ee3218 commit 4f47be2
Show file tree
Hide file tree
Showing 2 changed files with 36 additions and 15 deletions.
2 changes: 2 additions & 0 deletions lib/deps.ts
Original file line number Diff line number Diff line change
Expand Up @@ -41,3 +41,5 @@ export { Dlog };
export { PKAPI } from 'https://raw.githubusercontent.com/aronson/pkapi.ts/main/lib/mod.ts';
// Queue
export { Queue } from 'https://deno.land/x/queue@1.2.0/mod.ts';
// Event handler
export { Reflect } from 'https://deno.land/x/reflect_metadata@v0.1.12/mod.ts';
49 changes: 34 additions & 15 deletions lib/ircListeners.ts
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,14 @@ import {
RemoteAddr,
} from './deps.ts';
import { Dictionary, forEachAsync, tuple } from './helpers.ts';
import { Reflect } from './deps.ts';

// deno-lint-ignore no-explicit-any
type Constructor<T = unknown> = new (...args: any[]) => T;

function decorator<T>(_: Constructor<T>): void {}

@decorator
export class CustomIrcClient extends IrcClient {
channelUsers: Dictionary<string[]>;
channelMapping: ChannelMapper;
Expand All @@ -46,22 +53,20 @@ export class CustomIrcClient extends IrcClient {
this.ircStatusNotices = bot.config.ircStatusNotices;
this.announceSelfJoin = bot.config.announceSelfJoin;
this.exiting = () => bot.exiting;
this.on('register', this.onRegister.bind(this));
this.on('error', this.onError.bind(this));
this.on('privmsg:channel', this.onPrivMessage.bind(this));
this.on('notice', this.onNotice.bind(this));
this.on('nick', this.onNick.bind(this));
this.on('join', this.onJoin.bind(this));
this.on('part', this.onPart.bind(this));
this.on('quit', this.onQuit.bind(this));
this.on('nicklist', this.onNicklist.bind(this));
this.on('ctcp_action', this.onAction.bind(this));
this.on('invite', this.onInvite.bind(this));
this.on('connecting', this.onConnecting.bind(this));
this.on('connected', this.onConnected.bind(this));
this.on('disconnected', this.onDisconnected.bind(this));
this.on('reconnecting', this.onReconnecting.bind(this));
this.bindEvents();
}
// Bind event handlers to base client through Reflect metadata and bind each handler to this instance
bindEvents() {
for (const key of Object.getOwnPropertyNames(Object.getPrototypeOf(this))) {
const event = Reflect.getMetadata('event', this, key);
if (event) {
// deno-lint-ignore ban-types
const handler = this[key as keyof typeof this] as Function;
this.on(event, handler.bind(this));
}
}
}
@Reflect.metadata('event', 'connecting')
onConnecting(addr: RemoteAddr) {
this.logger.info(
`Connecting to IRC server ${addr.hostname}:${addr.port} ${
Expand All @@ -70,9 +75,11 @@ export class CustomIrcClient extends IrcClient {
}`,
);
}
@Reflect.metadata('event', 'connected')
onConnected(addr: RemoteAddr) {
this.logger.done(`Connected to IRC server ${addr.hostname}:${addr.port}`);
}
@Reflect.metadata('event', 'register')
onRegister(message: RegisterEvent) {
this.logger.done('Registered to IRC server.');
this.debug && this.logger.debug(
Expand Down Expand Up @@ -107,24 +114,28 @@ export class CustomIrcClient extends IrcClient {
this.join(firstChannel);
}
}
@Reflect.metadata('event', 'error')
onError(error: ClientError) {
this.logger.error(
`Received error event from IRC\n${JSON.stringify(error, null, 2)}`,
);
}
@Reflect.metadata('event', 'privmsg:channel')
async onPrivMessage(event: PrivmsgEvent) {
await this.sendToDiscord(
event.source?.name ?? '',
event.params.target,
event.params.text,
);
}
@Reflect.metadata('event', 'notice')
onNotice(event: NoticeEvent) {
this.debug &&
this.logger.debug(
`Received notice:\n${JSON.stringify(event.params.text)}`,
);
}
@Reflect.metadata('event', 'nick')
onNick(event: NickEvent) {
this.channelMapping?.discordIdToMapping.forEach((channelMapping) => {
const channelName = channelMapping.ircChannel;
Expand All @@ -150,6 +161,7 @@ export class CustomIrcClient extends IrcClient {
}
});
}
@Reflect.metadata('event', 'join')
async onJoin(event: JoinEvent) {
const channelName = event.params.channel;
const nick = event.source?.name ?? '';
Expand All @@ -176,6 +188,7 @@ export class CustomIrcClient extends IrcClient {
`*${nick}* has joined the connected IRC channel`,
);
}
@Reflect.metadata('event', 'part')
async onPart(event: PartEvent) {
const channelName = event.params.channel;
const nick = event.source?.name ?? '';
Expand Down Expand Up @@ -207,6 +220,7 @@ export class CustomIrcClient extends IrcClient {
`*${nick}* has left the connected IRC channel (${reason})`,
);
}
@Reflect.metadata('event', 'quit')
onQuit(event: QuitEvent) {
const nick = event.source?.name ?? '';
const reason = event.params.comment ?? '';
Expand Down Expand Up @@ -235,6 +249,7 @@ export class CustomIrcClient extends IrcClient {
);
});
}
@Reflect.metadata('event', 'nicklist')
onNicklist(event: NicklistEvent) {
const channelName = event.params.channel;
const nicks = event.params.nicklist;
Expand All @@ -244,13 +259,15 @@ export class CustomIrcClient extends IrcClient {
const channel = channelName.toLowerCase();
this.channelUsers[channel] = nicks.map((n) => n.nick);
}
@Reflect.metadata('event', 'ctcp_action')
async onAction(event: CtcpActionEvent) {
await this.sendToDiscord(
event.source?.name ?? '',
event.params.target,
`_${event.params.text}_`,
);
}
@Reflect.metadata('event', 'invite')
onInvite(event: InviteEvent) {
const channel = event.params.channel;
const from = event.params.nick;
Expand All @@ -264,6 +281,7 @@ export class CustomIrcClient extends IrcClient {
this.debug && this.logger.debug(`Joining channel: ${channel}`);
}
}
@Reflect.metadata('event', 'disconnected')
onDisconnected(addr: RemoteAddr) {
const message = `Disconnected from server ${addr.hostname}:${addr.port}`;
if (this.exiting()) {
Expand All @@ -272,6 +290,7 @@ export class CustomIrcClient extends IrcClient {
this.logger.error(message + '!');
}
}
@Reflect.metadata('event', 'reconnecting')
onReconnecting(addr: RemoteAddr) {
this.logger.info(
`Attempting to reconnect to server ${addr.hostname}:${addr.port}...`,
Expand Down

0 comments on commit 4f47be2

Please sign in to comment.