How to use the awaitMessages function in discord.js - discord.js

I have some code for discord.js that sends a user a DM when they join the server. They then have to enter the password given to them, and it will then give them a role that allows them access to channels.
const Discord = require('discord.js');
const client = new Discord.Client();
client.once('ready', () => {
console.log('Ready!');
});
client.on('guildMemberAdd', guildMember => {
console.log("Joined");
guildMember.send("Welcome to the server! Please enter the password given to you to gain access to the server:")
.then(function(){
guildMember.awaitMessages(response => message.content, {
max: 1,
time: 300000000,
errors: ['time'],
})
.then((collected) => {
if(response.content === "Pass"){
guildMember.send("Correct password! You now have access to the server.");
}
else{
guildMember.send("Incorrect password! Please try again.");
}
})
.catch(function(){
guildMember.send('You didnt input the password in time.');
});
});
});
client.login("token");
The thing is, I don't really know how to use the awaitResponses function. I do not know how to call it, because all the tutorials I find use it with message.member.
When I run my code, I get these three errors:
UnhandledPromiseRejectionWarning: TypeError: guildMember.awaitMessages is not a function
UnhandledPromiseRejectionWarning: Unhandled promise rejection. This error originated either by throwing inside of an async function without a catch block, or by rejecting a promise which was not handled with .catch(). To terminate the node process on unhandled promise rejection, use the CLI flag --unhandled-rejections=strict (see https://nodejs.org/api/cli.html#cli_unhandled_rejections_mode). (rejection id: 1)
Unhandled promise rejections are deprecated. In the future, promise rejections that are not handled will terminate the Node.
I do not know what lines these are referring to, so I am very confused.

Here's a quick rundown on how awaitMessages works:
First of all, the .awaitMessages() function extends GuildChannel, meaning you had already messed up a little bit by extending the GuildMember object instead. - You could easily fetch a channel using
const channelObject = guildMember.guild.channels.cache.get('Channel ID Here'); // Gets a channel object based on it's ID
const channelObject = guildMember.guild.channels.cache.find(ch => ch.name === 'channel name here') // Gets a channel object based on it's name
awaitMessages() also gives you the ability to add a filter for a certain condition an input must have.
Let's take the freshly new member as an example. We could simply tell the client to only accept input from members who have the same id as the guildMember object, so basically only the new Member.
const filter = m => m.author.id === guildMember.id
Now, finally, after we've gathered all of the resources needed, this should be our final code to await Messages.
const channelObject = guildMember.guild.channels.cache.get('Channel ID Here');
const filter = m => m.author.id === guildMember.id
channelObject.awaitMessages(filter, {
max: 1, // Requires only one message input
time: 300000000, // Maximum amount of time the bot will await messages for
errors: 'time' // would give us the error incase time runs out.
})
To read more about awaitMessages(), click here!

Related

How do you delete certain messages from a specific username not ID

twitchClient.on('timeout', async (channel, username, user, reason, duration) => {
discordClient.on('message', async (message, messages) => {
async function deleteMessage() {
await discordClient.channels.cache.get("901568598538063932")
.messages.fetch({limit: null})
.then(message.delete(messages.first(user["display-name"]).author.name))
}
await deleteMessage()
})
async function sendMessage() {
const request = new XMLHttpRequest();
request.open("POST", "API url");
request.setRequestHeader('Content-type', 'application/json');
const users = {
username: "User Timed Out",
avatar_url: 'https://i.imgur.com/GUrbNsB.jpg',
content: `**${username} has been timed out for ${duration} seconds.**`
}
request.send(JSON.stringify(users));
}
await sendMessage()
});
I have this code for twitch chat to sync in discord and I want to do on event timeout on twitch
I want it to delete the messages of a certain name on the channel is it possible without ID
I am lost on how to do it like I can delete the last message but not from a specific user and I
only have one webhook so the id of all usernames will be the same
TypeError: Cannot read properties of undefined (reading 'first')
Note: This code is for Discord.js v13.3.0
As stated by the error, you're trying to access an undefined variable called messages. This is because you did not define it in the then() arguments, you instantly went to a callback.
then() is a function that allows for you to provide parameters to add. You can simply put the collection of messages as one variable called messages and pass it to the callback accordingly.
// DON'T do this
messages.fetch({limit: null})
.then(message.delete(messages.first(user["display-name"]).author.name))
// DO this
messages.fetch({limit: null})
.then((messages) => message.delete(messages.first(user["display-name"]).author.name))

TypeError: Cannot read property 'id' of undefined | Discord.js

Aim: To ban every time a user is caught on the audit log attempting to create a channel
Code:
// Channel Create
client.on("channelCreate", async (channel) => {
const FetchingLogs = await client.guilds.cache.get(channel.guild.id).fetchAuditLogs({
limit: 1,
type: "CHANNEL_CREATE",
})
const ChannelLog = FetchingLogs.entries.first();
if (!ChannelLog) {
return console.log(red(`CHANNEL: ${channel.id} was created.`));
}
const { executor, target, createdAt } = ChannelLog;
if (target.id === channel.id) {
console.log(greenBright(`${channel.id} got created, by ${executor.tag}`));
} else if (target.id === executor.id) {
return
}
if (executor.id !== client.user.id) {
channel.guild.member(executor.id).ban({
reason: `Unauthorised Channel Created`
}).then(channel.guild.owner.send(`**Unauthorised Channel Created By:** ${executor.tag} \n**Channel ID:** ${channel.id} \n**Time:** ${createdAt.toDateString()} \n**Sentence:** Ban.`)).catch();
}
});
Result:
It bans the user successfully but still throws an error.
Error:
TypeError: Cannot read property 'id' of undefined
Code: Error Specified | Referring to channel.guild.id
const FetchingLogs = await client.guilds.cache.get(channel.guild.id).fetchAuditLogs({
limit: 1,
type: "CHANNEL_CREATE",
})
I'm guessing the reason for this is that the parameter ,channel, type is DMChannel and not GuildChannel
Is there any way to fix this or be able to change the parameter type to GuildChannel??? I've checked the Docs and I can't seem to find anything that indicates this is possible. Any help is appreciated ;)
Your assumption of why this error is occurring is correct. The channelCreate event does indeed handle the creation of both GuildChannel and DMChannel, and your code sends the guild owner a DM after banning the user. That's why the ban works but you get an error afterwards; because the DM creates a DMChannel with the owner, triggering the event handler again but with channel.guild being undefined since DMs do not have guilds.
So let me state the problem again. You are getting the error Cannot read property 'id' of undefined which you've figured out means channel.guild is undefined. You don't want the error to occur, so you don't want channel.guild to be undefined. But in your question you're asking:
Is there any way to fix this or be able to change the parameter type to GuildChannel???
That's not the approach you want to take. Doing that would mean users would get banned for DMing your bot because it would trigger your channelCreate event handler; plus, the bot would try to ban the guild owner since it sends the owner a DM. And you only want to ban users for creating channels in the guild.
When we put the problem that way, the solution is simple: check if the channel is a DMChannel, and discontinue if it is. Only allow users to get banned for creating a GuildChannel. So how do you do that? Well, as you've seen from your error already, channel.guild is undefined when the channel is a DMChannel. So simply check for this condition, and return if it is the case. Here's an example:
// Channel Create
client.on("channelCreate", async (channel) => {
if (!channel.guild) return; //<- added this
const FetchingLogs = await client.guilds.cache.get(channel.guild.id).fetchAuditLogs({
limit: 1,
type: "CHANNEL_CREATE",
})
const ChannelLog = FetchingLogs.entries.first();
if (!ChannelLog) {
return console.log(red(`CHANNEL: ${channel.id} was created.`));
}
const { executor, target, createdAt } = ChannelLog;
if (target.id === channel.id) {
console.log(greenBright(`${channel.id} got created, by ${executor.tag}`));
} else if (target.id === executor.id) {
return
}
if (executor.id !== client.user.id) {
channel.guild.member(executor.id).ban({
reason: `Unauthorised Channel Created`
}).then(channel.guild.owner.send(`**Unauthorised Channel Created By:** ${executor.tag} \n**Channel ID:** ${channel.id} \n**Time:** ${createdAt.toDateString()} \n**Sentence:** Ban.`)).catch();
}
});
This prevents the error from occurring, prevents users from getting banned for DMing the bot, and prevents the guild owner from being infinitely DM'd (if the DMChannel were to be somehow converted into a GuildChannel, the bot would DM the owner after banning the user that created the channel, which would trigger the event again and ban the user again, and DM the owner again, in an infinite loop).

