ICode9

精准搜索请尝试: 精确搜索
首页 > 其他分享> 文章详细

Bot in Discord with discord.js

2022-07-09 19:05:07  阅读:159  来源: 互联网

标签:commands interaction const discord 机器人 Bot js


前言

利用 discord.js 建立一个 Discord 机器人。

我也是第一次上手,利用博客来记录我的学习过程,定期整理后再发到公众号。

在简单对比了 discord.js (JavaScript),discordgo (Go),discord.py (Python),Discord4J (Java) 和 D++ (C++) 等项目后,我选择了 discord.js。不为别的,就为 JS 本身。

为什么选择了discord.js 呢?因为它:

  • 面向对象
  • 快速高效
  • 功能丰富
  • 灵活
  • 100% 基于 Promise

而且根据 Atwood 定律:任何可以使用 JavaScript 来编写的应用,并最终也会由 JavaScript 编写。所以,没得办法。

免责声明:先说好,不要将本教程的代码用于生产环境,因为它们通常有着已知或未知的漏洞。任何代码在上线之前,都应该经过充分的代码审查。本教程只是为了说明基本原理并自娱自乐。

下面,咱们开始吧。

Chapter 0 - 环境搭建

环境

你需要自行下载安装 node.js,npm,yarn,pnpm。

本文编写时,我的本地开发环境

操作系统可以选择 Linux 发行版、FreeBSD 和 Mac OS,Windows 不是必须的,但操作系统你得有。

IDE 也不是必须的,用 VS Code, Sublime Text, Vim, nano 或者记事本都可以。

Node.js 是必须安装的。

本文编写时,我的云端环境

云端环境是用来在我的笔记本关机时,保持机器人继续运行的环境。

但是我们这里也就写个机器人,图一乐,所以,凑合凑合就行了,当然没有也无所谓。

  • 外网 IP
  • 1 核 CPU + 512 MB 内存
  • FreeBSD 13.0
  • Node.js 18.2.0

从 Discord Developer Portal 注册机器人账号

打开链接 https://discord.com/developers/applications ,登录你的 Discord 账号,选择 New Application 来创建新应用程序。

NAME 一栏填写你的应用名称,这个名称将会是机器人的外显账号名称,后期可修改。

按下 Create 以完成创建。

点开新创建的应用,点击左侧菜单栏的 General Infromation,记下 APPLICATION ID,这就是通常所说的机器人的 "client_id",这个 ID 是公开可查的,不是秘密。

点击左侧菜单栏的 Bot,点击 Add Bot ,再点击弹出对话框的 Yes, do it! 创建机器人。注意此操作是不可逆的,也就是说机器人一旦创建,就不可被销毁删除。哪怕销毁应用程序,机器人账号仍会在 Discord 的世界里存在,只是变成无人能管理的孤儿账号了。

关于机器人账号和普通用户账号的区别,这里有介绍。

完成机器人账号创建后,在本页面的 Build-A-Bot 栏目中,你可以给机器人账号更换用户名和头像。

点击按钮 Reset Token 并点击 Yes, do it! 来首次获取我们的机器人账号 Token。

注意:Token (令牌)万万不可给别人看到,这是十分机密的一串文字,任何人有了它,就拥有了完全掌控机器人行为的能力了,比如机器人封禁和私聊服务器里的人、发送 @everyone 等恶劣行为都可能会发生。请妥善保管好这个密钥,

注意:Discord 出于安全目的,令牌在创建时只能查看一次。 如果您忘记或无法访问您的令牌,请重新生成一个新令牌,旧令牌将自动失效。

接着为了求福,取消勾选 Requires OAuth2 Code Grant

点击左侧菜单栏的 OAuth2 - URL Generator ,在 SCOPES 里勾选 botapplications.commands ,为了方便,在 BOT PERMISSIONS 里直接勾选第一条 Administrator (注意咱们只是为了玩哈,才直接赋予管理员权限的)。

复制最下方生成的 URL,粘贴到新浏览器窗口打开,选择服务器并添加。如果你没有看到任何可选选项,那么你需要去 Discord 先自己创建一个服务器,然后回来刷新一下。事实上,其他服务器如果给你管理服务器的权限的话,这个服务器将出现在可选选项中。

