mirror of
https://github.com/discordjs/discord.js.git
synced 2026-03-09 16:13:31 +01:00
Merge branch 'master' of https://github.com/hydrabolt/discord.js
This commit is contained in:
@@ -19,6 +19,7 @@ const Channel = require('../../structures/Channel');
|
||||
const GroupDMChannel = require('../../structures/GroupDMChannel');
|
||||
const Guild = require('../../structures/Guild');
|
||||
const VoiceRegion = require('../../structures/VoiceRegion');
|
||||
const GuildAuditLogs = require('../../structures/GuildAuditLogs');
|
||||
|
||||
class RESTMethods {
|
||||
constructor(restManager) {
|
||||
@@ -386,8 +387,9 @@ class RESTMethods {
|
||||
);
|
||||
}
|
||||
|
||||
kickGuildMember(guild, member) {
|
||||
return this.rest.makeRequest('delete', Endpoints.Guild(guild).Member(member), true).then(() =>
|
||||
kickGuildMember(guild, member, reason) {
|
||||
const url = `${Endpoints.Guild(guild).Member(member)}?reason=${reason}`;
|
||||
return this.rest.makeRequest('delete', url, true).then(() =>
|
||||
this.client.actions.GuildMemberRemove.handle({
|
||||
guild_id: guild.id,
|
||||
user: member.user,
|
||||
@@ -530,14 +532,12 @@ class RESTMethods {
|
||||
return this.rest.makeRequest('post', Endpoints.Channel(channelID).typing, true);
|
||||
}
|
||||
|
||||
banGuildMember(guild, member, deleteDays = 0) {
|
||||
banGuildMember(guild, member, options) {
|
||||
const id = this.client.resolver.resolveUserID(member);
|
||||
if (!id) return Promise.reject(new Error('Couldn\'t resolve the user ID to ban.'));
|
||||
return this.rest.makeRequest(
|
||||
'put', `${Endpoints.Guild(guild).bans}/${id}?delete-message-days=${deleteDays}`, true, {
|
||||
'delete-message-days': deleteDays,
|
||||
}
|
||||
).then(() => {
|
||||
|
||||
const url = `${Endpoints.Guild(guild).bans}/${id}?${querystring.stringify(options)}`;
|
||||
return this.rest.makeRequest('put', url, true).then(() => {
|
||||
if (member instanceof GuildMember) return member;
|
||||
const user = this.client.resolver.resolveUser(id);
|
||||
if (user) {
|
||||
@@ -576,14 +576,15 @@ class RESTMethods {
|
||||
}
|
||||
|
||||
getGuildBans(guild) {
|
||||
return this.rest.makeRequest('get', Endpoints.Guild(guild).bans, true).then(banItems => {
|
||||
const bannedUsers = new Collection();
|
||||
for (const banItem of banItems) {
|
||||
const user = this.client.dataManager.newUser(banItem.user);
|
||||
bannedUsers.set(user.id, user);
|
||||
}
|
||||
return bannedUsers;
|
||||
});
|
||||
return this.rest.makeRequest('get', Endpoints.Guild(guild).bans, true).then(bans =>
|
||||
bans.reduce((collection, ban) => {
|
||||
collection.set(ban.user.id, {
|
||||
reason: ban.reason,
|
||||
user: this.client.dataManager.newUser(ban.user),
|
||||
});
|
||||
return collection;
|
||||
}, new Collection())
|
||||
);
|
||||
}
|
||||
|
||||
updateGuildRole(role, _data) {
|
||||
@@ -674,6 +675,23 @@ class RESTMethods {
|
||||
.then(() => this.client.actions.GuildEmojiDelete.handle(emoji).data);
|
||||
}
|
||||
|
||||
getGuildAuditLogs(guild, options = {}) {
|
||||
if (options.before && options.before instanceof GuildAuditLogs.Entry) options.before = options.before.id;
|
||||
if (options.after && options.after instanceof GuildAuditLogs.Entry) options.after = options.after.id;
|
||||
if (typeof options.type === 'string') options.type = GuildAuditLogs.Actions[options.type];
|
||||
|
||||
const queryString = (querystring.stringify({
|
||||
before: options.before,
|
||||
after: options.after,
|
||||
limit: options.limit,
|
||||
user_id: this.client.resolver.resolveUserID(options.user),
|
||||
action_type: options.type,
|
||||
}).match(/[^=&?]+=[^=&?]+/g) || []).join('&');
|
||||
|
||||
return this.rest.makeRequest('get', `${Endpoints.Guild(guild).auditLogs}?${queryString}`, true)
|
||||
.then(data => GuildAuditLogs.build(guild, data));
|
||||
}
|
||||
|
||||
getWebhook(id, token) {
|
||||
return this.rest.makeRequest('get', Endpoints.Webhook(id, token), !token).then(data =>
|
||||
new Webhook(this.client, data)
|
||||
|
||||
@@ -347,7 +347,13 @@ class Guild {
|
||||
* @returns {Promise<Collection<Snowflake, User>>}
|
||||
*/
|
||||
fetchBans() {
|
||||
return this.client.rest.methods.getGuildBans(this);
|
||||
return this.client.rest.methods.getGuildBans(this)
|
||||
// This entire re-mapping can be removed in the next major release
|
||||
.then(bans => {
|
||||
const users = new Collection();
|
||||
for (const ban of bans.values()) users.set(ban.user.id, ban.user);
|
||||
return users;
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -374,6 +380,20 @@ class Guild {
|
||||
return this.client.rest.methods.fetchVoiceRegions(this.id);
|
||||
}
|
||||
|
||||
/**
|
||||
* Fetch audit logs for this guild
|
||||
* @param {Object} [options={}] Options for fetching audit logs
|
||||
* @param {Snowflake|GuildAuditLogsEntry} [options.before] Limit to entries from before specified entry
|
||||
* @param {Snowflake|GuildAuditLogsEntry} [options.after] Limit to entries from after specified entry
|
||||
* @param {number} [options.limit] Limit number of entries
|
||||
* @param {UserResolvable} [options.user] Only show entries involving this user
|
||||
* @param {string|number} [options.type] Only show entries involving this action type
|
||||
* @returns {Promise<GuildAuditLogs>}
|
||||
*/
|
||||
fetchAuditLogs(options) {
|
||||
return this.client.rest.methods.getGuildAuditLogs(this, options);
|
||||
}
|
||||
|
||||
/**
|
||||
* Adds a user to the guild using OAuth2. Requires the `CREATE_INSTANT_INVITE` permission.
|
||||
* @param {UserResolvable} user User to add to the guild
|
||||
@@ -607,8 +627,9 @@ class Guild {
|
||||
/**
|
||||
* Bans a user from the guild.
|
||||
* @param {UserResolvable} user The user to ban
|
||||
* @param {number} [deleteDays=0] The amount of days worth of messages from this user that should
|
||||
* also be deleted. Between `0` and `7`.
|
||||
* @param {Object} [options] Ban options.
|
||||
* @param {number} [options.days=0] Number of days of messages to delete
|
||||
* @param {string} [options.reason] Reason for banning
|
||||
* @returns {Promise<GuildMember|User|string>} Result object will be resolved as specifically as possible.
|
||||
* If the GuildMember cannot be resolved, the User will instead be attempted to be resolved. If that also cannot
|
||||
* be resolved, the user ID will be the result.
|
||||
@@ -618,8 +639,13 @@ class Guild {
|
||||
* .then(user => console.log(`Banned ${user.username || user.id || user} from ${guild.name}`))
|
||||
* .catch(console.error);
|
||||
*/
|
||||
ban(user, deleteDays = 0) {
|
||||
return this.client.rest.methods.banGuildMember(this, user, deleteDays);
|
||||
ban(user, options = {}) {
|
||||
if (typeof options === 'number') {
|
||||
options = { reason: null, days: options };
|
||||
} else if (typeof options === 'string') {
|
||||
options = { reason: options, days: 0 };
|
||||
}
|
||||
return this.client.rest.methods.banGuildMember(this, user, options);
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
196
src/structures/GuildAuditLogs.js
Normal file
196
src/structures/GuildAuditLogs.js
Normal file
@@ -0,0 +1,196 @@
|
||||
const Targets = {
|
||||
GUILD: 'GUILD',
|
||||
CHANNEL: 'CHANNEL',
|
||||
USER: 'USER',
|
||||
ROLE: 'ROLE',
|
||||
INVITE: 'INVITE',
|
||||
WEBHOOK: 'WEBHOOK',
|
||||
EMOJI: 'EMOJI',
|
||||
};
|
||||
|
||||
const Actions = {
|
||||
GUILD_UPDATE: 1,
|
||||
CHANNEL_CREATE: 10,
|
||||
CHANNEL_UPDATE: 11,
|
||||
CHANNEL_DELETE: 12,
|
||||
CHANNEL_OVERWRITE_CREATE: 13,
|
||||
CHANNEL_OVERWRITE_UPDATE: 14,
|
||||
CHANNEL_OVERWRITE_DELETE: 15,
|
||||
MEMBER_KICK: 20,
|
||||
MEMBER_PRUNE: 21,
|
||||
MEMBER_BAN_ADD: 22,
|
||||
MEMBER_BAN_REMOVE: 23,
|
||||
MEMBER_UPDATE: 24,
|
||||
MEMBER_ROLE_UPDATE: 25,
|
||||
ROLE_CREATE: 30,
|
||||
ROLE_UPDATE: 31,
|
||||
ROLE_DELETE: 32,
|
||||
INVITE_CREATE: 40,
|
||||
INVITE_UPDATE: 41,
|
||||
INVITE_DELETE: 42,
|
||||
WEBHOOK_CREATE: 50,
|
||||
WEBHOOK_UPDATE: 51,
|
||||
WEBHOOK_DELETE: 52,
|
||||
EMOJI_CREATE: 60,
|
||||
EMOJI_UPDATE: 61,
|
||||
EMOJI_DELETE: 62,
|
||||
};
|
||||
|
||||
class GuildAuditLogs {
|
||||
constructor(guild, data) {
|
||||
if (data.users) for (const user of data.users) guild.client.dataManager.newUser(user);
|
||||
|
||||
/**
|
||||
* Entries for this Guild's audit logs
|
||||
* @type {GuildAuditLogsEntry[]}
|
||||
*/
|
||||
this.entries = [];
|
||||
for (const entry of data.audit_log_entries) this.entries.push(new GuildAuditLogsEntry(guild, entry));
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles possible promises for entry targets
|
||||
* @returns {GuildAuditLogs}
|
||||
*/
|
||||
static build(...args) {
|
||||
return new Promise(resolve => {
|
||||
const logs = new GuildAuditLogs(...args);
|
||||
Promise.all(logs.entries.map(e => e.target)).then(() => resolve(logs));
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* Find target type from entry action
|
||||
* @param {number} target Action target
|
||||
* @returns {?string}
|
||||
*/
|
||||
static targetType(target) {
|
||||
if (target < 10) return Targets.GUILD;
|
||||
if (target < 20) return Targets.CHANNEL;
|
||||
if (target < 30) return Targets.USER;
|
||||
if (target < 40) return Targets.ROLE;
|
||||
if (target < 50) return Targets.INVITE;
|
||||
if (target < 60) return Targets.WEBHOOK;
|
||||
if (target < 70) return Targets.EMOJI;
|
||||
return null;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Find action type from entry action
|
||||
* @param {string} action Action target
|
||||
* @returns {string}
|
||||
*/
|
||||
static actionType(action) {
|
||||
if ([
|
||||
Actions.CHANNEL_CREATE,
|
||||
Actions.CHANNEL_OVERWRITE_CREATE,
|
||||
Actions.MEMBER_BAN_REMOVE,
|
||||
Actions.ROLE_CREATE,
|
||||
Actions.INVITE_CREATE,
|
||||
Actions.WEBHOOK_CREATE,
|
||||
Actions.EMOJI_CREATE,
|
||||
].includes(action)) return 'CREATE';
|
||||
|
||||
if ([
|
||||
Actions.CHANNEL_DELETE,
|
||||
Actions.CHANNEL_OVERWRITE_DELETE,
|
||||
Actions.MEMBER_KICK,
|
||||
Actions.MEMBER_PRUNE,
|
||||
Actions.MEMBER_BAN_ADD,
|
||||
Actions.ROLE_DELETE,
|
||||
Actions.INVITE_DELETE,
|
||||
Actions.WEBHOOK_DELETE,
|
||||
Actions.EMOJI_DELETE,
|
||||
].includes(action)) return 'DELETE';
|
||||
|
||||
if ([
|
||||
Actions.GUILD_UPDATE,
|
||||
Actions.CHANNEL_UPDATE,
|
||||
Actions.CHANNEL_OVERWRITE_UPDATE,
|
||||
Actions.MEMBER_UPDATE,
|
||||
Actions.ROLE_UPDATE,
|
||||
Actions.INVITE_UPDATE,
|
||||
Actions.WEBHOOK_UPDATE,
|
||||
Actions.EMOJI_UPDATE,
|
||||
].includes(action)) return 'UPDATE';
|
||||
|
||||
return 'ALL';
|
||||
}
|
||||
}
|
||||
|
||||
class GuildAuditLogsEntry {
|
||||
constructor(guild, data) {
|
||||
const targetType = GuildAuditLogs.targetType(data.action_type);
|
||||
/**
|
||||
* Target type of this entry
|
||||
* @type {string}
|
||||
*/
|
||||
this.targetType = targetType;
|
||||
|
||||
/**
|
||||
* Action type of this entry
|
||||
* @type {string}
|
||||
*/
|
||||
this.actionType = GuildAuditLogs.actionType(data.action_type);
|
||||
|
||||
/**
|
||||
* Specific action type of this entry
|
||||
* @type {string}
|
||||
*/
|
||||
this.action = Object.keys(Actions).find(k => Actions[k] === data.action_type);
|
||||
|
||||
/**
|
||||
* Reason of this entry
|
||||
* @type {?string}
|
||||
*/
|
||||
this.reason = data.reason || null;
|
||||
|
||||
/**
|
||||
* User that executed this entry
|
||||
* @type {User}
|
||||
*/
|
||||
this.executor = guild.client.users.get(data.user_id);
|
||||
|
||||
/**
|
||||
* Specific property changes
|
||||
* @type {Object[]}
|
||||
*/
|
||||
this.changes = data.changes ? data.changes.map(c => ({ name: c.key, old: c.old_value, new: c.new_value })) : null;
|
||||
|
||||
/**
|
||||
* ID of this entry
|
||||
* @type {Snowflake}
|
||||
*/
|
||||
this.id = data.id;
|
||||
|
||||
if (['USER', 'GUILD'].includes(targetType)) {
|
||||
/**
|
||||
* Target of this entry
|
||||
* @type {?Guild|User|Role|Emoji|Promise<Invite>|Promise<Webhook>}
|
||||
*/
|
||||
this.target = guild.client[`${targetType.toLowerCase()}s`].get(data.target_id);
|
||||
} else if (targetType === 'WEBHOOK') {
|
||||
this.target = guild.fetchWebhooks()
|
||||
.then(hooks => {
|
||||
this.target = hooks.find(h => h.id === data.target_id);
|
||||
return this.target;
|
||||
});
|
||||
} else if (targetType === 'INVITE') {
|
||||
const change = this.changes.find(c => c.name === 'code');
|
||||
this.target = guild.fetchInvites()
|
||||
.then(invites => {
|
||||
this.target = invites.find(i => i.code === (change.new || change.old));
|
||||
return this.target;
|
||||
});
|
||||
} else {
|
||||
this.target = guild[`${targetType.toLowerCase()}s`].get(data.target_id);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
GuildAuditLogs.Actions = Actions;
|
||||
GuildAuditLogs.Targets = Targets;
|
||||
GuildAuditLogs.Entry = GuildAuditLogsEntry;
|
||||
|
||||
module.exports = GuildAuditLogs;
|
||||
@@ -473,23 +473,25 @@ class GuildMember {
|
||||
|
||||
/**
|
||||
* Kick this member from the guild
|
||||
* @param {string} [reason] Reason for kicking user
|
||||
* @returns {Promise<GuildMember>}
|
||||
*/
|
||||
kick() {
|
||||
return this.client.rest.methods.kickGuildMember(this.guild, this);
|
||||
kick(reason) {
|
||||
return this.client.rest.methods.kickGuildMember(this.guild, this, reason);
|
||||
}
|
||||
|
||||
/**
|
||||
* Ban this guild member
|
||||
* @param {number} [deleteDays=0] The amount of days worth of messages from this member that should
|
||||
* also be deleted. Between `0` and `7`.
|
||||
* @param {Object} [options] Ban options.
|
||||
* @param {number} [options.days=0] Number of days of messages to delete
|
||||
* @param {string} [options.reason] Reason for banning
|
||||
* @returns {Promise<GuildMember>}
|
||||
* @example
|
||||
* // ban a guild member
|
||||
* guildMember.ban(7);
|
||||
*/
|
||||
ban(deleteDays = 0) {
|
||||
return this.client.rest.methods.banGuildMember(this.guild, this, deleteDays);
|
||||
ban(options) {
|
||||
return this.guild.ban(this, options);
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
@@ -132,6 +132,7 @@ const Endpoints = exports.Endpoints = {
|
||||
webhooks: `${base}/webhooks`,
|
||||
ack: `${base}/ack`,
|
||||
settings: `${base}/settings`,
|
||||
auditLogs: `${base}/audit-logs`,
|
||||
Emoji: emojiID => Endpoints.CDN(root).Emoji(emojiID),
|
||||
Icon: (root, hash) => Endpoints.CDN(root).Icon(guildID, hash),
|
||||
Splash: (root, hash) => Endpoints.CDN(root).Splash(guildID, hash),
|
||||
|
||||
@@ -212,6 +212,7 @@ Permissions.FLAGS = {
|
||||
MANAGE_CHANNELS: 1 << 4,
|
||||
MANAGE_GUILD: 1 << 5,
|
||||
ADD_REACTIONS: 1 << 6,
|
||||
VIEW_AUDIT_LOG: 1 << 7,
|
||||
|
||||
READ_MESSAGES: 1 << 10,
|
||||
SEND_MESSAGES: 1 << 11,
|
||||
|
||||
Reference in New Issue
Block a user