welcome event sometimes not firing all the way discord.js

My bot is suppose to welcome a member in both the main join/leave channel and also in the chat room so that way we can all welcome the user. For some reason there's a bug where sometimes it'll not send the welcome message to the chat room.
Error:
(node:194) UnhandledPromiseRejectionWarning: TypeError: Cannot read property 'send' of null
The welcome event:
client.on('guildMemberAdd', async (member) => {
const welcomeEmbed = new Discord.RichEmbed()
.setAuthor(member.user.tag, member.user.avatarURL)
.setColor(`GREEN`)
.setDescription(`Welcome **${member.user.username}** to member.guild.name! Consider reading <# {HIDDEN}> to have a basic understand of what we do and do not allow.
Come hang out with us in <#{HIDDEN}> and have a good time!`)
.setFooter(`Member ID: ${member.id}`)
member.guild.channels.find(channel => channel.id === 'HIDDEN').send(welcomeEmbed);
const welcomeEmbed2 = new Discord.RichEmbed()
.setAuthor("New Member Joined!", member.user.avatarURL)
.setDescription(`**${member.user.tag} has joined the server!**`)
.setColor('GREEN')
member.guild.channels.find(channel => channel.id === 'HIDDEN').send(welcomeEmbed2); // This is the one providing the error sometimes
});
I've tried different things such as a .then or just recoding it in different ways to see if it'll work. So far, this has been the only thing my friends do not understand why it's providing errors
You can just fetch the channel by ID using client
client.channels.fetch("SOME_CHANNEL_ID").then(channel => {
channel.send(welcomeEmbed);
})

