调用interaction.options.getSubcommand()遇TS类型错误,如何解决?
Discord.js TypeScript调用getSubcommand()报错的解决方法
错误信息
Property 'getSubcommand' does not exist on type 'Omit<CommandInteractionOptionResolver
, "getMessage" | "getFocused" | "getMentionable" | "getRole" | "getAttachment" | ... 6 more ... | "getSubcommand">'.
你的代码
Hello.ts
import { CommandInteraction, CommandInteractionOptionResolver, SlashCommandBuilder, } from "discord.js"; import { CustomClient } from "../Client"; import { Command } from "../Command"; export default class HelloCommand extends Command { public constructor(client: CustomClient) { super(client, { name: "hello", description: "Says hello to user.", }); } public getOptions() { return new SlashCommandBuilder() .setName(this.name) .setDescription(this.description) .addSubcommand((subcommand) => subcommand.setName("say").setDescription("Say hello to someone.") ) as SlashCommandBuilder; } public async execute(interaction: CommandInteraction): Promise<void> { const subcommand = interaction.options.getSubcommand(); if (subcommand === "say") { interaction.reply({ content: `Hello, ${interaction.user.username}` }); } } }
Command.ts
import { CommandInteraction, PermissionResolvable } from "discord.js"; import { CustomClient } from "./Client"; import { SlashCommandBuilder } from "@discordjs/builders"; interface CommandOptions { name: string; description: string; permission?: PermissionResolvable; } export abstract class Command { public client: CustomClient; public name: string; public description: string; public permission?: PermissionResolvable; constructor(client: CustomClient, props: CommandOptions) { this.client = client; this.name = props.name; this.description = props.description; this.permission = props.permission; } abstract getOptions(): SlashCommandBuilder; abstract execute(interaction: CommandInteraction): any; }
问题原因
你在Command.ts中使用了宽泛的CommandInteraction类型作为execute方法的参数,但这个类型包含了上下文菜单命令(ContextMenuCommandInteraction)这类没有子命令的交互类型。TypeScript无法确定传入的交互一定是带有子命令的斜杠命令,因此会将getSubcommand()这类仅斜杠命令支持的方法从类型中排除,导致报错。
解决方法
将Command.ts和Hello.ts中的交互类型替换为**ChatInputCommandInteraction**——这是专门用于斜杠命令的交互类型,TypeScript会默认其支持子命令相关方法。
修改后的Command.ts
import { ChatInputCommandInteraction, PermissionResolvable } from "discord.js"; import { CustomClient } from "./Client"; import { SlashCommandBuilder } from "@discordjs/builders"; interface CommandOptions { name: string; description: string; permission?: PermissionResolvable; } export abstract class Command { public client: CustomClient; public name: string; public description: string; public permission?: PermissionResolvable; constructor(client: CustomClient, props: CommandOptions) { this.client = client; this.name = props.name; this.description = props.description; this.permission = props.permission; } abstract getOptions(): SlashCommandBuilder; abstract execute(interaction: ChatInputCommandInteraction): any; }
修改后的Hello.ts
import { ChatInputCommandInteraction, SlashCommandBuilder, } from "discord.js"; import { CustomClient } from "../Client"; import { Command } from "../Command"; export default class HelloCommand extends Command { public constructor(client: CustomClient) { super(client, { name: "hello", description: "Says hello to user.", }); } public getOptions() { return new SlashCommandBuilder() .setName(this.name) .setDescription(this.description) .addSubcommand((subcommand) => subcommand.setName("say").setDescription("Say hello to someone.") ) as SlashCommandBuilder; } public async execute(interaction: ChatInputCommandInteraction): Promise<void> { const subcommand = interaction.options.getSubcommand(); if (subcommand === "say") { interaction.reply({ content: `Hello, ${interaction.user.username}` }); } } }
这样修改后,TypeScript就能正确识别interaction.options包含getSubcommand()方法,报错会消失。
内容的提问来源于stack exchange,提问作者Meenic
相关产品推荐
相关产品推荐

