summaryrefslogtreecommitdiff
path: root/node_modules/discord.js/src/structures/GuildChannel.js
diff options
context:
space:
mode:
author8cy <[email protected]>2020-04-03 02:37:42 -0700
committer8cy <[email protected]>2020-04-03 02:37:42 -0700
commit60867fb030bae582082340ead7dbc7efdc2f5398 (patch)
tree4c6a7356351be2e4914e15c4703172597c45656e /node_modules/discord.js/src/structures/GuildChannel.js
parentcommenting (diff)
downloads5nical-60867fb030bae582082340ead7dbc7efdc2f5398.tar.xz
s5nical-60867fb030bae582082340ead7dbc7efdc2f5398.zip
2020/04/03, 02:34, v1.2.0
Diffstat (limited to 'node_modules/discord.js/src/structures/GuildChannel.js')
-rw-r--r--node_modules/discord.js/src/structures/GuildChannel.js601
1 files changed, 601 insertions, 0 deletions
diff --git a/node_modules/discord.js/src/structures/GuildChannel.js b/node_modules/discord.js/src/structures/GuildChannel.js
new file mode 100644
index 0000000..0dbc0e3
--- /dev/null
+++ b/node_modules/discord.js/src/structures/GuildChannel.js
@@ -0,0 +1,601 @@
+const Channel = require('./Channel');
+const Role = require('./Role');
+const PermissionOverwrites = require('./PermissionOverwrites');
+const Permissions = require('../util/Permissions');
+const Collection = require('../util/Collection');
+const Constants = require('../util/Constants');
+const Invite = require('./Invite');
+const Util = require('../util/Util');
+
+/**
+ * Represents a guild channel (i.e. text channels and voice channels).
+ * @extends {Channel}
+ */
+class GuildChannel extends Channel {
+ constructor(guild, data) {
+ super(guild.client, data);
+
+ /**
+ * The guild the channel is in
+ * @type {Guild}
+ */
+ this.guild = guild;
+ }
+
+ setup(data) {
+ super.setup(data);
+
+ /**
+ * The name of the guild channel
+ * @type {string}
+ */
+ this.name = data.name;
+
+ /**
+ * The position of the channel in the list
+ * @type {number}
+ */
+ this.position = data.position;
+
+ /**
+ * The ID of the category parent of this channel
+ * @type {?Snowflake}
+ */
+ this.parentID = data.parent_id;
+
+ /**
+ * A map of permission overwrites in this channel for roles and users
+ * @type {Collection<Snowflake, PermissionOverwrites>}
+ */
+ this.permissionOverwrites = new Collection();
+ if (data.permission_overwrites) {
+ for (const overwrite of data.permission_overwrites) {
+ this.permissionOverwrites.set(overwrite.id, new PermissionOverwrites(this, overwrite));
+ }
+ }
+ }
+
+ /**
+ * The position of the channel
+ * @type {number}
+ * @readonly
+ */
+ get calculatedPosition() {
+ const sorted = this.guild._sortedChannels(this.type);
+ return sorted.array().indexOf(sorted.get(this.id));
+ }
+
+ /**
+ * The category parent of this channel
+ * @type {?CategoryChannel}
+ * @readonly
+ */
+ get parent() {
+ return this.guild.channels.get(this.parentID) || null;
+ }
+
+ /**
+ * If the permissionOverwrites match the parent channel, null if no parent
+ * @type {?boolean}
+ * @readonly
+ */
+ get permissionsLocked() {
+ if (!this.parent) return null;
+ if (this.permissionOverwrites.size !== this.parent.permissionOverwrites.size) return false;
+ return this.permissionOverwrites.every((value, key) => {
+ const testVal = this.parent.permissionOverwrites.get(key);
+ return testVal !== undefined &&
+ testVal.deny === value.deny &&
+ testVal.allow === value.allow;
+ });
+ }
+
+ /**
+ * Gets the overall set of permissions for a user in this channel, taking into account channel overwrites.
+ * @param {GuildMemberResolvable} member The user that you want to obtain the overall permissions for
+ * @returns {?Permissions}
+ */
+ memberPermissions(member) {
+ member = this.client.resolver.resolveGuildMember(this.guild, member);
+ if (!member) return null;
+
+ if (member.id === this.guild.ownerID) return new Permissions(member, Permissions.ALL);
+
+ const roles = member.roles;
+ const permissions = new Permissions(roles.map(role => role.permissions));
+
+ if (permissions.has(Permissions.FLAGS.ADMINISTRATOR)) return new Permissions(Permissions.ALL).freeze();
+
+ const overwrites = this.overwritesFor(member, true, roles);
+
+ return permissions
+ .remove(overwrites.everyone ? overwrites.everyone.deny : 0)
+ .add(overwrites.everyone ? overwrites.everyone.allow : 0)
+ .remove(overwrites.roles.length > 0 ? overwrites.roles.map(role => role.deny) : 0)
+ .add(overwrites.roles.length > 0 ? overwrites.roles.map(role => role.allow) : 0)
+ .remove(overwrites.member ? overwrites.member.deny : 0)
+ .add(overwrites.member ? overwrites.member.allow : 0)
+ .freeze();
+ }
+
+ /**
+ * Gets the overall set of permissions for a role in this channel, taking into account channel overwrites.
+ * @param {RoleResolvable} role The role that you want to obtain the overall permissions for
+ * @returns {?Permissions}
+ */
+ rolePermissions(role) {
+ if (role.permissions & Permissions.FLAGS.ADMINISTRATOR) return new Permissions(Permissions.ALL).freeze();
+
+ const everyoneOverwrites = this.permissionOverwrites.get(this.guild.id);
+ const roleOverwrites = this.permissionOverwrites.get(role.id);
+
+ return new Permissions(role.permissions)
+ .remove(everyoneOverwrites ? everyoneOverwrites.deny : 0)
+ .add(everyoneOverwrites ? everyoneOverwrites.allow : 0)
+ .remove(roleOverwrites ? roleOverwrites.deny : 0)
+ .add(roleOverwrites ? roleOverwrites.allow : 0)
+ .freeze();
+ }
+
+ /**
+ * Get the overall set of permissions for a member or role in this channel, taking into account channel overwrites.
+ * @param {GuildMemberResolvable|RoleResolvable} memberOrRole The member or role to obtain the overall permissions for
+ * @returns {?Permissions}
+ */
+ permissionsFor(memberOrRole) {
+ const member = this.guild.member(memberOrRole);
+ if (member) return this.memberPermissions(member);
+ const role = this.client.resolver.resolveRole(this.guild, memberOrRole);
+ if (role) return this.rolePermissions(role);
+ return null;
+ }
+
+ overwritesFor(member, verified = false, roles = null) {
+ if (!verified) member = this.client.resolver.resolveGuildMember(this.guild, member);
+ if (!member) return [];
+
+ roles = roles || member.roles;
+ const roleOverwrites = [];
+ let memberOverwrites;
+ let everyoneOverwrites;
+
+ for (const overwrite of this.permissionOverwrites.values()) {
+ if (overwrite.id === this.guild.id) {
+ everyoneOverwrites = overwrite;
+ } else if (roles.has(overwrite.id)) {
+ roleOverwrites.push(overwrite);
+ } else if (overwrite.id === member.id) {
+ memberOverwrites = overwrite;
+ }
+ }
+
+ return {
+ everyone: everyoneOverwrites,
+ roles: roleOverwrites,
+ member: memberOverwrites,
+ };
+ }
+
+ /**
+ * Replaces the permission overwrites for a channel
+ * @param {Object} [options] Options
+ * @param {ChannelCreationOverwrites[]|Collection<Snowflake, PermissionOverwrites>} [options.overwrites]
+ * Permission overwrites
+ * @param {string} [options.reason] Reason for updating the channel overwrites
+ * @returns {Promise<GuildChannel>}
+ * @example
+ * channel.replacePermissionOverwrites({
+ * overwrites: [
+ * {
+ * id: message.author.id,
+ * denied: ['VIEW_CHANNEL'],
+ * },
+ * ],
+ * reason: 'Needed to change permissions'
+ * });
+ */
+ replacePermissionOverwrites({ overwrites, reason } = {}) {
+ return this.edit({ permissionOverwrites: overwrites, reason })
+ .then(() => this);
+ }
+
+ /**
+ * An object mapping permission flags to `true` (enabled), `null` (unset) or `false` (disabled).
+ * ```js
+ * {
+ * 'SEND_MESSAGES': true,
+ * 'EMBED_LINKS': null,
+ * 'ATTACH_FILES': false,
+ * }
+ * ```
+ * @typedef {Object} PermissionOverwriteOptions
+ */
+
+ /**
+ * Overwrites the permissions for a user or role in this channel.
+ * @param {Role|Snowflake|UserResolvable} userOrRole The user or role to update
+ * @param {PermissionOverwriteOptions} options The configuration for the update
+ * @param {string} [reason] Reason for creating/editing this overwrite
+ * @returns {Promise<GuildChannel>}
+ * @example
+ * // Overwrite permissions for a message author
+ * message.channel.overwritePermissions(message.author, {
+ * SEND_MESSAGES: false
+ * })
+ * .then(updated => console.log(updated.permissionOverwrites.get(message.author.id)))
+ * .catch(console.error);
+ * @example
+ * // Overwite permissions for a message author and reset some
+ * message.channel.overwritePermissions(message.author, {
+ * VIEW_CHANNEL: false,
+ * SEND_MESSAGES: null
+ * })
+ * .then(updated => console.log(updated.permissionOverwrites.get(message.author.id)))
+ * .catch(console.error);
+ */
+ overwritePermissions(userOrRole, options, reason) {
+ const payload = {
+ allow: 0,
+ deny: 0,
+ };
+
+ if (userOrRole instanceof Role) {
+ payload.type = 'role';
+ } else if (this.guild.roles.has(userOrRole)) {
+ userOrRole = this.guild.roles.get(userOrRole);
+ payload.type = 'role';
+ } else {
+ userOrRole = this.client.resolver.resolveUser(userOrRole);
+ payload.type = 'member';
+ if (!userOrRole) return Promise.reject(new TypeError('Supplied parameter was neither a User nor a Role.'));
+ }
+
+ payload.id = userOrRole.id;
+
+ const prevOverwrite = this.permissionOverwrites.get(userOrRole.id);
+
+ if (prevOverwrite) {
+ payload.allow = prevOverwrite.allow;
+ payload.deny = prevOverwrite.deny;
+ }
+
+ for (const perm of Object.keys(options)) {
+ if (options[perm] === true) {
+ payload.allow |= Permissions.FLAGS[perm] || 0;
+ payload.deny &= ~(Permissions.FLAGS[perm] || 0);
+ } else if (options[perm] === false) {
+ payload.allow &= ~(Permissions.FLAGS[perm] || 0);
+ payload.deny |= Permissions.FLAGS[perm] || 0;
+ } else if (options[perm] === null) {
+ payload.allow &= ~(Permissions.FLAGS[perm] || 0);
+ payload.deny &= ~(Permissions.FLAGS[perm] || 0);
+ }
+ }
+
+ return this.client.rest.methods.setChannelOverwrite(this, payload, reason).then(() => this);
+ }
+
+ /**
+ * Locks in the permission overwrites from the parent channel.
+ * @returns {Promise<GuildChannel>}
+ */
+ lockPermissions() {
+ if (!this.parent) return Promise.reject(new TypeError('Could not find a parent to this guild channel.'));
+ const permissionOverwrites = this.parent.permissionOverwrites.map(overwrite => ({
+ deny: overwrite.deny,
+ allow: overwrite.allow,
+ id: overwrite.id,
+ type: overwrite.type,
+ }));
+ return this.edit({ permissionOverwrites });
+ }
+
+ /**
+ * The data for a guild channel.
+ * @typedef {Object} ChannelData
+ * @property {string} [type] The type of the channel (Only when creating)
+ * @property {string} [name] The name of the channel
+ * @property {number} [position] The position of the channel
+ * @property {string} [topic] The topic of the text channel
+ * @property {boolean} [nsfw] Whether the channel is NSFW
+ * @property {number} [bitrate] The bitrate of the voice channel
+ * @property {number} [userLimit] The user limit of the channel
+ * @property {CategoryChannel|Snowflake} [parent] The parent or parent ID of the channel
+ * @property {ChannelCreationOverwrites[]|Collection<Snowflake, PermissionOverwrites>} [permissionOverwrites]
+ * Overwrites of the channel
+ * @property {number} [rateLimitPerUser] The rate limit per user of the channel in seconds
+ * @property {string} [reason] Reason for creating the channel (Only when creating)
+ */
+
+ /**
+ * Edits the channel.
+ * @param {ChannelData} data The new data for the channel
+ * @param {string} [reason] Reason for editing this channel
+ * @returns {Promise<GuildChannel>}
+ * @example
+ * // Edit a channel
+ * channel.edit({ name: 'new-channel' })
+ * .then(console.log)
+ * .catch(console.error);
+ */
+ edit(data, reason) {
+ return this.client.rest.methods.updateChannel(this, data, reason).then(() => this);
+ }
+
+ /**
+ * Set a new name for the guild channel.
+ * @param {string} name The new name for the guild channel
+ * @param {string} [reason] Reason for changing the guild channel's name
+ * @returns {Promise<GuildChannel>}
+ * @example
+ * // Set a new channel name
+ * channel.setName('not_general')
+ * .then(newChannel => console.log(`Channel's new name is ${newChannel.name}`))
+ * .catch(console.error);
+ */
+ setName(name, reason) {
+ return this.edit({ name }, reason);
+ }
+
+ /**
+ * Set a new position for the guild channel.
+ * @param {number} position The new position for the guild channel
+ * @param {boolean} [relative=false] Move the position relative to its current value
+ * @returns {Promise<GuildChannel>}
+ * @example
+ * // Set a new channel position
+ * channel.setPosition(2)
+ * .then(newChannel => console.log(`Channel's new position is ${newChannel.position}`))
+ * .catch(console.error);
+ */
+ setPosition(position, relative) {
+ return this.guild.setChannelPosition(this, position, relative).then(() => this);
+ }
+
+ /**
+ * Set a new parent for the guild channel.
+ * @param {CategoryChannel|SnowFlake} parent The new parent for the guild channel
+ * @param {string} [reason] Reason for changing the guild channel's parent
+ * @returns {Promise<GuildChannel>}
+ * @example
+ * // Sets the parent of a channel
+ * channel.setParent('174674066072928256')
+ * .then(updated => console.log(`Set the category of ${updated.name} to ${updated.parent.name}`))
+ * .catch(console.error);
+ */
+ setParent(parent, reason) {
+ parent = this.client.resolver.resolveChannelID(parent);
+ return this.edit({ parent }, reason);
+ }
+
+ /**
+ * Set a new topic for the guild channel.
+ * @param {string} topic The new topic for the guild channel
+ * @param {string} [reason] Reason for changing the guild channel's topic
+ * @returns {Promise<GuildChannel>}
+ * @example
+ * // Set a new channel topic
+ * channel.setTopic('Needs more rate limiting')
+ * .then(updated => console.log(`Channel's new topic is ${updated.topic}`))
+ * .catch(console.error);
+ */
+ setTopic(topic, reason) {
+ return this.edit({ topic }, reason);
+ }
+
+ /**
+ * Create an invite to this guild channel.
+ * <warn>This is only available when using a bot account.</warn>
+ * @param {Object} [options={}] Options for the invite
+ * @param {boolean} [options.temporary=false] Whether members that joined via the invite should be automatically
+ * kicked after 24 hours if they have not yet received a role
+ * @param {number} [options.maxAge=86400] How long the invite should last (in seconds, 0 for forever)
+ * @param {number} [options.maxUses=0] Maximum number of uses
+ * @param {boolean} [options.unique=false] Create a unique invite, or use an existing one with similar settings
+ * @param {string} [reason] Reason for creating the invite
+ * @returns {Promise<Invite>}
+ * @example
+ * // Create an invite to a channel
+ * channel.createInvite()
+ * .then(invite => console.log(`Created an invite with a code of ${invite.code}`))
+ * .catch(console.error);
+ */
+ createInvite(options = {}, reason) {
+ return this.client.rest.methods.createChannelInvite(this, options, reason);
+ }
+
+ /* eslint-disable max-len */
+ /**
+ * Options to clone a guild channel.
+ * @typedef {Object} GuildChannelCloneOptions
+ * @property {string} [name=this.name] Name of the new channel
+ * @property {ChannelCreationOverwrites[]|Collection<Snowflake, PermissionOverwrites>} [permissionOverwrites=this.permissionOverwrites]
+ * Permission overwrites of the new channel
+ * @property {string} [type=this.type] Type of the new channel
+ * @property {string} [topic=this.topic] Topic of the new channel (only text)
+ * @property {boolean} [nsfw=this.nsfw] Whether the new channel is nsfw (only text)
+ * @property {number} [bitrate=this.bitrate] Bitrate of the new channel in bits (only voice)
+ * @property {number} [userLimit=this.userLimit] Maximum amount of users allowed in the new channel (only voice)
+ * @property {number} [rateLimitPerUser=ThisType.rateLimitPerUser] Ratelimit per user for the new channel (only text)
+ * @property {ChannelResolvable} [parent=this.parent] Parent of the new channel
+ * @property {string} [reason] Reason for cloning this channel
+ */
+ /* eslint-enable max-len */
+
+ /**
+ * Clone this channel.
+ * @param {string|GuildChannelCloneOptions} [nameOrOptions={}] Name for the new channel.
+ * **(deprecated, use options)**
+ * Alternatively options for cloning the channel
+ * @param {boolean} [withPermissions=true] Whether to clone the channel with this channel's permission overwrites
+ * **(deprecated, use options)**
+ * @param {boolean} [withTopic=true] Whether to clone the channel with this channel's topic
+ * **(deprecated, use options)**
+ * @param {string} [reason] Reason for cloning this channel **(deprecated, user options)**
+ * @returns {Promise<GuildChannel>}
+ * @example
+ * // Clone a channel
+ * channel.clone({ topic: null, reason: 'Needed a clone' })
+ * .then(clone => console.log(`Cloned ${channel.name} to make a channel called ${clone.name}`))
+ * .catch(console.error);
+ */
+ clone(nameOrOptions = {}, withPermissions = true, withTopic = true, reason) {
+ // If more than one parameter was specified or the first is a string,
+ // convert them to a compatible options object and issue a warning
+ if (arguments.length > 1 || typeof nameOrOptions === 'string') {
+ process.emitWarning(
+ 'GuildChannel#clone: Clone channels using an options object instead of separate parameters.',
+ 'Deprecation Warning'
+ );
+
+ nameOrOptions = {
+ name: nameOrOptions,
+ permissionOverwrites: withPermissions ? this.permissionOverwrites : null,
+ topic: withTopic ? this.topic : null,
+ reason: reason || null,
+ };
+ }
+
+ Util.mergeDefault({
+ name: this.name,
+ permissionOverwrites: this.permissionOverwrites,
+ topic: this.topic,
+ type: this.type,
+ nsfw: this.nsfw,
+ parent: this.parent,
+ bitrate: this.bitrate,
+ userLimit: this.userLimit,
+ rateLimitPerUser: this.rateLimitPerUser,
+ reason: null,
+ }, nameOrOptions);
+
+ return this.guild.createChannel(nameOrOptions.name, nameOrOptions);
+ }
+
+ /**
+ * Fetches a collection of invites to this guild channel.
+ * Resolves with a collection mapping invites by their codes.
+ * @returns {Promise<Collection<string, Invite>>}
+ */
+ fetchInvites() {
+ return this.client.rest.makeRequest('get', Constants.Endpoints.Channel(this.id).invites, true)
+ .then(data => {
+ const invites = new Collection();
+ for (let invite of data) {
+ invite = new Invite(this.client, invite);
+ invites.set(invite.code, invite);
+ }
+
+ return invites;
+ });
+ }
+
+ /**
+ * Deletes this channel.
+ * @param {string} [reason] Reason for deleting this channel
+ * @returns {Promise<GuildChannel>}
+ * @example
+ * // Delete the channel
+ * channel.delete('Making room for new channels')
+ * .then(deleted => console.log(`Deleted ${deleted.name} to make room for new channels`))
+ * .catch(console.error);
+ */
+ delete(reason) {
+ return this.client.rest.methods.deleteChannel(this, reason);
+ }
+
+ /**
+ * Checks if this channel has the same type, topic, position, name, overwrites and ID as another channel.
+ * In most cases, a simple `channel.id === channel2.id` will do, and is much faster too.
+ * @param {GuildChannel} channel Channel to compare with
+ * @returns {boolean}
+ */
+ equals(channel) {
+ let equal = channel &&
+ this.id === channel.id &&
+ this.type === channel.type &&
+ this.topic === channel.topic &&
+ this.position === channel.position &&
+ this.name === channel.name;
+
+ if (equal) {
+ if (this.permissionOverwrites && channel.permissionOverwrites) {
+ equal = this.permissionOverwrites.equals(channel.permissionOverwrites);
+ } else {
+ equal = !this.permissionOverwrites && !channel.permissionOverwrites;
+ }
+ }
+
+ return equal;
+ }
+
+ /**
+ * Whether the channel is deletable by the client user
+ * @type {boolean}
+ * @readonly
+ */
+ get deletable() {
+ return this.id !== this.guild.id &&
+ this.permissionsFor(this.client.user).has(Permissions.FLAGS.MANAGE_CHANNELS);
+ }
+
+ /**
+ * Whether the channel is manageable by the client user
+ * @type {boolean}
+ * @readonly
+ */
+ get manageable() {
+ if (this.client.user.id === this.guild.ownerID) return true;
+ const permissions = this.permissionsFor(this.client.user);
+ if (!permissions) return false;
+ return permissions.has([Permissions.FLAGS.MANAGE_CHANNELS, Permissions.FLAGS.VIEW_CHANNEL]);
+ }
+
+ /**
+ * Whether the channel is muted
+ * <warn>This is only available when using a user account.</warn>
+ * @type {?boolean}
+ * @readonly
+ * @deprecated
+ */
+ get muted() {
+ if (this.client.user.bot) return null;
+ try {
+ return this.client.user.guildSettings.get(this.guild.id).channelOverrides.get(this.id).muted;
+ } catch (err) {
+ return false;
+ }
+ }
+
+ /**
+ * The type of message that should notify you
+ * <warn>This is only available when using a user account.</warn>
+ * @type {?MessageNotificationType}
+ * @readonly
+ * @deprecated
+ */
+ get messageNotifications() {
+ if (this.client.user.bot) return null;
+ try {
+ return this.client.user.guildSettings.get(this.guild.id).channelOverrides.get(this.id).messageNotifications;
+ } catch (err) {
+ return Constants.MessageNotificationTypes[3];
+ }
+ }
+
+ /**
+ * When concatenated with a string, this automatically returns the channel's mention instead of the Channel object.
+ * @returns {string}
+ * @example
+ * // Logs: Hello from <#123456789012345678>
+ * console.log(`Hello from ${channel}`);
+ * @example
+ * // Logs: Hello from <#123456789012345678>
+ * console.log('Hello from ' + channel);
+ */
+ toString() {
+ return `<#${this.id}>`;
+ }
+}
+
+module.exports = GuildChannel;