到此,我们完成了搭建开发环境、创建机器人账号和邀请机器人进入服务器。

Chapter 1 - 工作目录的初始化

创建工程文件夹(工作目录)

对于 IDE 用户,创建一个 Node.js 项目。对于编辑器用户,新建文件夹即可。

比如我的工作目录是 C:\Users\root\WebstormProjects\discord_bot_2022

获取 discord.js

本文编写时,discord.js 的最新版本是 v13。因此,后文的所有代码可能在未来的版本(比如 v14)中失效。

不过幸运的是,v14 的推出还远着呢。

注意:你的 Node.js 的版本需高于 16.6.0(含)

cd 到 工作目录,在终端输入来获取 discord.js:

npm install discord.js @discordjs/rest discord-api-types
yarn add discord.js @discordjs/rest discord-api-types
pnpm add discord.js @discordjs/rest discord-api-types

打开 Discord 开发者模式

为了方便地获取服务器和用户 id,我们必须这么做。

打开你的 Discord,无论是手机 APP 还是 PC 还是网页版。在 设置 - 高级设置 里,勾选 开发者模式

创建配置文件 config.json

在工作目录下创建文件 config.json,写入:

{  
   "token": "bot-token-goes-here",  
   "clientId": "bot-clientid-goes here",  
   "guildId": "serverid-goes-here"  
}

比如

{  
   "token": "OTEzNDMyTEN0OTkzOTk1ODA4.Bhz0k7.97sjsWOGtmx-LBIlFvrkk6A9lkk9YGMX9OYbf",  
   "clientId": "913432114993090099",  
   "guildId": "978274108671780933"  
}

需要说明的是,token 字段就是那个极为重要不能外泄的机器人密钥,把你的粘贴过来。

clientId 字段就是 Application id。在 Discord 服务器里。右击机器人头像,点击 复制 ID 即可轻松获取。

guildId 字段是服务器的 ID,当然得是机器人所在的服务器的 ID。右击服务器头像,点击 复制 ID 即可轻松获取。

接下来确保你的工作目录下存在 .gitignore 文件,确保文件内已写入

node_modules
config.json

否则你的 token 将会在 git 推送后外泄。

实现一个机器人

工作目录 创建文件 deploy_commands.js,写入:

const fs = require("fs");  
const { REST } = require('@discordjs/rest');  
const { Routes } = require('discord-api-types/v9');  
const { clientId, guildId, token } = require('./config.json');

const commands = [];  
const commandFiles = fs.readdirSync("./commands").filter(file => file.endsWith(".js"));  
  
for (const file of commandFiles) {  
   const command = require(`./commands/${file}`);  
   commands.push(command.data.toJSON());  
}  
  
const rest = new REST({ version: '9' }).setToken(token);  
  
rest.put(Routes.applicationGuildCommands(clientId, guildId), { body: commands })  
   .then(() => console.log('Successfully registered application commands.'))  
   .catch(console.error);

工作目录 下创建文件夹 events,在这个文件夹里创建文件 ready.js,写入:

module.exports = {  
   name: "ready",  
   once: true,  
   execute(client) {  
      console.log(`Ready! Logged in as ${client.user.tag}`);  
   },  
};

工作目录/event 文件夹里,创建文件 interactionCreate.js,写入:

module.exports = {  
   name: "interactionCreate",  
   execute(interaction) {  
      console.log(`${interaction.user.tag} in #${interaction.channel.name} triggered an interaction.`);  
   },  
};

工作目录 创建文件 index.js ,写入:

const fs = require('fs');  
const { Client, Collection, Intents } = require('discord.js');  
const { token } = require('./config.json');  

const client = new Client({ intents: [Intents.FLAGS.GUILDS] });  
  
const eventFiles = fs.readdirSync('./events').filter(file => file.endsWith('.js'));  
  
for (const file of eventFiles) {
    const event = require(`./events/${file}`);
    if (event.once) {
        client.once(event.name, (...args) => event.execute(...args));
    } else {
        client.on(event.name, (...args) => event.execute(...args));
    }
}