discord.js TypeError: can not read property 'id' of undefined & Making a fail system

So this command worked just a second ago then the next a error came out of nowhere. Is there a fix to this?
Here is the code
run: async (client, message, args) => {
const cooldown = cooldowns.get(message.author.id);
if (cooldown) {
const remaining = humanizeDuration(cooldown - Date.now(),{ units: ['m', 's'],round: true });
let cEmbed = new MessageEmbed()
.setColor("RANDOM")
.setTitle("Slow down, cmon!")
.setDescription(`You will be able to work in \`${remaining}\` just you wait!\n\nWhile you wait why not follow our [Twitter](https://twitter.com/switchoffical)`)
return message.channel.send(cEmbed)
.catch(console.error);
} else {
let member = message.mentions.users.first() || client.users.cache.get(args[0]);
let user = message.mentions.members.first()
let targetuser = await db.fetch(`money_${user.id}`) // fetch mentioned users balance
let author = await db.fetch(`money_${message.author.id}`) // fetch authors balance
let uBalance = balance[member.id].balance;
let TuBalance = balance[user.id].balance;
let random = Math.floor(Math.random() * 200) + 1; // random number 200-1, you can change 200 to whatever you'd like
let curBal = balance[message.author.id].balance
balance[message.author.id].balance = curBal + random;
let crurBal = balance[message.author.id].balance
balance[user.id].balance = crurBal - random;
if (!user) {
return message.channel.send('Sorry, you forgot to mention somebody.')
if (uBalance < 500) { // if the authors balance is less than 250, return this.
return message.channel.send(':x: You need at least 500$ to rob somebody.')
}
if (TuBalance < 0) { // if mentioned user has 0 or less, it will return this.
return message.channel.send(`:x: ${user.user.username} does not have anything to rob.`)
}
message.channel.send(`${message.author} you robbed ${user} and got away with ${random}!`)
cooldowns.set(message.author.id, Date.now() + 900000);
setTimeout(() => cooldowns.delete(message.author.id), 900000);
db.subtract(`money_${user.id}`, random)
db.add(`money_${message.author.id}`, random)
}
}
}
The error that is made is
(node:7574) UnhandledPromiseRejectionWarning: TypeError: Cannot read property 'id' of undefined
at Object.run (/app/commands/economy/rob.js:37:47)
at module.exports (/app/events/guild/message.js:10:33)
at Client.emit (events.js:196:13)
at MessageCreateAction.handle (/rbd/pnpm-volume/5936e237-314d-4884-9101-9ef8b43cdb53/node_modules/.registry.npmjs.org/discord.js/12.2.0/node_modules/discord.js/src/client/actions/MessageCreate.js:31:14)
at Object.module.exports [as MESSAGE_CREATE] (/rbd/pnpm-volume/5936e237-314d-4884-9101-9ef8b43cdb53/node_modules/.registry.npmjs.org/discord.js/12.2.0/node_modules/discord.js/src/client/websocket/handlers/MESSAGE_CREATE.js:4:32)
at WebSocketManager.handlePacket (/rbd/pnpm-volume/5936e237-314d-4884-9101-9ef8b43cdb53/node_modules/.registry.npmjs.org/discord.js/12.2.0/node_modules/discord.js/src/client/websocket/WebSocketManager.js:386:31)
at WebSocketShard.onPacket (/rbd/pnpm-volume/5936e237-314d-4884-9101-9ef8b43cdb53/node_modules/.registry.npmjs.org/discord.js/12.2.0/node_modules/discord.js/src/client/websocket/WebSocketShard.js:436:22)
at WebSocketShard.onMessage (/rbd/pnpm-volume/5936e237-314d-4884-9101-9ef8b43cdb53/node_modules/.registry.npmjs.org/discord.js/12.2.0/node_modules/discord.js/src/client/websocket/WebSocketShard.js:293:10)
at WebSocket.onMessage (/rbd/pnpm-volume/5936e237-314d-4884-9101-9ef8b43cdb53/node_modules/.registry.npmjs.org/discord.js/12.2.0/node_modules/discord.js/node_modules/ws/lib/event-target.js:125:16)
at WebSocket.emit (events.js:196:13)
(node:7574) UnhandledPromiseRejectionWarning: Unhandled promise rejection. This error originated either by throwing inside of an async function without a catch block, or by rejecting a promise which was not handled with .catch(). (rejection id: 1)
(node:7574) [DEP0018] DeprecationWarning: Unhandled promise rejections are deprecated. In the future, promise rejections that are not handled will terminate the Node.js process with a non-zero exit code.
Now to my next question for the fail system I want it to subtract $500 away from the author and give the 500 to whom they were robbing from. I have the code but it broke the command and there is just too much going on in the code where the system will not fit that I have. SO I completely trashed the fail portion. For the fail rate it is pretty high and there is about a 10% chance you will actually rob someone. is there a efficient way to do this with the big code I have.
There are 2 issues here :
Issue 1:
By using
let user = message.mentions.members.first()`
The variable user can be undefined if there are no mentions in the message.
You were right to check for !user, however, you forgot to move the line just before :
let user = message.mentions.members.first()`
// [...]
balance[user.id].balance = crurBal - random;
if (!user) {
Should be :
let user = message.mentions.members.first()`
// [...]
if (!user) {
balance[user.id].balance = crurBal - random;
Issue 2:
Keep in mind that a message does not always have an author. A webhook message has no author, as you can see in the documentation with the return type being ?User (? here means that it can also be null). Here is the related code.
So you also need to check for an author to the recieved message.

Switching a prefix for a command in discord.js

First post on this site so my bad if I don't format something correctly. I've been trying to make a change prefix command and I don't know how to check next message content for a variable to use instead of the old prefix.
msg.reply("Which prefix do you want?");
const collector = new Discord.MessageCollector(msg.channel, m => m.author.id === msg.author.id, { time: 5000 });
console.log(collector)
collector.on('collect', msg => {
newprefix=collector.content();
msg.reply('Prefix succesfully changed!');
});
I strongly advise using the awaitMessages method. First you need to define a filter, a delegate function that returns true if the reaction is one you want. Typically in a command/response setting, you want a filter that indicates the original command invoker replied.
const filter = (reaction, user) => {
return user.id === msg.author.id;
};
You can then define options for your awaitMessages. (It's quite common to do this in-line with the awaitMessages method, that's fine if that is more clear to you)
const options = {
max: 1,
time: 30000,
errors: ['time']
}
The above example accepts 1 message, if given in 30 seconds, otherwise it throws an exception.
Finally, you are ready to begin...
msg.reply("Which prefix do you want?").then(() => {
msg.channel.awaitMessages(filter, options)
.then(collected => {
newprefix = collected.first();
// Record newprefix to a persistent config here
msg.reply('Prefix successfully changed!');
})
.catch(collected => {
msg.reply("You didn't respond fast enough.");
});
}
Keep in mind, this occurs asynchronously, so if you need to write newprefix somewhere, a JSON config file for example, you should do from within the scope of the .then

Resources