Discord bot Javascript 声明或预期声明
Posted
技术标签:
【中文标题】Discord bot Javascript 声明或预期声明【英文标题】:Discord bot Javascript Declaration or statement expected 【发布时间】:2018-06-12 05:11:42 【问题描述】:const Discord = require("discord.js");
const TOKEN = "BEEP";
const PREFIX = "$$";
var bot = new Discord.Client();
bot.on("ready", function()
console.log("ThunderBird is a go");
bot.user.setPresence(
game:
name: "Choccy Milk",
type: 0
);
);
bot.on("message", function(message)
if (message.author.equals(bot.user)) return;
if (message.content == "hello")
message.channel.send("Hi, how are you!");
if (!message.content.startsWith(PREFIX)) return;
var args = message.content.substring(PREFIX.length).split(" ");
switch (args[0])
case "ping":
message.channel.send("Pong!");
break;
);
bot.login(TOKEN);
【问题讨论】:
检查你的括号,它们在接近尾声时关闭了。 【参考方案1】:注意:最终代码在答案的底部,因为中间有很多我需要说的。
注意:如果您只是担心它的工作原理,不要过分关注使用好的做法,或者不喜欢我为了使用好的做法而更改的内容:在第四步之后停止。
为了让您的机器人正常工作,必须修复此代码的一些问题。首先是缩进。您发送的内容非常难以阅读,因此如果我们对其进行一些修改,我们可以轻松识别错误。这是带有适当缩进的代码。
第一步:缩进:
const Discord = require("discord.js");
const TOKEN = "BEEP";
const PREFIX = "$$";
var bot = new Discord.Client();
bot.on("ready", function()
console.log("ThunderBird is a go");
bot.user.setPresence(game:
name: "Choccy Milk",
type: 0
);
);
bot.on("message", function(message)
if (message.author.equals(bot.user)) return;
if (message.content == "hello")
message.channel.send("Hi, how are you!");
if (!message.content.startsWith(PREFIX)) return;
var args = message.content.substring(PREFIX.length).split(" ");
switch (args[0])
case "ping":
message.channel.send("Pong!");
break;
);
现在阅读起来并不容易。您可能已经看到错误。倒数第二行缺少某些内容。如果您的代码末尾附近没有任何红色下划线,我会下载一个新的文本编辑器。可以做到这一点的一些最流行的编辑器包括 VSCode、Atom 和 Sublime Text。链接包括https://code.visualstudio.com/ & https://atom.io/ & http://www.sublimetext.com/(我更喜欢VSCode)。
如果你仔细观察,有一个 IF 块永远不会完全关闭。您只需在倒数第二行添加另一个花括号即可将其关闭。
第二步:语法更正:
const Discord = require("discord.js");
const TOKEN = "BEEP";
const PREFIX = "$$";
var bot = new Discord.Client();
bot.on("ready", function()
console.log("ThunderBird is a go");
bot.user.setPresence(game:
name: "Choccy Milk",
type: 0
);
);
bot.on("message", function(message)
if (message.author.equals(bot.user)) return;
if (message.content == "hello")
message.channel.send("Hi, how are you!");
if (!message.content.startsWith(PREFIX)) return;
var args = message.content.substring(PREFIX.length).split(" ");
switch (args[0])
case "ping":
message.channel.send("Pong!");
break;
);
此时您会注意到您的程序运行良好,没有错误。唯一的问题是您的机器人实际上并没有启动,这是因为您从未告诉它连接到 Discord。你永远不能认为它只会假设显而易见。您的程序然后关闭的原因是因为您只是定义了操作但从未运行它们。值得庆幸的是,Discord.JS 为您完成了大部分工作,因此您只需键入一行代码即可。
第三步:连接:
const Discord = require("discord.js");
const TOKEN = "BEEP";
const PREFIX = "$$";
var bot = new Discord.Client();
bot.on("ready", function()
console.log("ThunderBird is a go");
bot.user.setPresence(game:
name: "Choccy Milk",
type: 0
);
);
bot.on("message", function(message)
if (message.author.equals(bot.user)) return;
if (message.content == "hello")
message.channel.send("Hi, how are you!");
if (!message.content.startsWith(PREFIX)) return;
var args = message.content.substring(PREFIX.length).split(" ");
switch (args[0])
case "ping":
message.channel.send("Pong!");
break;
);
bot.login(TOKEN);
嗯,这很容易。现在您的机器人将通过正确的游戏上线。就像您指定的那样,如果您输入 hello “hello”,它会回复“Hi, how are you!”。这很好,但是如果你输入 $$ping,实际上什么都不会发生。这是因为它仅在消息也是“hello”时才查找消息 $$ping。显然这是有问题的,因为一条消息不能同时说出两件事。如果消息不是“hello”,我们真正想要的是它寻找 $$ping。您可以使用 ELSE 子句来做到这一点。
第四步:ELSE 子句:
const Discord = require("discord.js");
const TOKEN = "BEEP";
const PREFIX = "$$";
var bot = new Discord.Client();
bot.on("ready", function()
console.log("ThunderBird is a go");
bot.user.setPresence(game:
name: "Choccy Milk",
type: 0
);
);
bot.on("message", function(message)
if (message.author.equals(bot.user)) return;
if (message.content == "hello")
message.channel.send("Hi, how are you!");
else
if (!message.content.startsWith(PREFIX)) return;
var args = message.content.substring(PREFIX.length).split(" ");
switch (args[0])
case "ping":
message.channel.send("Pong!");
break;
);
bot.login(TOKEN);
我所做的只是添加一个新行(第 22 行)和“ else ”。现在一切正常,但仍有一些问题需要解决。如果你不喜欢我在这里做的事情,只需复制并粘贴第四步中的代码。
我建议更改的第一件事是变量名;特别是机器人的名称。您可能注意到,method.Client() 以大写字母开头。这不是偶然的,并且在开发人员部分是非常正确的。当方法是一个类或遵循特定的对象创建模式时,就会这样做。 (主要的OCP包括工厂、构造器和原型)。您可以说它是其中之一,因为它需要 new 关键字。看了Discord.JS的代码,相信是一个类。解决此问题的方法是将变量名称从“bot”更改为“Bot”以及该变量的所有用途。
第五步:变量名
const Discord = require("discord.js");
const TOKEN = "BEEP";
const PREFIX = "$$";
var Bot = new Discord.Client();
Bot.on("ready", function()
console.log("ThunderBird is a go");
Bot.user.setPresence(game:
name: "Choccy Milk",
type: 0
);
);
Bot.on("message", function(message)
if (message.author.equals(Bot.user)) return;
if (message.content == "hello")
message.channel.send("Hi, how are you!");
else
if (!message.content.startsWith(PREFIX)) return;
var args = message.content.substring(PREFIX.length).split(" ");
switch (args[0])
case "ping":
message.channel.send("Pong!");
break;
);
Bot.login(TOKEN);
接下来应该更改的是 Bot 变量类型。通常,您希望变量是常数。这是因为如果变量发生变化,您不希望它继续运行;相反,您希望它停止并告诉您错误及其发生时间。如果您曾经对您的机器人使用 eval 命令,这可能变得非常重要。
第六步:常量变量:
const Discord = require("discord.js");
const Bot = new Discord.Client();
const TOKEN = "BEEP";
const PREFIX = "$$";
Bot.on("ready", function()
console.log("ThunderBird is a go");
Bot.user.setPresence(game:
name: "Choccy Milk",
type: 0
);
);
Bot.on("message", function(message)
if (message.author.equals(Bot.user)) return;
if (message.content == "hello")
message.channel.send("Hi, how are you!");
else
if (!message.content.startsWith(PREFIX)) return;
var args = message.content.substring(PREFIX.length).split(" ");
switch (args[0])
case "ping":
message.channel.send("Pong!");
break;
);
Bot.login(TOKEN);
这段代码的另一个问题是它使用了旧形式的函数。使用所谓的箭头函数是 ECMAScript(AKA javascript)中的一个标准。老实说,我不确定为什么它是一个标准,而不仅仅是一种偏好,但它是这样的,所以我们最好遵循它。箭头函数也更好,因为它们更具可读性并且没有 this 关键字的本地范围(这是一个优势,因为您仍然可以访问全局范围)。您可以通过将 function() ... 替换为 () => ... 来使用箭头函数,如果需要参数,可以像函数一样将它们放在括号中。例如 (function(req, res, next) ... 到 (req, res, next) => ... )。此外,如果只有一个参数,您甚至不需要括号。例如(函数(消息) ... 到消息 => ... )。您可以在此处阅读 ECMAScript 和箭头函数的标准:https://github.com/lukehoban/es6features#arrows。
第七步:箭头函数:
const Discord = require("discord.js");
const Bot = new Discord.Client();
const TOKEN = "BEEP";
const PREFIX = "$$";
Bot.on("ready", () =>
console.log("ThunderBird is a go");
Bot.user.setPresence(game:
name: "Choccy Milk",
type: 0
);
);
Bot.on("message", message =>
if (message.author.equals(Bot.user)) return;
if (message.content == "hello")
message.channel.send("Hi, how are you!");
else
if (!message.content.startsWith(PREFIX)) return;
var args = message.content.substring(PREFIX.length).split(" ");
switch (args[0])
case "ping":
message.channel.send("Pong!");
break;
);
Bot.login(TOKEN);
另一个应该做的调整是将“var”关键字替换为“let”。尽管有些人只是更喜欢“var”,但这是它已成为标准的另一件事。 “let”关键字更好,因为它使您的代码运行得稍微快一些,它的作用域是块级,而不是函数级,这是一种更一致的方式。 let 关键字也很棒,因为它允许您临时覆盖 IF 语句之类的变量。就个人而言,我使用 let 修复了代码中的错误,可能是因为较低范围的变量不会与较高范围的变量发生冲突。您可以在https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Statements/let 阅读有关“let”关键字的信息。要进行此更改,只需将单词“var”替换为“let”。 (其他代码段可能需要其他步骤,这就是为什么我建议阅读 let 的原因)。您可以在以下示例中看到这个额外的步骤:
(() =>
var regex = /^[1-9]/u;
var DateNow = Date.now();
var token = process.env.BOT_TOKEN;
var condition1 = regex.test(String(token));
var condition2 = DateNow > 1515354893761;
if((condition1) && (condition2))
var text = 'Yes';
else
var text = 'No';
console.log(text);
)();
这会很完美,但是如果我尝试使用“let”,它会做一些非常意想不到的事情。
(() =>
let regex = /^[1-9]/u;
let DateNow = Date.now();
let token = process.env.BOT_TOKEN;
let condition1 = regex.test(String(token));
let condition2 = DateNow > 1515354893761;
if((condition1) && (condition2))
let text = 'Yes';
else
let text = 'No';
console.log(text);
)();
这不起作用,而是给出错误“ReferenceError: text is not defined”。要解决这个问题并仍然使用“let”,我们只需将其移至更高的范围。
(() =>
let regex = /^[1-9]/u;
let DateNow = Date.now();
let token = process.env.BOT_TOKEN;
let condition1 = regex.test(String(token));
let condition2 = DateNow > 1515354893761;
let text;
if((condition1) && (condition2))
text = 'Yes';
else
text = 'No';
console.log(text);
)();
这与使用“var”的示例完全相同,同时仍然能够保留“let”关键字。我们可以做到这一点的另一种方法是使用三元运算符。
(() =>
let regex = /^[1-9]/u;
let DateNow = Date.now();
let token = process.env.BOT_TOKEN;
let condition1 = regex.test(String(token));
let condition2 = DateNow > 1515354893761;
let text = (condition1) && (condition2) ? 'Yes' : 'No';
console.log(text);
)();
三元组是一种更快的方法,但对于循环等其他块类型没有三元组。
现在让我们回到代码。
第八步:LET 关键字:
const Discord = require("discord.js");
const Bot = new Discord.Client();
const TOKEN = "BEEP";
const PREFIX = "$$";
Bot.on("ready", () =>
console.log("ThunderBird is a go");
Bot.user.setPresence(game:
name: "Choccy Milk",
type: 0
);
);
Bot.on("message", message =>
if (message.author.equals(Bot.user)) return;
if (message.content == "hello")
message.channel.send("Hi, how are you!");
else
if (!message.content.startsWith(PREFIX)) return;
let args = message.content.substring(PREFIX.length).split(" ");
switch (args[0])
case "ping":
message.channel.send("Pong!");
break;
);
Bot.login(TOKEN);
您可能希望在所有可能的情况下都使用三等号运算符。虽然在这个例子中没有太多内容,但它是一个好习惯。双等号和三等号的区别在于双等号会改变一侧的数据类型以使它们匹配。虽然这在实践中看起来很有用,但最好在需要停止潜在错误时自己转换它们。在处理奇怪的转换(例如布尔值)时,这可能会很混乱。要全面了解这些错误,我建议在 YouTube 上使用 JavaScript:了解奇怪的部分 - 前 3.5 小时。
第九步:三等号:
const Discord = require("discord.js");
const Bot = new Discord.Client();
const TOKEN = "BEEP";
const PREFIX = "$$";
Bot.on("ready", () =>
console.log("ThunderBird is a go");
Bot.user.setPresence(game:
name: "Choccy Milk",
type: 0
);
);
Bot.on("message", message =>
if (message.author.equals(Bot.user)) return;
if (message.content === "hello")
message.channel.send("Hi, how are you!");
else
if (!message.content.startsWith(PREFIX)) return;
let args = message.content.substring(PREFIX.length).split(" ");
switch (args[0])
case "ping":
message.channel.send("Pong!");
break;
);
Bot.login(TOKEN);
在 Node.JS 中,您经常希望使您的函数异步。这不会影响当前代码,但我认为这将是一个很好的添加细节。您可以通过在函数之前添加“async”关键字来创建异步函数。通常这无关紧要,但由于 Discord.JS 是基于 Promise 的,因此这是非常好的实践。你可以在这里阅读 async 和 await:https://javascript.info/async-await。
异步函数:
const Discord = require("discord.js");
const Bot = new Discord.Client();
const TOKEN = "BEEP";
const PREFIX = "$$";
Bot.on("ready", async () =>
console.log("ThunderBird is a go");
Bot.user.setPresence(game:
name: "Choccy Milk",
type: 0
);
);
Bot.on("message", async message =>
if (message.author.equals(Bot.user)) return;
if (message.content === "hello")
message.channel.send("Hi, how are you!");
else
if (!message.content.startsWith(PREFIX)) return;
let args = message.content.substring(PREFIX.length).split(" ");
switch (args[0])
case "ping":
message.channel.send("Pong!");
break;
);
Bot.login(TOKEN);
我不会向您展示如何执行此部分,因为它涉及很多个人偏好,您希望将来如何处理代码。我建议您通过以下几种方式修改您的命令系统:
使命令成为一个独立于参数的变量。您可能需要查看 Array.slice() 方法。 使命令不区分大小写。您可能需要为此查看 String.toLowerCase() 方法。 将命令代码放在不同的文件中。您可能需要查看 module.exports 属性。如果您不确定如何执行此列表中的任何操作,请告诉我,我们很乐意为您提供帮助。
从您的代码的简单性来看,您似乎是 Discord.JS 的初学者。我建议您阅读以下文档:https://discord.js.org/#/ > 文档。
记得将令牌变量改回你的机器人的令牌。
最终代码
const Discord = require("discord.js");
const Bot = new Discord.Client();
const TOKEN = "BEEP";
const PREFIX = "$$";
Bot.on("ready", async () =>
console.log("ThunderBird is a go");
Bot.user.setPresence(game:
name: "Choccy Milk",
type: 0
);
);
Bot.on("message", async message =>
if (message.author.equals(Bot.user)) return;
if (message.content === "hello")
message.channel.send("Hi, how are you!");
else
if (!message.content.startsWith(PREFIX)) return;
let args = message.content.substring(PREFIX.length).split(" ");
switch (args[0])
case "ping":
message.channel.send("Pong!");
break;
);
Bot.login(TOKEN);
编辑:我刚刚意识到您确实输入了 bot.login。对此感到抱歉。
【讨论】:
以上是关于Discord bot Javascript 声明或预期声明的主要内容,如果未能解决你的问题,请参考以下文章
Discord bot 使用 javascript .sendMessage 不是函数
如何在 javascript 中使用 like、telegraf、discord.js 设置 bot.on()?
制作 Discord Bot 时在 Javascript 中出现“意外的输入结束”
在 JavaScript Discord Bot 中,为啥 message.react() 是“不是函数”