client.commands = new Collection();
const commandFiles = fs.readdirSync("./commands").filter(file => file.endsWith(".js"));

for (const file of commandFiles) {
    const command = require(`./commands/${file}`);
    client.commands.set(command.data.name, command);
}

client.once('ready', () => {});
client.on('interactionCreate', async interaction => {
    if (!interaction.isCommand()) return;

    const command = client.commands.get(interaction.commandName);

    if (!command) return;

    try {
        await command.execute(interaction);
    } catch (error) {
        console.error(error);
        await interaction.reply({
            content: 'There was an error while executing this command!',
            ephemeral: true
        });
    }
});

client.on('interactionCreate', interaction => {});

client.login(token);

工作目录 下创建文件夹 commands,在这个文件夹里创建文件 ping.js,写入:

const { SlashCommandBuilder } = require('@discordjs/builders');  
  
module.exports = {  
   data: new SlashCommandBuilder()  
      .setName('ping')  
      .setDescription('Replies with Pong!'),  
   async execute(interaction) {  
      await interaction.reply("Pong!");  
   },  
};

这些代码,不懂正常。先照做,以后会介绍到的,何况我们的工作重点不是这些“框架”性的东西,而是真正的机器人交互逻辑代码。

对于 IDE 用户,创建运行配置后,点击“运行”或者什么之类的按钮即可让机器人跑起来。

对于非 IDE 用户(IDE 用户也可以),打开终端,cd 到工作目录,输入 node deploy_commands.js 注册斜杠命令。成功消息是 Successfully registered application commands.

成功后,cd 到工作目录,终端输入 node index.js 运行机器人。成功消息类似于 Ready! Logged in as abcd#0001

如果出现 “ 无法将“node”项识别为 cmdlet、函数、脚本文件或可运行程序的名称。请检查名称的拼写,如果包括路径,请确保路径正确,然后再试一次。” 或者 “ 'node' 不是内部或外部命令,也不是可运行的程序
或批处理文件。”亦或者“ -bash: node: command not found ”,请检查你的 PATH 是否有包含 node.exe 所在文件夹,这通常是 C:\Program Files\nodejs\node.exe

如果失败,请检查你的网络是否能连接到 DIscord、你的上述步骤有没有漏做或者顺序错误的。

与机器人交互

cd 到工作目录。

确保你已经通过 node deploy_commands.js 注册了斜杠命令,并已通过 node index.js 使机器人程序保持运行状态。验证方法是:能看到你的机器人是在线状态而非离线状态。

打开 Discord,在机器人所在的服务器的任何文字频道,输入 /ping,回车选定斜杠命令,再次回车发送命令,机器人应该会发送消息 Pong! ,而且在机器人后端程序,会输出类似于 xxxx#0001 in #bot triggered an interaction.

这样,一个非常简单的机器人就完成了。

后续我们将学习更多的东西,先写到这吧。记得关注从而收取最新消息。

原文链接:https://www.cnblogs.com/hhzm/p/16461628.html

标签:commands,interaction,const,discord,机器人,Bot,js
来源: https://www.cnblogs.com/hhzm/p/16461628.html

本站声明: 1. iCode9 技术分享网(下文简称本站)提供的所有内容,仅供技术学习、探讨和分享;
2. 关于本站的所有留言、评论、转载及引用,纯属内容发起人的个人观点,与本站观点和立场无关;
3. 关于本站的所有言论和文字,纯属内容发起人的个人观点,与本站观点和立场无关;
4. 本站文章均是网友提供,不完全保证技术分享内容的完整性、准确性、时效性、风险性和版权归属;如您发现该文章侵犯了您的权益,可联系我们第一时间进行删除;
5. 本站为非盈利性的个人网站,所有内容不会用来进行牟利,也不会利用任何形式的广告来间接获益,纯粹是为了广大技术爱好者提供技术内容和技术思想的分享性交流网站。

专注分享技术,共同学习,共同进步。侵权联系[81616952@qq.com]

Copyright (C)ICode9.com, All Rights Reserved.

ICode9版权所有