diff --git a/lib/bot.js b/lib/bot.js index fa3b1474..3572f15f 100644 --- a/lib/bot.js +++ b/lib/bot.js @@ -133,6 +133,12 @@ class Bot { this.attachListeners(); } + disconnect() { + this.ircClient.disconnect(); + this.discord.destroy(); + Object.values(this.webhooks).forEach(x => x.client.destroy()); + } + attachListeners() { this.discord.on('ready', () => { logger.info('Connected to Discord'); @@ -258,7 +264,7 @@ class Bot { static getDiscordNicknameOnServer(user, guild) { if (guild) { - const userDetails = guild.members.get(user.id); + const userDetails = guild.members.cache.get(user.id); if (userDetails) { return userDetails.nickname || user.username; } @@ -277,12 +283,12 @@ class Bot { return text .replace(/\n|\r\n|\r/g, ' ') .replace(/<#(\d+)>/g, (match, channelId) => { - const channel = this.discord.channels.get(channelId); + const channel = this.discord.channels.cache.get(channelId); if (channel) return `#${channel.name}`; return '#deleted-channel'; }) .replace(/<@&(\d+)>/g, (match, roleId) => { - const role = message.guild.roles.get(roleId); + const role = message.guild.roles.cache.get(roleId); if (role) return `@${role.name}`; return '@deleted-role'; }) @@ -391,10 +397,10 @@ class Bot { // #channel -> channel before retrieving and select only text channels: let discordChannel = null; - if (this.discord.channels.has(discordChannelName)) { - discordChannel = this.discord.channels.get(discordChannelName); + if (this.discord.channels.cache.has(discordChannelName)) { + discordChannel = this.discord.channels.cache.get(discordChannelName); } else if (discordChannelName.startsWith('#')) { - discordChannel = this.discord.channels + discordChannel = this.discord.channels.cache .filter(c => c.type === 'text') .find(c => c.name === discordChannelName.slice(1)); } @@ -417,7 +423,7 @@ class Bot { } getDiscordAvatar(nick, channel) { - const guildMembers = this.findDiscordChannel(channel).guild.members; + const guildMembers = this.findDiscordChannel(channel).guild.members.cache; const findByNicknameOrUsername = caseSensitive => (member) => { if (caseSensitive) { @@ -438,8 +444,8 @@ class Bot { // No matching user or more than one => default avatar if (users && users.size === 1) { - const url = users.first().user.avatarURL; - if (url) return url.replace(/\?size=\d{1,}$/, '?size=128'); + const url = users.first().user.avatarURL({ size: 128, format: 'png' }); + if (url) return url; } // If there isn't a URL format, don't send an avatar at all @@ -498,7 +504,7 @@ class Bot { // @username#1234 => mention // skips usernames including spaces for ease (they cannot include hashes) // checks case insensitively as Discord does - const user = guild.members.find(x => + const user = guild.members.cache.find(x => Bot.caseComp(x.user.username, username) && x.user.discriminator === discriminator); if (user) return user; @@ -510,16 +516,16 @@ class Bot { // this preliminary stuff is ultimately unnecessary // but might save time over later more complicated calculations // @nickname => mention, case insensitively - const nickUser = guild.members.find(x => - x.nickname !== null && Bot.caseComp(x.nickname, reference)); + const nickUser = guild.members.cache.find(x => + x.nickname && Bot.caseComp(x.nickname, reference)); if (nickUser) return nickUser; // @username => mention, case insensitively - const user = guild.members.find(x => Bot.caseComp(x.user.username, reference)); + const user = guild.members.cache.find(x => Bot.caseComp(x.user.username, reference)); if (user) return user; // @role => mention, case insensitively - const role = guild.roles.find(x => x.mentionable && Bot.caseComp(x.name, reference)); + const role = guild.roles.cache.find(x => x.mentionable && Bot.caseComp(x.name, reference)); if (role) return role; // No match found checking the whole word. Check for partial matches now instead. @@ -544,13 +550,13 @@ class Bot { }; // check users by username and nickname - guild.members.forEach((member) => { + guild.members.cache.forEach((member) => { checkMatch(member.user.username, member); - if (bestMatch === member || member.nickname === null) return; + if (bestMatch === member || !member.nickname) return; checkMatch(member.nickname, member); }); // check mentionable roles by visible name - guild.roles.forEach((member) => { + guild.roles.cache.forEach((member) => { if (!member.mentionable) return; checkMatch(member.name, member); }); @@ -561,7 +567,7 @@ class Bot { return match; }).replace(/:(\w+):/g, (match, ident) => { // :emoji: => mention, case sensitively - const emoji = guild.emojis.find(x => x.name === ident && x.requiresColons); + const emoji = guild.emojis.cache.find(x => x.name === ident && x.requiresColons); if (emoji) return emoji; return match; @@ -571,7 +577,7 @@ class Bot { // but these seem likely to be common around channel references) // discord matches channel names case insensitively - const chan = guild.channels.find(x => Bot.caseComp(x.name, channelName)); + const chan = guild.channels.cache.find(x => Bot.caseComp(x.name, channelName)); return chan || match; }); @@ -586,11 +592,10 @@ class Bot { } const avatarURL = this.getDiscordAvatar(author, channel); const username = _.padEnd(author.substring(0, USERNAME_MAX_LENGTH), USERNAME_MIN_LENGTH, '_'); - webhook.client.sendMessage(withMentions, { + webhook.client.send(withMentions, { username, - text, avatarURL, - disableEveryone: !canPingEveryone, + disableMentions: canPingEveryone ? 'none' : 'everyone', }).catch(logger.error); return; } diff --git a/package-lock.json b/package-lock.json index ed03ac43..4ccec0e5 100644 --- a/package-lock.json +++ b/package-lock.json @@ -2787,6 +2787,21 @@ "kuler": "^2.0.0" } }, + "@discordjs/collection": { + "version": "0.1.6", + "resolved": "https://registry.npmjs.org/@discordjs/collection/-/collection-0.1.6.tgz", + "integrity": "sha512-utRNxnd9kSS2qhyivo9lMlt5qgAUasH2gb7BEOn6p0efFh24gjGomHzWKMAPn2hEReOPQZCJaRKoURwRotKucQ==" + }, + "@discordjs/form-data": { + "version": "3.0.1", + "resolved": "https://registry.npmjs.org/@discordjs/form-data/-/form-data-3.0.1.tgz", + "integrity": "sha512-ZfFsbgEXW71Rw/6EtBdrP5VxBJy4dthyC0tpQKGKmYFImlmmrykO14Za+BiIVduwjte0jXEBlhSKf0MWbFp9Eg==", + "requires": { + "asynckit": "^0.4.0", + "combined-stream": "^1.0.8", + "mime-types": "^2.1.12" + } + }, "@istanbuljs/load-nyc-config": { "version": "1.1.0", "resolved": "https://registry.npmjs.org/@istanbuljs/load-nyc-config/-/load-nyc-config-1.1.0.tgz", @@ -2940,6 +2955,14 @@ "csstype": "^3.0.2" } }, + "abort-controller": { + "version": "3.0.0", + "resolved": "https://registry.npmjs.org/abort-controller/-/abort-controller-3.0.0.tgz", + "integrity": "sha512-h8lQ8tacZYnR3vNQTgibj+tODHI5/+l06Au2Pcriv/Gmet0eaj4TwWH41sO9wnHDiQsEj19q0drzdWdeAHtweg==", + "requires": { + "event-target-shim": "^5.0.0" + } + }, "acorn": { "version": "7.4.0", "resolved": "https://registry.npmjs.org/acorn/-/acorn-7.4.0.tgz", @@ -3149,16 +3172,10 @@ "dev": true, "optional": true }, - "async-limiter": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/async-limiter/-/async-limiter-1.0.1.tgz", - "integrity": "sha512-csOlWGAcRFJaI6m+F2WKdnMKr4HhdhFVBk0H/QbJFMCr+uO2kwohwXQPxw/9OCxp05r5ghVBFSyioixx3gfkNQ==" - }, "asynckit": { "version": "0.4.0", "resolved": "https://registry.npmjs.org/asynckit/-/asynckit-0.4.0.tgz", - "integrity": "sha1-x57Zf380y48robyXkLzDZkdLS3k=", - "dev": true + "integrity": "sha1-x57Zf380y48robyXkLzDZkdLS3k=" }, "atob": { "version": "2.1.2", @@ -3831,7 +3848,6 @@ "version": "1.0.8", "resolved": "https://registry.npmjs.org/combined-stream/-/combined-stream-1.0.8.tgz", "integrity": "sha512-FQN4MRfuJeHf7cBbBMJFXhKSDq+2kAArBlmRBvcvFE5BB1HZKXtSFASDhdlz9zOYwxh8lDdnvmMOe/+5cdoEdg==", - "dev": true, "requires": { "delayed-stream": "~1.0.0" } @@ -4088,8 +4104,7 @@ "delayed-stream": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/delayed-stream/-/delayed-stream-1.0.0.tgz", - "integrity": "sha1-3zrhmayt+31ECqrgsp4icrJOxhk=", - "dev": true + "integrity": "sha1-3zrhmayt+31ECqrgsp4icrJOxhk=" }, "diff": { "version": "4.0.2", @@ -4098,15 +4113,18 @@ "dev": true }, "discord.js": { - "version": "11.5.1", - "resolved": "https://registry.npmjs.org/discord.js/-/discord.js-11.5.1.tgz", - "integrity": "sha512-tGhV5xaZXE3Z+4uXJb3hYM6gQ1NmnSxp9PClcsSAYFVRzH6AJH74040mO3afPDMWEAlj8XsoPXXTJHTxesqcGw==", + "version": "12.2.0", + "resolved": "https://registry.npmjs.org/discord.js/-/discord.js-12.2.0.tgz", + "integrity": "sha512-Ueb/0SOsxXyqwvwFYFe0msMrGqH1OMqpp2Dpbplnlr4MzcRrFWwsBM9gKNZXPVBHWUKiQkwU8AihXBXIvTTSvg==", "requires": { - "long": "^4.0.0", - "prism-media": "^0.0.3", - "snekfetch": "^3.6.4", - "tweetnacl": "^1.0.0", - "ws": "^6.0.0" + "@discordjs/collection": "^0.1.5", + "@discordjs/form-data": "^3.0.1", + "abort-controller": "^3.0.0", + "node-fetch": "^2.6.0", + "prism-media": "^1.2.0", + "setimmediate": "^1.0.5", + "tweetnacl": "^1.0.3", + "ws": "^7.2.1" } }, "doctrine": { @@ -4629,6 +4647,11 @@ "integrity": "sha1-Cr9PHKpbyx96nYrMbepPqqBLrJs=", "dev": true }, + "event-target-shim": { + "version": "5.0.1", + "resolved": "https://registry.npmjs.org/event-target-shim/-/event-target-shim-5.0.1.tgz", + "integrity": "sha512-i/2XbnSz/uxRCU6+NdVJgKWDTM427+MqYbkQzD321DuCQJUqOuJKIA0IM2+W2xtYHdKOmZ4dR6fExsd4SXL+WQ==" + }, "expand-brackets": { "version": "2.1.4", "resolved": "https://registry.npmjs.org/expand-brackets/-/expand-brackets-2.1.4.tgz", @@ -5972,11 +5995,6 @@ } } }, - "long": { - "version": "4.0.0", - "resolved": "https://registry.npmjs.org/long/-/long-4.0.0.tgz", - "integrity": "sha512-XsP+KhQif4bjX1kbuSiySJFNAehNxgLb6hPRGJ9QsUr8ajHkuXGdrHmFUTUUXhDwVX2R5bY4JNZEwbUiMhV+MA==" - }, "loose-envify": { "version": "1.4.0", "resolved": "https://registry.npmjs.org/loose-envify/-/loose-envify-1.4.0.tgz", @@ -6046,14 +6064,12 @@ "mime-db": { "version": "1.44.0", "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.44.0.tgz", - "integrity": "sha512-/NOTfLrsPBVeH7YtFPgsVWveuL+4SjjYxaQ1xtM1KMFj7HdxlBlxeyNLzhyJVx7r4rZGJAZ/6lkKCitSc/Nmpg==", - "dev": true + "integrity": "sha512-/NOTfLrsPBVeH7YtFPgsVWveuL+4SjjYxaQ1xtM1KMFj7HdxlBlxeyNLzhyJVx7r4rZGJAZ/6lkKCitSc/Nmpg==" }, "mime-types": { "version": "2.1.27", "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.27.tgz", "integrity": "sha512-JIhqnCasI9yD+SsmkquHBxTSEuZdQX5BuQnS2Vc7puQQQ+8yiP5AY5uWhpdv4YL4VM5c6iliiYWPgJ/nJQLp7w==", - "dev": true, "requires": { "mime-db": "1.44.0" } @@ -6471,6 +6487,11 @@ "path-to-regexp": "^1.7.0" } }, + "node-fetch": { + "version": "2.6.0", + "resolved": "https://registry.npmjs.org/node-fetch/-/node-fetch-2.6.0.tgz", + "integrity": "sha512-8dG4H5ujfvFiqDmVu9fQ5bOHUC15JMjMY/Zumv26oOvvVJjM67KF8koCWIabKQ1GJIa9r2mMZscBq/TbdOcmNA==" + }, "node-modules-regexp": { "version": "1.0.0", "resolved": "https://registry.npmjs.org/node-modules-regexp/-/node-modules-regexp-1.0.0.tgz", @@ -6975,9 +6996,9 @@ "dev": true }, "prism-media": { - "version": "0.0.3", - "resolved": "https://registry.npmjs.org/prism-media/-/prism-media-0.0.3.tgz", - "integrity": "sha512-c9KkNifSMU/iXT8FFTaBwBMr+rdVcN+H/uNv1o+CuFeTThNZNTOrQ+RgXA1yL/DeLk098duAeRPP3QNPNbhxYQ==" + "version": "1.2.2", + "resolved": "https://registry.npmjs.org/prism-media/-/prism-media-1.2.2.tgz", + "integrity": "sha512-I+nkWY212lJ500jLe4tN9tWO7nRiBAVdMv76P9kffZjYhw20raMlW1HSSvS+MLXC9MmbNZCazMrAr+5jEEgTuw==" }, "process-nextick-args": { "version": "2.0.1", @@ -7368,6 +7389,11 @@ } } }, + "setimmediate": { + "version": "1.0.5", + "resolved": "https://registry.npmjs.org/setimmediate/-/setimmediate-1.0.5.tgz", + "integrity": "sha1-KQy7Iy4waULX1+qbg3Mqt4VvgoU=" + }, "shebang-command": { "version": "2.0.0", "resolved": "https://registry.npmjs.org/shebang-command/-/shebang-command-2.0.0.tgz", @@ -7590,11 +7616,6 @@ } } }, - "snekfetch": { - "version": "3.6.4", - "resolved": "https://registry.npmjs.org/snekfetch/-/snekfetch-3.6.4.tgz", - "integrity": "sha512-NjxjITIj04Ffqid5lqr7XdgwM7X61c/Dns073Ly170bPQHLm6jkmelye/eglS++1nfTWktpP6Y2bFXjdPlQqdw==" - }, "source-map": { "version": "0.5.7", "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.5.7.tgz", @@ -8051,9 +8072,9 @@ } }, "tweetnacl": { - "version": "1.0.1", - "resolved": "https://registry.npmjs.org/tweetnacl/-/tweetnacl-1.0.1.tgz", - "integrity": "sha512-kcoMoKTPYnoeS50tzoqjPY3Uv9axeuuFAZY9M/9zFnhoVvRfxz9K29IMPD7jGmt2c8SW7i3gT9WqDl2+nV7p4A==" + "version": "1.0.3", + "resolved": "https://registry.npmjs.org/tweetnacl/-/tweetnacl-1.0.3.tgz", + "integrity": "sha512-6rt+RN7aOi1nGMyC4Xa5DdYiukl2UWCbcJft7YhxReBGQD7OAM8Pbxw6YMo4r2diNEA8FEmu32YOn9rhaiE5yw==" }, "type-check": { "version": "0.4.0", @@ -8415,12 +8436,9 @@ } }, "ws": { - "version": "6.2.1", - "resolved": "https://registry.npmjs.org/ws/-/ws-6.2.1.tgz", - "integrity": "sha512-GIyAXC2cB7LjvpgMt9EKS2ldqr0MTrORaleiOno6TweZ6r3TKtoFQWay/2PceJ3RuBasOHzXNn5Lrw1X0bEjqA==", - "requires": { - "async-limiter": "~1.0.0" - } + "version": "7.3.1", + "resolved": "https://registry.npmjs.org/ws/-/ws-7.3.1.tgz", + "integrity": "sha512-D3RuNkynyHmEJIpD2qrgVkc9DQ23OrN/moAwZX4L8DfvszsJxpjQuUq3LMx6HoYji9fbIOBY18XWBsAux1ZZUA==" }, "y18n": { "version": "4.0.0", diff --git a/package.json b/package.json index bc29ac6a..89d634d5 100644 --- a/package.json +++ b/package.json @@ -37,7 +37,7 @@ "license": "MIT", "dependencies": { "commander": "^6.0.0", - "discord.js": "11.5.1", + "discord.js": "12.2.0", "irc-colors": "1.5.0", "irc-formatting": "1.0.0-rc3", "irc-upd": "0.11.0", diff --git a/test/bot-events.test.js b/test/bot-events.test.js index 04947132..73af949d 100644 --- a/test/bot-events.test.js +++ b/test/bot-events.test.js @@ -7,6 +7,7 @@ import discord from 'discord.js'; import Bot from '../lib/bot'; import logger from '../lib/logger'; import createDiscordStub from './stubs/discord-stub'; +import createWebhookStub from './stubs/webhook-stub'; import ClientStub from './stubs/irc-client-stub'; import config from './fixtures/single-test-config.json'; @@ -34,9 +35,9 @@ describe('Bot Events', function () { this.warnSpy = sandbox.stub(logger, 'warn'); this.errorSpy = sandbox.stub(logger, 'error'); this.sendStub = sandbox.stub(); - this.getUserStub = sandbox.stub(); irc.Client = ClientStub; - discord.Client = createDiscordStub(this.sendStub, this.getUserStub); + discord.Client = createDiscordStub(this.sendStub); + discord.WebhookClient = createWebhookStub(this.sendStub); ClientStub.prototype.send = sandbox.stub(); ClientStub.prototype.join = sandbox.stub(); this.bot = createBot(); @@ -44,6 +45,7 @@ describe('Bot Events', function () { }); afterEach(function () { + this.bot.disconnect(); sandbox.restore(); }); diff --git a/test/bot.test.js b/test/bot.test.js index bcf38e93..90372773 100644 --- a/test/bot.test.js +++ b/test/bot.test.js @@ -28,9 +28,8 @@ describe('Bot', function () { this.errorSpy = sandbox.stub(logger, 'error'); this.sendStub = sandbox.stub(); - this.discordUsers = new discord.Collection(); irc.Client = ClientStub; - discord.Client = createDiscordStub(this.sendStub, this.discordUsers); + discord.Client = createDiscordStub(this.sendStub); ClientStub.prototype.say = sandbox.stub(); ClientStub.prototype.send = sandbox.stub(); @@ -40,7 +39,7 @@ describe('Bot', function () { this.setCustomBot = conf => { this.bot = new Bot(conf); - this.guild = this.bot.discord.guild; + this.guild = this.bot.discord.guilds.cache.first(); this.bot.connect(); }; @@ -53,21 +52,21 @@ describe('Bot', function () { // also set guild members const guildMember = { ...(member || user), user: userObj }; guildMember.nick = guildMember.nickname; // nick => nickname in Discord API - const memberObj = new discord.GuildMember(this.guild, guildMember); - this.guild.members.set(userObj.id, memberObj); - this.discordUsers.set(userObj.id, userObj); + const memberObj = new discord.GuildMember(this.bot.discord, guildMember, this.guild); + this.guild.members.cache.set(userObj.id, memberObj); + this.bot.discord.users.cache.set(userObj.id, userObj); return memberObj; }; this.addRole = function (role) { - const roleObj = new discord.Role(this.guild, role); - this.guild.roles.set(roleObj.id, roleObj); + const roleObj = new discord.Role(this.bot.discord, role, this.guild); + this.guild.roles.cache.set(roleObj.id, roleObj); return roleObj; }; this.addEmoji = function (emoji) { - const emojiObj = new discord.Emoji(this.guild, emoji); - this.guild.emojis.set(emojiObj.id, emojiObj); + const emojiObj = new discord.GuildEmoji(this.bot.discord, emoji, this.guild); + this.guild.emojis.cache.set(emojiObj.id, emojiObj); return emojiObj; }; }); @@ -627,7 +626,7 @@ describe('Bot', function () { this.setCustomBot(newConfig); const id = 'not bot id'; const nickname = 'discord-nickname'; - this.guild.members.set(id, { nickname }); + this.guild.members.cache.set(id, { nickname }); const message = { content: text, mentions: { users: [] }, @@ -1002,9 +1001,8 @@ describe('Bot', function () { this.bot.sendToDiscord('n', '#irc', text); this.sendWebhookMessageStub.should.have.been.calledWith(text, { username: 'n_', - text, avatarURL: null, - disableEveryone: true, + disableMentions: 'everyone', }); }); @@ -1013,9 +1011,8 @@ describe('Bot', function () { this.bot.sendToDiscord('1234567890123456789012345678901234567890', '#irc', text); this.sendWebhookMessageStub.should.have.been.calledWith(text, { username: '12345678901234567890123456789012', - text, avatarURL: null, - disableEveryone: true, + disableMentions: 'everyone', }); }); @@ -1023,16 +1020,15 @@ describe('Bot', function () { const text = 'message'; const permission = discord.Permissions.FLAGS.VIEW_CHANNEL + discord.Permissions.FLAGS.SEND_MESSAGES; - this.bot.discord.channels.get('1234').setPermissionStub( + this.bot.discord.channels.cache.get('1234').setPermissionStub( this.bot.discord.user, new discord.Permissions(permission), ); this.bot.sendToDiscord('nick', '#irc', text); this.sendWebhookMessageStub.should.have.been.calledWith(text, { username: 'nick', - text, avatarURL: null, - disableEveryone: true, + disableMentions: 'everyone', }); }); @@ -1041,16 +1037,15 @@ describe('Bot', function () { const permission = discord.Permissions.FLAGS.VIEW_CHANNEL + discord.Permissions.FLAGS.SEND_MESSAGES + discord.Permissions.FLAGS.MENTION_EVERYONE; - this.bot.discord.channels.get('1234').setPermissionStub( + this.bot.discord.channels.cache.get('1234').setPermissionStub( this.bot.discord.user, new discord.Permissions(permission), ); this.bot.sendToDiscord('nick', '#irc', text); this.sendWebhookMessageStub.should.have.been.calledWith(text, { username: 'nick', - text, avatarURL: null, - disableEveryone: false, + disableMentions: 'none', }); }); diff --git a/test/stubs/discord-stub.js b/test/stubs/discord-stub.js index 72979fac..484e07cf 100644 --- a/test/stubs/discord-stub.js +++ b/test/stubs/discord-stub.js @@ -3,29 +3,33 @@ import events from 'events'; import sinon from 'sinon'; import discord from 'discord.js'; -export default function createDiscordStub(sendStub, discordUsers) { +export default function createDiscordStub(sendStub) { return class DiscordStub extends events.EventEmitter { constructor() { super(); this.user = { id: 'testid' }; - this.channels = new discord.Collection(); + this.channels = new discord.ChannelManager(this, []); this.options = { http: { cdn: '' } }; - this.users = discordUsers; - this.guilds = new discord.Collection(); - this.guild = this.createGuildStub(); - this.guilds.set(this.guild.id, this.guild); + this.users = new discord.UserManager(this, []); + this.guilds = new discord.GuildManager(this, []); + const guild = this.createGuildStub(); + this.guilds.cache.set(guild.id, guild); + + this.rest = this.createRestStub(); } + destroy() {} + addTextChannel(guild, textChannel) { const textChannelData = { - type: 'text', + type: discord.Constants.ChannelTypes.TEXT, ...textChannel }; const textChannelObj = new discord.TextChannel(guild, textChannelData); @@ -33,7 +37,7 @@ export default function createDiscordStub(sendStub, discordUsers) { const permissions = new discord.Collection(); textChannelObj.setPermissionStub = (user, perms) => permissions.set(user, perms); textChannelObj.permissionsFor = user => permissions.get(user); - this.channels.set(textChannelObj.id, textChannelObj); + this.channels.cache.set(textChannelObj.id, textChannelObj); return textChannelObj; } @@ -41,18 +45,18 @@ export default function createDiscordStub(sendStub, discordUsers) { const guild = { id: '1', client: this, - roles: new discord.Collection(), - members: new discord.Collection(), - emojis: new discord.Collection(), - channels: new discord.Collection(), addTextChannel: (textChannel) => { const textChannelObj = this.addTextChannel(guild, textChannel); - textChannelObj.guild.channels.set(textChannelObj.id, textChannelObj); + textChannelObj.guild.channels.cache.set(textChannelObj.id, textChannelObj); return textChannelObj; } }; + guild.roles = new discord.RoleManager(guild, []); + guild.members = new discord.GuildMemberManager(guild, []); + guild.emojis = new discord.GuildEmojiManager(guild, []); + guild.channels = new discord.GuildChannelManager(guild, []); Object.assign(guild, guildData); - this.guilds.set(guild.id, guild); + this.guilds.cache.set(guild.id, guild); if (guild.id === '1') { guild.addTextChannel({ @@ -64,6 +68,12 @@ export default function createDiscordStub(sendStub, discordUsers) { return guild; } + createRestStub() { + return { + cdn: discord.Constants.Endpoints.CDN(''), + }; + } + login() { return sinon.stub(); } diff --git a/test/stubs/irc-client-stub.js b/test/stubs/irc-client-stub.js index 195c394e..935d02be 100644 --- a/test/stubs/irc-client-stub.js +++ b/test/stubs/irc-client-stub.js @@ -1,10 +1,13 @@ import events from 'events'; +/* eslint-disable class-methods-use-this */ class ClientStub extends events.EventEmitter { constructor(...args) { super(); this.nick = args[1]; // eslint-disable-line prefer-destructuring } + + disconnect() {} } export default ClientStub; diff --git a/test/stubs/webhook-stub.js b/test/stubs/webhook-stub.js index 79e6b27c..6ec8aabc 100644 --- a/test/stubs/webhook-stub.js +++ b/test/stubs/webhook-stub.js @@ -6,9 +6,11 @@ export default function createWebhookStub(sendWebhookMessage) { this.token = token; } - sendMessage(...args) { + send(...args) { sendWebhookMessage(...args); return new Promise(() => {}); } + + destroy() {} }; }