You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Discord.js抽奖机器人开发需求:等待抽奖结束后执行操作

让Discord机器人在抽奖期间等待直至结束的实现方案

看起来你想实现一个Discord抽奖机器人,让它发起抽奖后进入等待状态,直到设定的时长结束再自动抽取获奖者。我来帮你完善代码,实现这个核心功能:

const Discord = require('discord.js');
// Discord.js v13+需要声明所需权限(intents),否则无法接收消息和反应事件
const client = new Discord.Client({ 
    intents: [
        Discord.Intents.FLAGS.GUILDS, 
        Discord.Intents.FLAGS.GUILD_MESSAGES, 
        Discord.Intents.FLAGS.GUILD_MESSAGE_REACTIONS
    ] 
});
const config = require("./config.json");
const prefix = config.prefix;

client.login(config.token);

client.on('ready', () => { 
    console.log('机器人已上线,准备处理抽奖活动!'); 
});

// 封装延迟函数,用async/await实现更易读的等待逻辑
const delay = ms => new Promise(resolve => setTimeout(resolve, ms));

// v13+版本事件名改为messageCreate,替代旧版的message
client.on('messageCreate', async message => { 
    // 忽略非前缀命令和机器人自身消息
    if (!message.content.startsWith(prefix) || message.author.bot) return;

    const args = message.content.slice(prefix.length).trim().split(/ +/g);
    const command = args.shift().toLowerCase();

    // 抽奖命令示例:!giveaway 60s 游戏皮肤
    if (command === 'giveaway') {
        // 检查参数是否完整
        if (!args[0] || !args[1]) {
            return message.reply('请正确使用命令:`!giveaway 时长(如60s/5m) 奖品名称`');
        }

        // 解析用户输入的时长(支持秒s/分钟m)
        const timeArg = args[0];
        const timeUnit = timeArg.slice(-1);
        const timeValue = parseInt(timeArg.slice(0, -1));
        let giveawayDuration;

        switch(timeUnit) {
            case 's':
                giveawayDuration = timeValue * 1000;
                break;
            case 'm':
                giveawayDuration = timeValue * 60 * 1000;
                break;
            default:
                return message.reply('时长格式错误,请用`s`(秒)或`m`(分钟),比如`60s`或`5m`');
        }

        const prize = args.slice(1).join(' ');

        // 发送抽奖启动消息并添加参与反应
        const giveawayMsg = await message.channel.send(
            `🎉 **抽奖开始!** 🎉\n奖品:${prize}\n参与方式:点击下方🎉反应\n抽奖将在${timeArg}后结束!`
        );
        await giveawayMsg.react('🎉');

        message.channel.send(`抽奖已启动,将在${timeArg}后自动抽取获奖者!`);

        // 核心:让机器人等待抽奖时长结束
        await delay(giveawayDuration);

        // 重新获取消息确保反应数据最新
        const fetchedMsg = await message.channel.messages.fetch(giveawayMsg.id);
        const reaction = fetchedMsg.reactions.cache.get('🎉');
        if (!reaction) {
            return message.channel.send('抽奖过程出错,无法获取参与者数据!');
        }

        // 筛选出所有参与的真实用户(排除机器人)
        const users = await reaction.users.fetch();
        const participants = users.filter(user => !user.bot);

        if (participants.size === 0) {
            return message.channel.send('没有人参与抽奖,活动取消!');
        }

        // 随机抽取一名获奖者
        const winner = participants.random();
        message.channel.send(`🎉 **抽奖结束!** 🎉\n恭喜${winner}获得奖品:${prize}!`);
    }
});

关键逻辑说明:

  • 延迟函数:delay把setTimeout包装成Promise,用await delay(ms)实现同步风格的等待,代码比嵌套回调更清晰。
  • 等待核心:await delay(giveawayDuration)这一行会让机器人暂停执行后续代码,直到设定的抽奖时长过去,完美实现“等待至抽奖结束”的需求。
  • 反应参与:通过添加🎉反应让用户参与,等待结束后收集所有点击反应的用户,再随机抽取获奖者,这是Discord抽奖的常见交互方式。
  • 版本适配:针对Discord.js v13+做了适配,包括事件名变更和权限声明,确保机器人能正常接收消息和反应事件。

内容的提问来源于stack exchange,提问作者Dillgo

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.21 08:14:00