Update eslintrc.json to also make it consider typings

note that I've marked Promises awaiting as a warn,
because I don't want to be bothered with it for now.

I also edited all files to accomodate with the new rules.

I should also think find a way to type-safely import Commands directory,
another time
This commit is contained in:
Wroclaw 2023-07-30 22:28:13 +02:00
parent c4676175ff
commit 7225739527
9 changed files with 35 additions and 23 deletions

View file

@ -1,8 +1,15 @@
{
"extends": ["eslint:recommended", "plugin:@typescript-eslint/recommended"],
"extends": ["eslint:recommended", "plugin:@typescript-eslint/recommended-type-checked"],
"parser": "@typescript-eslint/parser",
"parserOptions": {
"project": "./tsconfig.json"
},
"rules": {
"@typescript-eslint/no-floating-promises": "warn",
"@typescript-eslint/no-unsafe-declaration-merging": "warn",
"@typescript-eslint/semi": ["error", "always"],
"eol-last": ["error", "always"]
"semi": "off",
"eol-last": ["error", "always"],
"eqeqeq": ["error", "always"]
}
}

View file

@ -10,7 +10,7 @@ export default class Summon extends Command {
type = ApplicationCommandType.ChatInput;
dm_permission = false;
async execute(interaction: ChatInputCommandInteraction) {
queueRequest(interaction);
execute(interaction: ChatInputCommandInteraction) {
return queueRequest(interaction);
}
}

View file

@ -134,9 +134,9 @@ function canReplyToRequest(request: apiRequest) {
export async function queueRequest(request: apiRequest) {
if (!request.channelId) {
if (request instanceof DiscordApi.Message)
request.reply("request does not have channelId");
await request.reply("request does not have channelId");
else if (request.isRepliable())
request.reply("request does not have channelId");
await request.reply("request does not have channelId");
console.log("There was incoming execution without channelId set, ignoring");
console.log(request);
return;
@ -148,7 +148,7 @@ export async function queueRequest(request: apiRequest) {
if (userLimit !== false && userLimit.remaining <= 0) {
if (request instanceof DiscordApi.Message) {
request.react("🛑").catch(/*it's okay*/);
request.react("🛑").catch(() => { /* NOTE: We send an informaton about limit reached in DM */ });
if (!request.author.dmChannel) await request.author.createDM();
request.author.dmChannel?.send({
embeds: [{
@ -157,13 +157,13 @@ export async function queueRequest(request: apiRequest) {
"You've used up your message limit for today,\n" +
`${userLimit.limit} requests in last 24 hours`,
}]
});
}).catch(() => {/* GRACEFAIL: */});
}
else if (request.isRepliable()) {
request.reply({
content: `You've used up your message limit for today, ${userLimit.limit} requests in last 24 hours`,
ephemeral: true,
});
}).catch(() => { /* Impossible to get there unless connection lost*/ });
}
return;
}
@ -172,7 +172,7 @@ export async function queueRequest(request: apiRequest) {
request.channelId,
() => { return []; },
);
const shouldStart = messagesForChannel.length == 0;
const shouldStart = messagesForChannel.length === 0;
messagesForChannel.push(request as request);
if (shouldStart)
executeFromQueue(request.channelId);
@ -191,7 +191,7 @@ function logUsedTokens(
) {
const usage = answer.data.usage;
const functionName = answer.data.choices[0].message?.function_call?.name;
if (usage != undefined) {
if (usage !== undefined) {
const channelName: string = !message.channel.isDMBased() ? `${message.channel.name} (${message.guild?.name})` : `@${getAuthor(message).tag}`;
console.log(`Used ${usage.total_tokens} (${usage.prompt_tokens} + ${usage.completion_tokens}) tokens for ${getAuthor(message).tag} (${getAuthor(message).id}) in #${channelName}${functionName ? " [Function: " + functionName + "]" : ""}`);
@ -231,7 +231,7 @@ async function executeFromQueue(channel: string) {
messages = messages.filter(m => message.createdTimestamp - m.createdTimestamp < config.limits.time );
messages.forEach(m => Moderation.checkMessage(m));
messages.forEach(m => { Moderation.checkMessage(m); });
if (message instanceof DiscordApi.Message) {
message.channel.sendTyping();
@ -269,7 +269,7 @@ async function executeFromQueue(channel: string) {
const answerContent = answer.data.choices[0].message?.content;
if (answerContent == undefined || answerContent == "") {
if (answerContent === undefined || answerContent === "") {
if (message instanceof DiscordApi.Message) message.react("😶").catch(/*it's okay*/);
}
else {
@ -293,7 +293,7 @@ async function executeFromQueue(channel: string) {
} catch (e) {
console.error(`Error ocurred while handling chat completion request (${(e as object).constructor.name}):`);
console.error(e);
if (OpenAImessages.length != 0) {
if (OpenAImessages.length !== 0) {
console.error("Messages:");
console.error(OpenAImessages);
}
@ -319,7 +319,7 @@ async function executeFromQueue(channel: string) {
}
channelQueue.shift();
if (channelQueue.length == 0)
if (channelQueue.length === 0)
channelsRunning.delete(channel);
else
executeFromQueue(channel);

View file

@ -76,15 +76,18 @@ export default class FunctionManager {
}
try {
// eslint-disable-next-line @typescript-eslint/no-unsafe-assignment
parsedArguments = JSON.parse(request.arguments ?? "");
}
catch (e) {
console.error("Function arguments raw: " + request.arguments);
throw new Error(`Failed to parse the function JSON arguments when running function [${request.name}]`, {cause: e});
}
// FIXME: Verify if the parsedArguments matches the requested function argument declaration.
return {
role: "function",
name: request.name,
// eslint-disable-next-line @typescript-eslint/no-unsafe-argument
content: functionToRun.execute(parsedArguments),
};
}

View file

@ -23,11 +23,11 @@ export const database = new PrismaClient();
const interactionManager = new InteractionManager();
interactionManager.bindClient(discord);
discord.on("ready", async event => {
discord.on("ready", event => {
console.log(`Connected to Discord as ${event.user.tag} (${event.user.id})`);
});
discord.on("messageCreate", async message => {
discord.on("messageCreate", message => {
if (message.author.bot) return;
if (!message.mentions.has(message.client.user)) return;

View file

@ -12,6 +12,7 @@ export default class CommandManager {
try {
// eslint-disable-next-line @typescript-eslint/ban-ts-comment
// @ts-ignore
// eslint-disable-next-line @typescript-eslint/no-unsafe-argument
this.commands.push(new (files[i].default as Command)());
}
catch (e) {
@ -27,13 +28,13 @@ export default class CommandManager {
interaction.isMessageContextMenuCommand() ||
interaction.isUserContextMenuCommand()
) {
const foundCommand = this.commands.find((command) => command.name == interaction.commandName );
const foundCommand = this.commands.find((command) => command.name === interaction.commandName );
if (!foundCommand) throw new Error(`Unknown command received (${interaction.commandName}). Did you forgot to push updated commands?`);
foundCommand.execute(interaction);
return;
}
if (interaction.isAutocomplete()) {
const foundCommand = this.commands.find((command) => command.name == interaction.commandName );
const foundCommand = this.commands.find((command) => command.name === interaction.commandName );
if (!foundCommand) throw new Error(`Unknown command received (${interaction.commandName}). Did you forgot to push updated commands?`);
if (!foundCommand.autocomplete) return;
foundCommand.autocomplete(interaction);

View file

@ -31,11 +31,11 @@ export default class Moderation {
const flagged = answer.data.results[0].flagged;
this.cache.set(message.id, flagged);
if (flagged) if (message instanceof Message) {
message.react("⚠");
message.react("⚠").catch(() => { /* GRACEFAIL: We don't inform the enduser then */ });
}
else {
const channelMessage = await message.fetch();
channelMessage.react("⚠");
channelMessage.react("⚠").catch(() => { /* GRACEFAIL: We don't inform the enduser then */ });
}
return flagged;

View file

@ -14,6 +14,7 @@ requireDirectory<{default: Command}, void>(module, "../commands", {
console.log(obj);
// eslint-disable-next-line @typescript-eslint/ban-ts-comment
// @ts-ignore
// eslint-disable-next-line @typescript-eslint/no-unsafe-argument, @typescript-eslint/no-unsafe-member-access, @typescript-eslint/no-unsafe-call
post.push(new obj.default().toRESTPostApplicationCommands());
},
});
@ -22,7 +23,7 @@ const rest = new REST().setToken(config.tokens.Discord);
(async () => {
const me = await rest.get(Routes.oauth2CurrentApplication()) as RESTGetAPIOAuth2CurrentApplicationResult;
if (guildId && guildId != "") {
if (guildId && guildId !== "") {
console.log(`Started refreshing ${post.length} application guild (${guildId}) commands.`);
await rest.put(
Routes.applicationGuildCommands(me.id, guildId),

View file

@ -108,7 +108,7 @@ export default function toOpenAIMessages(messages: Collection<string, DiscordMes
tokenCount += countTokens(content);
if (tokenCount > config.limits.tokens) break;
rvalue.push({
role: message.author.id == message.client.user.id ? "assistant" : "user",
role: message.author.id === message.client.user.id ? "assistant" : "user",
content: content,
name: getAuthorUsername(message),
});