运行播放命令时未定义的歌曲
Posted
技术标签:
【中文标题】运行播放命令时未定义的歌曲【英文标题】:undefined song when I run the play command 【发布时间】:2021-07-01 05:18:16 【问题描述】:我正在尝试使用yt-search
构建一个音乐不和谐机器人,但每当我播放歌曲时它都会给我undefined
,它会在不播放歌曲的情况下加入语音频道。我正在尝试使用yt-search
来查找我想要的视频,或者仅使用URL 然后将其传递给ytdl
以使用yt-search
提供的URL 运行它,但我认为我在某些方面是错误的。我不知道在哪里,你能修复我的代码吗?
显示问题的图片:
我的代码:
const Discord = require("discord.js");
const prefix, token = require("./config.json");
const ytdl = require("ytdl-core");
const yts = require("yt-search");
const client = new Discord.Client();
const queue = new Map();
client.once("ready", () =>
console.log("Ready!");
);
client.once("reconnecting", () =>
console.log("Reconnecting!");
);
client.once("disconnect", () =>
console.log("Disconnect!");
);
client.on("message", async message =>
if (message.author.bot) return;
if (!message.content.startsWith(prefix)) return;
const serverQueue = queue.get(message.guild.id);
if (message.content.startsWith(`$prefixplay`))
execute(message, serverQueue);
return;
else if (message.content.startsWith(`$prefixskip`))
skip(message, serverQueue);
return;
else if (message.content.startsWith(`$prefixstop`))
stop(message, serverQueue);
return;
else
message.channel.send("You need to enter a valid command!");
);
async function execute(message, serverQueue)
const args = message.content.split(" ");
const voiceChannel = message.member.voice.channel;
if (!voiceChannel)
return message.channel.send(
"You need to be in a voice channel to play music!"
);
const permissions = voiceChannel.permissionsFor(message.client.user);
if (!permissions.has("CONNECT") || !permissions.has("SPEAK"))
return message.channel.send(
"I need the permissions to join and speak in your voice channel!"
);
const r = await yts(args[1,2]);
const video = r.videos.slice( 0, 1 );
console.log(video);
const songInfo = await ytdl.getInfo(video.url);
const song =
title: songInfo.videoDetails.title,
url: songInfo.videoDetails.video_url,
;
if (!serverQueue)
const queueContruct =
textChannel: message.channel,
voiceChannel: voiceChannel,
connection: null,
songs: [],
volume: 5,
playing: true
;
queue.set(message.guild.id, queueContruct);
queueContruct.songs.push(song);
try
var connection = await voiceChannel.join();
queueContruct.connection = connection;
play(message.guild, queueContruct.songs[0]);
catch (err)
console.log(err);
queue.delete(message.guild.id);
return message.channel.send(err);
else
serverQueue.songs.push(song);
return message.channel.send(`$song.title has been added to the queue!`);
function skip(message, serverQueue)
if (!message.member.voice.channel)
return message.channel.send(
"You have to be in a voice channel to stop the music!"
);
if (!serverQueue)
return message.channel.send("There is no song that I could skip!");
serverQueue.connection.dispatcher.end();
function stop(message, serverQueue)
if (!message.member.voice.channel)
return message.channel.send(
"You have to be in a voice channel to stop the music!"
);
if (!serverQueue)
return message.channel.send("There is no song that I could stop!");
serverQueue.songs = [];
serverQueue.connection.dispatcher.end();
function play(guild, song)
const serverQueue = queue.get(guild.id);
if (!song)
serverQueue.voiceChannel.leave();
queue.delete(guild.id);
return;
const dispatcher = serverQueue.connection
.play(ytdl(song.url))
.on("finish", () =>
serverQueue.songs.shift();
play(guild, serverQueue.songs[0]);
)
.on("error", error => console.error(error));
dispatcher.setVolumeLogarithmic(serverQueue.volume / 5);
serverQueue.textChannel.send(`Start playing: **$song.title**`);
client.login(token);
【问题讨论】:
【参考方案1】:有两个错误。我不确定您认为args[1,2]
是什么,但它与args[2]
相同,后者是args
数组的第三项。通过阅读您的代码,我认为您想在这里使用一个字符串,即搜索词。通过从args
数组中删除第一项(命令)并加入其余项,您将收到一个可以用作关键字的字符串。看看下面的例子:
const message = content: '!play some music I want'
const args = message.content.split(' ')
console.log( args )
// => ["!play", "some", "music", "I", "want"]
console.log( 'args[1, 2]': args[1, 2] )
// => "music"
console.log( 'search': args.slice(1).join(' ') )
// => "some music I want"
另一个错误是await yts(query)
返回一个结果数组,当您定义video
变量时,您使用r.videos.slice(0, 1)
。 .slice()
方法返回一个新数组,其中第一项为r.videos
。
由于video
变量是一个数组,video.url
是未定义的。您可以改用第一项来修复它,因为它将具有 url
属性。您还应该检查是否有任何搜索结果。
查看下面的更新代码:
async function execute(message, serverQueue)
const args = message.content.split(' ');
const voiceChannel = message.member.voice.channel;
if (!voiceChannel)
return message.channel.send(
'You need to be in a voice channel to play music!',
);
const permissions = voiceChannel.permissionsFor(message.client.user);
if (!permissions.has('CONNECT') || !permissions.has('SPEAK'))
return message.channel.send(
'I need the permissions to join and speak in your voice channel!',
);
const query = args.slice(1).join(' ');
const results = await yts(query);
if (!results.videos.length)
return message.channel.send(`No results for \`$query\``);
const firstVideo = results.videos[0];
const songInfo = await ytdl.getInfo(firstVideo.url);
const song =
title: songInfo.videoDetails.title,
url: songInfo.videoDetails.video_url,
;
console.log(song);
if (!serverQueue)
// ...
// ...
【讨论】:
以上是关于运行播放命令时未定义的歌曲的主要内容,如果未能解决你的问题,请参考以下文章
在 jenkins 的 Visual Studio for Linux 项目上运行 devenv 时未定义的远程主机