Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 2 additions & 2 deletions src/commands/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -39,7 +39,7 @@ export const commands = new ManagedCommands<Role, Context, TelemetryContextFlavo
logger.info(
`[ManagedCommands] Command '/${command.trigger}' with scope '${command.scope}' invoked by ${printCtxFrom(context)} in a '${context.chat.type}' chat`
)
await ephemeral(
void ephemeral(
context.reply(
fmt(
({ n }) =>
Expand All @@ -55,7 +55,7 @@ export const commands = new ManagedCommands<Role, Context, TelemetryContextFlavo
`[ManagedCommands] Command '/${command.trigger}' invoked by ${printCtxFrom(context)} without permissions`
)
// Inform the user of restricted access
await ephemeral(context.reply(fmt(({ n }) => n`You are not allowed to execute this command`)))
void ephemeral(context.reply(fmt(({ n }) => n`You are not allowed to execute this command`)))
},
conversationBegin: async ({ context, command, conversation }) => {
const now = await conversation.now()
Expand Down
5 changes: 2 additions & 3 deletions src/commands/invite.ts
Original file line number Diff line number Diff line change
Expand Up @@ -13,9 +13,8 @@ export const invite = new CommandsCollection<Role>().createCommand({
const inviteLink =
chat.invite_link ?? (await api.tg.groups.getById.query({ telegramId: context.chatId }).catch(() => null))?.link

if (!inviteLink)
return await ephemeral(context.reply(fmt(({ n }) => n`❌ Cannot retrieve the invite link`)), 10_000)
if (!inviteLink) return void ephemeral(context.reply(fmt(({ n }) => n`❌ Cannot retrieve the invite link`)), 10_000)

await ephemeral(context.reply(fmt(({ n }) => n`🔗 ${inviteLink}`)))
void ephemeral(context.reply(fmt(({ n }) => n`🔗 ${inviteLink}`)))
},
})
2 changes: 1 addition & 1 deletion src/commands/link-admin-dashboard.ts
Original file line number Diff line number Diff line change
Expand Up @@ -109,6 +109,6 @@ export const linkAdminDashboard = new CommandsCollection<Role>().createCommand({
)
}

await ephemeral(msg)
void ephemeral(msg)
},
})
14 changes: 6 additions & 8 deletions src/commands/moderation/ban.ts
Original file line number Diff line number Diff line change
Expand Up @@ -32,7 +32,7 @@ export const ban = new CommandsCollection<Role>("Banning")
handler: async ({ args, context, repliedTo }) => {
const userOverload = await getOverloadUser(context, repliedTo, args.reasonOrUser, args.reason)
if (userOverload.isErr()) {
await ephemeral(
void ephemeral(
context.reply(
repliedTo
? fmt(({ n }) => n`There was an error`)
Expand All @@ -53,7 +53,7 @@ export const ban = new CommandsCollection<Role>("Banning")
repliedTo ? [repliedTo] : undefined,
reason
)
if (res.isErr()) await ephemeral(context.reply(res.error.fmtError))
if (res.isErr()) void ephemeral(context.reply(res.error.fmtError))
},
})
.createCommand({
Expand Down Expand Up @@ -89,7 +89,7 @@ export const ban = new CommandsCollection<Role>("Banning")
[repliedTo],
args.reason
)
if (res.isErr()) await ephemeral(context.reply(res.error.fmtError))
if (res.isErr()) void ephemeral(context.reply(res.error.fmtError))
},
})
.createCommand({
Expand All @@ -108,18 +108,16 @@ export const ban = new CommandsCollection<Role>("Banning")

if (!userId) {
logger.debug(`unban: no userId for username ${args.username}`)
await ephemeral(context.reply(fmt(({ b }) => b`@${context.from.username} user not found`)))
return
return void ephemeral(context.reply(fmt(({ b }) => b`@${context.from.username} user not found`)))
}

const user = await getUser(userId, context)
if (!user) {
logger.error({ userId }, "UNBAN: cannot retrieve the user")
await ephemeral(context.reply(fmt(({ n }) => [n`Error: cannot find this user`])))
return
return void ephemeral(context.reply(fmt(({ n }) => [n`Error: cannot find this user`])))
}

const res = await Moderation.unban(user, context.chat, context.from)
if (res.isErr()) await ephemeral(context.reply(res.error.fmtError))
if (res.isErr()) void ephemeral(context.reply(res.error.fmtError))
},
})
2 changes: 1 addition & 1 deletion src/commands/moderation/del.ts
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,6 @@ export const del = new CommandsCollection<Role>("Deletion").createCommand({
})

