Skip to content

Commit

Permalink
fix(bot): don't throw if channel couldn't be found (#397)
Browse files Browse the repository at this point in the history
  • Loading branch information
CarelessInternet authored Sep 7, 2024
1 parent cd65d2d commit d1e44f1
Show file tree
Hide file tree
Showing 20 changed files with 365 additions and 265 deletions.
2 changes: 1 addition & 1 deletion apps/bot/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,6 @@
"devDependencies": {
"@eslint/eslintrc": "^3.1.0",
"@ticketer/eslint-config": "workspace:*",
"@types/node": "^22.5.2"
"@types/node": "^22.5.4"
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,7 @@ import {
automaticThreadsEmbed,
automaticThreadsOpeningMessageDescription,
automaticThreadsOpeningMessageTitle,
fetchChannel,
goToPage,
messageWithPagination,
withPagination,
Expand Down Expand Up @@ -473,9 +474,9 @@ export class ModalInteraction extends Modal.Interaction {
@DeferReply()
private async createConfigurationOrUpdateOpeningMessage({ interaction }: Modal.Context) {
const { dynamicValue } = super.extractCustomId(interaction.customId, true);
const channel = await interaction.guild.channels.fetch(dynamicValue);
const channel = await fetchChannel(interaction.guild, dynamicValue);

if (!channel || channel.type !== ChannelType.GuildText) {
if (channel?.type !== ChannelType.GuildText) {
return interaction.editReply({
embeds: [super.userEmbedError(interaction.user).setDescription('The channel is not a text channel.')],
});
Expand Down
5 changes: 3 additions & 2 deletions apps/bot/src/commands/staff/configuration-user-forums.ts
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@ import {
userForumsConfigurationsSelectSchema,
} from '@ticketer/database';
import {
fetchChannel,
goToPage,
messageWithPagination,
userForumEmbed,
Expand Down Expand Up @@ -479,9 +480,9 @@ export class ModalInteraction extends Modal.Interaction {
@DeferReply()
private async createConfigurationOrUpdateOpeningMessage({ interaction }: Modal.Context) {
const { dynamicValue } = super.extractCustomId(interaction.customId, true);
const channel = await interaction.guild.channels.fetch(dynamicValue);
const channel = await fetchChannel(interaction.guild, dynamicValue);

if (!channel || channel.type !== ChannelType.GuildForum) {
if (channel?.type !== ChannelType.GuildForum) {
return interaction.editReply({
embeds: [super.userEmbedError(interaction.user).setDescription('The channel is not a forum channel.')],
});
Expand Down
4 changes: 2 additions & 2 deletions apps/bot/src/commands/thread-ticketing/panel.ts
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@ import {
TextInputStyle,
} from 'discord.js';
import { Command, DeferReply, Modal } from '@ticketer/djs-framework';
import { extractEmoji, zodErrorToString } from '@/utils';
import { extractEmoji, fetchChannel, zodErrorToString } from '@/utils';
import { z } from 'zod';

export default class extends Command.Interaction {
Expand Down Expand Up @@ -102,7 +102,7 @@ export class ModalInteraction extends Modal.Interaction {
}

const { dynamicValue: channelId } = super.extractCustomId(customId, true);
const channel = await guild.channels.fetch(channelId);
const channel = await fetchChannel(guild, channelId);

if (!channel?.isTextBased()) {
return interaction.editReply({
Expand Down
4 changes: 2 additions & 2 deletions apps/bot/src/commands/thread-ticketing/ticket.ts
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@ import {
ticketThreadsCategoriesSelectSchema,
ticketsThreads,
} from '@ticketer/database';
import { ThreadTicketing, zodErrorToString } from '@/utils';
import { ThreadTicketing, fetchChannel, zodErrorToString } from '@/utils';
import { getTranslations, translate } from '@/i18n';
import { z } from 'zod';

Expand Down Expand Up @@ -358,7 +358,7 @@ export class ModalInteraction extends Modal.Interaction {

if (row.logsChannelId) {
const me = await guild.members.fetchMe();
const logsChannel = await guild.channels.fetch(row.logsChannelId);
const logsChannel = await fetchChannel(guild, row.logsChannelId);

if (!logsChannel?.isTextBased()) return;
if (!logsChannel.permissionsFor(me).has([PermissionFlagsBits.ViewChannel, PermissionFlagsBits.SendMessages]))
Expand Down
6 changes: 3 additions & 3 deletions apps/bot/src/events/guild/GuildMemberAdd.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import { LogExceptions, welcomeEmbed } from '@/utils';
import { LogExceptions, fetchChannel, welcomeEmbed } from '@/utils';
import { database, eq, welcomeAndFarewell } from '@ticketer/database';
import { Event } from '@ticketer/djs-framework';
import { PermissionFlagsBits } from 'discord.js';
Expand All @@ -8,12 +8,12 @@ export default class extends Event.Handler {

@LogExceptions
public async execute([member]: Event.ArgumentsOf<this['name']>) {
const { channels, id: guildId, members, preferredLocale, roles } = member.guild;
const { id: guildId, members, preferredLocale, roles } = member.guild;
const [data] = await database.select().from(welcomeAndFarewell).where(eq(welcomeAndFarewell.guildId, guildId));

if (!data?.welcomeChannelId || !data.welcomeEnabled) return;

const channel = await channels.fetch(data.welcomeChannelId);
const channel = await fetchChannel(member.guild, data.welcomeChannelId);

if (!channel?.isTextBased()) return;

Expand Down
6 changes: 3 additions & 3 deletions apps/bot/src/events/guild/GuildMemberRemove.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import { LogExceptions, farewellEmbed } from '@/utils';
import { LogExceptions, farewellEmbed, fetchChannel } from '@/utils';
import { database, eq, welcomeAndFarewell } from '@ticketer/database';
import { Event } from '@ticketer/djs-framework';
import { PermissionFlagsBits } from 'discord.js';
Expand All @@ -8,12 +8,12 @@ export default class extends Event.Handler {

@LogExceptions
public async execute([member]: Event.ArgumentsOf<this['name']>) {
const { channels, id: guildId, members, preferredLocale } = member.guild;
const { id: guildId, members, preferredLocale } = member.guild;
const [data] = await database.select().from(welcomeAndFarewell).where(eq(welcomeAndFarewell.guildId, guildId));

if (!data?.farewellChannelId || !data.farewellEnabled) return;

const channel = await channels.fetch(data.farewellChannelId);
const channel = await fetchChannel(member.guild, data.farewellChannelId);

if (!channel?.isTextBased()) return;

Expand Down
4 changes: 2 additions & 2 deletions apps/bot/src/events/guild/ThreadCreate.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import { ChannelType, PermissionFlagsBits } from 'discord.js';
import { LogExceptions, ticketButtons, userForumEmbed } from '@/utils';
import { LogExceptions, fetchChannel, ticketButtons, userForumEmbed } from '@/utils';
import { database, eq, userForumsConfigurations } from '@ticketer/database';
import { Event } from '@ticketer/djs-framework';
import { translate } from '@/i18n';
Expand All @@ -11,7 +11,7 @@ export default class extends Event.Handler {
public async execute([thread, newlyCreated]: Event.ArgumentsOf<this['name']>) {
if (!newlyCreated || !thread.parentId) return;

const parent = thread.parent ?? (await thread.guild.channels.fetch(thread.parentId));
const parent = thread.parent ?? (await fetchChannel(thread.guild, thread.parentId));
const me = await thread.guild.members.fetchMe();

if (!parent?.permissionsFor(me).has([PermissionFlagsBits.ViewChannel, PermissionFlagsBits.SendMessagesInThreads]))
Expand Down
3 changes: 2 additions & 1 deletion apps/bot/src/utils/thread-ticketing/closeTicket.ts
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ import {
ticketThreadsCategories,
ticketsThreads,
} from '@ticketer/database';
import { fetchChannel } from '..';
import { translate } from '@/i18n';

export async function closeTicket(
Expand Down Expand Up @@ -83,7 +84,7 @@ export async function closeTicket(

if (row.logsChannelId) {
const me = await guild.members.fetchMe();
const logsChannel = await guild.channels.fetch(row.logsChannelId);
const logsChannel = await fetchChannel(guild, row.logsChannelId);

if (!logsChannel?.isTextBased()) return;
if (!logsChannel.permissionsFor(me).has([PermissionFlagsBits.ViewChannel, PermissionFlagsBits.SendMessages]))
Expand Down
9 changes: 5 additions & 4 deletions apps/bot/src/utils/thread-ticketing/createTicket.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
import type { BaseInteraction, Command, Component, Modal } from '@ticketer/djs-framework';

import {
ChannelType,
Colors,
Expand All @@ -20,7 +21,7 @@ import {
ticketThreadsConfigurations,
ticketsThreads,
} from '@ticketer/database';
import { formatDateShort, ticketButtons, ticketThreadsOpeningMessageEmbed, zodErrorToString } from '..';
import { fetchChannel, formatDateShort, ticketButtons, ticketThreadsOpeningMessageEmbed, zodErrorToString } from '..';
import { translate } from '@/i18n';
import { z } from 'zod';

Expand Down Expand Up @@ -121,9 +122,9 @@ export async function createTicket(
});
}

const channel = await guild.channels.fetch(configuration.ticketThreadsCategories.channelId ?? '');
const channel = await fetchChannel(guild, configuration.ticketThreadsCategories.channelId);

if (!channel || channel.type !== ChannelType.GuildText) {
if (channel?.type !== ChannelType.GuildText) {
return interaction.editReply({
components: [],
embeds: [
Expand Down Expand Up @@ -314,7 +315,7 @@ export async function createTicket(
await interaction.editReply({ components: [], embeds: [ticketCreatedEmbed] });

if (configuration.ticketThreadsCategories.logsChannelId) {
const logsChannel = await guild.channels.fetch(configuration.ticketThreadsCategories.logsChannelId);
const logsChannel = await fetchChannel(guild, configuration.ticketThreadsCategories.logsChannelId);

if (!logsChannel?.isTextBased()) return;
if (!logsChannel.permissionsFor(me).has([PermissionFlagsBits.ViewChannel, PermissionFlagsBits.SendMessages]))
Expand Down
3 changes: 2 additions & 1 deletion apps/bot/src/utils/thread-ticketing/deleteTicket.ts
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ import {
ticketThreadsCategories,
ticketsThreads,
} from '@ticketer/database';
import { fetchChannel } from '..';
import { translate } from '@/i18n';

export async function deleteTicket(
Expand Down Expand Up @@ -83,7 +84,7 @@ export async function deleteTicket(

if (row.logsChannelId) {
const me = await guild.members.fetchMe();
const logsChannel = await guild.channels.fetch(row.logsChannelId);
const logsChannel = await fetchChannel(guild, row.logsChannelId);

if (!logsChannel?.isTextBased()) return;
if (!logsChannel.permissionsFor(me).has([PermissionFlagsBits.ViewChannel, PermissionFlagsBits.SendMessages]))
Expand Down
3 changes: 2 additions & 1 deletion apps/bot/src/utils/thread-ticketing/lockTicket.ts
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ import {
ticketThreadsCategories,
ticketsThreads,
} from '@ticketer/database';
import { fetchChannel } from '..';
import { translate } from '@/i18n';

export async function lockTicket(
Expand Down Expand Up @@ -95,7 +96,7 @@ export async function lockTicket(

if (row.logsChannelId) {
const me = await guild.members.fetchMe();
const logsChannel = await guild.channels.fetch(row.logsChannelId);
const logsChannel = await fetchChannel(guild, row.logsChannelId);

if (!logsChannel?.isTextBased()) return;
if (!logsChannel.permissionsFor(me).has([PermissionFlagsBits.ViewChannel, PermissionFlagsBits.SendMessages]))
Expand Down
12 changes: 12 additions & 0 deletions apps/bot/src/utils/utility/fetchChannel.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
import { DiscordAPIError, type Guild, RESTJSONErrorCodes, type Snowflake } from 'discord.js';

// This async (<-- important) function prevents the bot from crashing if the channel is not found.
export async function fetchChannel(guild: Guild, id?: Snowflake | null) {
if (!id) return;

try {
return await guild.channels.fetch(id);
} catch (error) {
if (error instanceof DiscordAPIError && error.code === RESTJSONErrorCodes.UnknownChannel) return;
}
}
1 change: 1 addition & 0 deletions apps/bot/src/utils/utility/index.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
export * from './capitalise';
export * from './DeepPartial';
export * from './extractEmoji';
export * from './fetchChannel';
export * from './format';
export * from './goToPage';
export * from './invalidTicket';
Expand Down
10 changes: 5 additions & 5 deletions apps/website/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -20,8 +20,8 @@
"@vercel/speed-insights": "^1.0.12",
"class-variance-authority": "^0.7.0",
"clsx": "^2.1.1",
"lucide-react": "^0.438.0",
"next": "14.2.7",
"lucide-react": "^0.439.0",
"next": "14.2.8",
"next-themes": "^0.3.0",
"react": "^18.3.1",
"react-dom": "^18.3.1",
Expand All @@ -31,13 +31,13 @@
"devDependencies": {
"@eslint/compat": "^1.1.1",
"@eslint/eslintrc": "^3.1.0",
"@next/eslint-plugin-next": "^14.2.7",
"@next/eslint-plugin-next": "^14.2.8",
"@ticketer/eslint-config": "workspace:*",
"@types/node": "^22.5.2",
"@types/node": "^22.5.4",
"@types/react": "^18.3.5",
"@types/react-dom": "^18.3.0",
"autoprefixer": "^10.4.20",
"postcss": "^8.4.44",
"postcss": "^8.4.45",
"tailwindcss": "^3.4.10",
"typescript": "^5.5.4"
}
Expand Down
2 changes: 1 addition & 1 deletion package.json
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,7 @@
"prettier": "prettier --write \"apps/**/*.{ts,tsx,js,jsx}\" \"packages/**/*.{ts,tsx,js,jsx}\""
},
"devDependencies": {
"eslint": "^9.9.1",
"eslint": "^9.10.0",
"prettier": "^3.3.3",
"prettier-plugin-tailwindcss": "^0.6.6",
"turbo": "^2.1.1"
Expand Down
2 changes: 1 addition & 1 deletion packages/djs-framework/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,7 @@
},
"devDependencies": {
"@ticketer/eslint-config": "workspace:*",
"@types/node": "^22.5.2",
"@types/node": "^22.5.4",
"tsx": "^4.19.0"
}
}
2 changes: 1 addition & 1 deletion packages/env/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,6 @@
},
"devDependencies": {
"@ticketer/eslint-config": "workspace:*",
"@types/node": "^22.5.2"
"@types/node": "^22.5.4"
}
}
6 changes: 3 additions & 3 deletions packages/eslint-config/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -6,14 +6,14 @@
"devDependencies": {
"@eslint/compat": "^1.1.1",
"@eslint/eslintrc": "^3.1.0",
"@eslint/js": "^9.9.1",
"@eslint/js": "^9.10.0",
"@types/eslint__js": "^8.42.3",
"eslint-config-next": "^14.2.7",
"eslint-config-next": "^14.2.8",
"eslint-config-prettier": "^9.1.0",
"eslint-config-turbo": "^2.1.1",
"eslint-plugin-drizzle": "^0.2.3",
"eslint-plugin-prettier": "^5.2.1",
"eslint-plugin-react": "^7.35.1",
"eslint-plugin-react": "^7.35.2",
"eslint-plugin-unicorn": "^55.0.0",
"typescript-eslint": "^8.4.0"
}
Expand Down
Loading

0 comments on commit d1e44f1

Please sign in to comment.