const res = await Moderation.deleteMessages([repliedTo], context.from, "Command /del")
if (res.isErr()) await ephemeral(context.reply(fmt(({ n }) => n`Cannot delete the message`)))
if (res.isErr()) void ephemeral(context.reply(fmt(({ n }) => n`Cannot delete the message`)))
},
})
2 changes: 1 addition & 1 deletion src/commands/moderation/kick.ts
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,6 @@ export const kick = new CommandsCollection<Role>("Kicking").createCommand({
}

const res = await Moderation.kick(repliedTo.from, context.chat, context.from, [repliedTo], args.reason)
if (res.isErr()) await ephemeral(context.reply(res.error.fmtError))
if (res.isErr()) void ephemeral(context.reply(res.error.fmtError))
},
})
14 changes: 6 additions & 8 deletions src/commands/moderation/mute.ts
Original file line number Diff line number Diff line change
Expand Up @@ -42,7 +42,7 @@ export const mute = new CommandsCollection<Role>("Muting")
[repliedTo],
args.reason
)
if (res.isErr()) await ephemeral(context.reply(res.error.fmtError))
if (res.isErr()) void ephemeral(context.reply(res.error.fmtError))
},
})
.createCommand({
Expand All @@ -68,7 +68,7 @@ export const mute = new CommandsCollection<Role>("Muting")
handler: async ({ args, context, repliedTo }) => {
const userOverload = await getOverloadUser(context, repliedTo, args.reasonOrUser, args.reason)
if (userOverload.isErr()) {
await ephemeral(
void ephemeral(
context.reply(
repliedTo
? fmt(({ n }) => n`There was an error`)
Expand All @@ -89,7 +89,7 @@ export const mute = new CommandsCollection<Role>("Muting")
repliedTo ? [repliedTo] : undefined,
reason
)
if (res.isErr()) await ephemeral(context.reply(res.error.fmtError))
if (res.isErr()) void ephemeral(context.reply(res.error.fmtError))
},
})
.createCommand({
Expand All @@ -108,19 +108,17 @@ export const mute = new CommandsCollection<Role>("Muting")
if (!userId) {
logger.debug(`unmute: no userId for username ${args.username}`)
const msg = await context.reply(fmt(({ b }) => b`@${context.from.username} user not found`))
await ephemeral(msg)
return
return void ephemeral(msg)
}

const user = await getUser(userId, context)
if (!user) {
const msg = await context.reply(fmt(({ n }) => n`Error: cannot find this user`))
logger.error({ userId }, "UNMUTE: cannot retrieve the user")
await ephemeral(msg)
return
return void ephemeral(msg)
}

const res = await Moderation.unmute(user, context.chat, context.from)
if (res.isErr()) await ephemeral(context.reply(res.error.fmtError))
if (res.isErr()) void ephemeral(context.reply(res.error.fmtError))
},
})
17 changes: 8 additions & 9 deletions src/commands/pin.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,4 @@
import { CommandsCollection } from "@/lib/managed-commands"
import { logger } from "@/logger"
import { fmt } from "@/utils/format"
import { ephemeral } from "@/utils/messages"
import type { Role } from "@/utils/types"
Expand All @@ -17,18 +16,18 @@ export const pin = new CommandsCollection<Role>()
handler: async ({ context, repliedTo }) => {
const member = await context.getChatMember(context.me.id)
if (member.status !== "administrator")
return await ephemeral(context.reply(fmt(({ n }) => n`❌ The bot is not an admin`)), 10_000)
return void ephemeral(context.reply(fmt(({ n }) => n`❌ The bot is not an admin`)), 10_000)

if (!member.can_pin_messages)
return await ephemeral(
return void ephemeral(
context.reply(fmt(({ n, code }) => n`❌ The bot is missing the ${code`Pin messages`} permission.`)),
10_000
)

const res = await context.pinChatMessage(repliedTo.message_id).catch(() => false)
if (!res) return await ephemeral(context.reply(fmt(({ n }) => n`❌ Cannot pin the message`)), 10_000)
if (!res) return void ephemeral(context.reply(fmt(({ n }) => n`❌ Cannot pin the message`)), 10_000)

await ephemeral(context.reply(fmt(({ n }) => n`✅ Message pinned`)), 10_000)
void ephemeral(context.reply(fmt(({ n }) => n`✅ Message pinned`)), 10_000)
},
})
.createCommand({
Expand All @@ -43,17 +42,17 @@ export const pin = new CommandsCollection<Role>()
handler: async ({ context, repliedTo }) => {
const member = await context.getChatMember(context.me.id)
if (member.status !== "administrator")
return await ephemeral(context.reply(fmt(({ n }) => n`❌ The bot is not an admin`)), 10_000)
return void ephemeral(context.reply(fmt(({ n }) => n`❌ The bot is not an admin`)), 10_000)

if (!member.can_pin_messages)
return await ephemeral(
return void ephemeral(
context.reply(fmt(({ n, code }) => n`❌ The bot is missing the ${code`Pin messages`} permission.`)),
10_000
)

const res = await context.unpinChatMessage(repliedTo.message_id).catch(() => false)
if (!res) return await ephemeral(context.reply(fmt(({ n }) => n`❌ Cannot unpin the message`)), 10_000)
if (!res) return void ephemeral(context.reply(fmt(({ n }) => n`❌ Cannot unpin the message`)), 10_000)

await ephemeral(context.reply(fmt(({ n }) => n`✅ Message unpinned`)), 10_000)
void ephemeral(context.reply(fmt(({ n }) => n`✅ Message unpinned`)), 10_000)
},
})
6 changes: 2 additions & 4 deletions src/lib/managed-commands/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -365,13 +365,11 @@ export class ManagedCommands<
)

this.composer.command("help", async (ctx) => {
if (ctx.chat.type !== "private") {
await ephemeral(
if (ctx.chat.type !== "private")
return void ephemeral(
ctx.reply(fmt(({ n, code }) => n`You can only send ${code`/help`} in private chat with the bot.`)),
10_000
)
return
}

const text = ctx.message?.text ?? ""

Expand Down
11 changes: 6 additions & 5 deletions src/utils/messages.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
import type { MessageXFragment } from "@grammyjs/hydrate/out/data/message"
import type { Message, User } from "grammy/types"
import type { MaybePromise } from "./types"
import { modules } from "@/modules"
import type { MaybePromise, PartialMessage } from "./types"
import { wait } from "./wait"

type TextReturn<M extends Message> = M extends { text: string }
Expand Down Expand Up @@ -47,9 +47,10 @@ export function createFakeMessage(chatId: number, messageId: number, from: User,
* @param timeout Timeout in ms, defaults to 20 seconds
* @returns a void promise that resolves after the message is deleted (or if the deletion fails)
*/
export async function ephemeral(message: MaybePromise<MessageXFragment>, timeout = 20000): Promise<void> {
const msg = await Promise.resolve(message)
export async function ephemeral(message: MaybePromise<PartialMessage>, timeout = 20000): Promise<void> {
const msg = await Promise.resolve(message).catch(() => null)
if (!msg) return
await wait(timeout)
.then(() => msg.delete())
.then(() => modules.shared.api.deleteMessage(msg.chat.id, msg.message_id))
.catch(() => {})
}
5 changes: 5 additions & 0 deletions src/utils/types.ts
Original file line number Diff line number Diff line change
Expand Up @@ -42,3 +42,8 @@ export const toGrammyUser = (apiUser: Exclude<ApiOutput["tg"]["users"]["get"]["u
is_premium: undefined,
added_to_attachment_menu: undefined,
})

export type PartialMessage = {
message_id: number
chat: { id: number }
}
1 change: 0 additions & 1 deletion src/utils/users.ts
Original file line number Diff line number Diff line change
@@ -1,7 +1,6 @@
import type { Context } from "grammy"
import type { Message, User } from "grammy/types"
import { Err, Ok, type Result } from "neverthrow"
import { logger } from "@/logger"
import { MessageUserStorage } from "@/middlewares/message-user-storage"
import { getTelegramId } from "./telegram-id"

Expand Down
Loading