From fc2a8bb6750919ecd6ee7c872df05f4b677ff5d3 Mon Sep 17 00:00:00 2001 From: Jiralite <33201955+Jiralite@users.noreply.github.com> Date: Thu, 14 Apr 2022 11:46:51 +0100 Subject: [PATCH] feat(GuildBanManager): Support pagination results (#7734) --- .../src/managers/GuildBanManager.js | 36 +++++++++++-------- packages/discord.js/typings/index.d.ts | 5 ++- packages/discord.js/typings/index.test-d.ts | 16 +++++++++ 3 files changed, 42 insertions(+), 15 deletions(-) diff --git a/packages/discord.js/src/managers/GuildBanManager.js b/packages/discord.js/src/managers/GuildBanManager.js index 6ad9d2ab5579..bedcf2e832cd 100644 --- a/packages/discord.js/src/managers/GuildBanManager.js +++ b/packages/discord.js/src/managers/GuildBanManager.js @@ -1,6 +1,7 @@ 'use strict'; const { Collection } = require('@discordjs/collection'); +const { makeURLSearchParams } = require('@discordjs/rest'); const { Routes } = require('discord-api-types/v10'); const CachedManager = require('./CachedManager'); const { TypeError, Error } = require('../errors'); @@ -55,9 +56,12 @@ class GuildBanManager extends CachedManager { */ /** - * Options used to fetch all bans from a guild. + * Options used to fetch multiple bans from a guild. * @typedef {Object} FetchBansOptions - * @property {boolean} cache Whether or not to cache the fetched bans + * @property {number} [limit] The maximum number of bans to return + * @property {Snowflake} [before] Consider only bans before this id + * @property {Snowflake} [after] Consider only bans after this id + * @property {boolean} [cache] Whether to cache the fetched bans */ /** @@ -65,13 +69,13 @@ class GuildBanManager extends CachedManager { * @param {UserResolvable|FetchBanOptions|FetchBansOptions} [options] Options for fetching guild ban(s) * @returns {Promise>} * @example - * // Fetch all bans from a guild + * // Fetch multiple bans from a guild * guild.bans.fetch() * .then(console.log) * .catch(console.error); * @example - * // Fetch all bans from a guild without caching - * guild.bans.fetch({ cache: false }) + * // Fetch a maximum of 5 bans from a guild without caching + * guild.bans.fetch({ limit: 5, cache: false }) * .then(console.log) * .catch(console.error); * @example @@ -92,14 +96,15 @@ class GuildBanManager extends CachedManager { */ fetch(options) { if (!options) return this._fetchMany(); - const user = this.client.users.resolveId(options); - if (user) return this._fetchSingle({ user, cache: true }); - options.user &&= this.client.users.resolveId(options.user); - if (!options.user) { - if ('cache' in options) return this._fetchMany(options.cache); + const { user, cache, force, limit, before, after } = options; + const resolvedUser = this.client.users.resolveId(user ?? options); + if (resolvedUser) return this._fetchSingle({ user: resolvedUser, cache, force }); + + if (!before && !after && !limit && typeof cache === 'undefined') { return Promise.reject(new Error('FETCH_BAN_RESOLVE_ID')); } - return this._fetchSingle(options); + + return this._fetchMany(options); } async _fetchSingle({ user, cache, force = false }) { @@ -112,9 +117,12 @@ class GuildBanManager extends CachedManager { return this._add(data, cache); } - async _fetchMany(cache) { - const data = await this.client.rest.get(Routes.guildBans(this.guild.id)); - return data.reduce((col, ban) => col.set(ban.user.id, this._add(ban, cache)), new Collection()); + async _fetchMany(options = {}) { + const data = await this.client.rest.get(Routes.guildBans(this.guild.id), { + query: makeURLSearchParams(options), + }); + + return data.reduce((col, ban) => col.set(ban.user.id, this._add(ban, options.cache)), new Collection()); } /** diff --git a/packages/discord.js/typings/index.d.ts b/packages/discord.js/typings/index.d.ts index 4622bbe9a6d9..ce9c97ba41b8 100644 --- a/packages/discord.js/typings/index.d.ts +++ b/packages/discord.js/typings/index.d.ts @@ -4262,7 +4262,10 @@ export interface FetchBanOptions extends BaseFetchOptions { } export interface FetchBansOptions { - cache: boolean; + limit?: number; + before?: Snowflake; + after?: Snowflake; + cache?: boolean; } export interface FetchChannelOptions extends BaseFetchOptions { diff --git a/packages/discord.js/typings/index.test-d.ts b/packages/discord.js/typings/index.test-d.ts index ad8eb79e19e9..f90434eab29d 100644 --- a/packages/discord.js/typings/index.test-d.ts +++ b/packages/discord.js/typings/index.test-d.ts @@ -117,6 +117,8 @@ import { TextInputComponent, Embed, MessageActionRowComponentBuilder, + GuildBanManager, + GuildBan, } from '.'; import { expectAssignable, expectDeprecated, expectNotAssignable, expectNotType, expectType } from 'tsd'; import { UnsafeButtonBuilder, UnsafeEmbedBuilder, UnsafeSelectMenuBuilder } from '@discordjs/builders'; @@ -1027,6 +1029,20 @@ expectType>>(guildEmojiManager.fetch() expectType>>(guildEmojiManager.fetch(undefined, {})); expectType>(guildEmojiManager.fetch('0')); +declare const guildBanManager: GuildBanManager; +{ + expectType>(guildBanManager.fetch('1234567890')); + expectType>(guildBanManager.fetch({ user: '1234567890' })); + expectType>(guildBanManager.fetch({ user: '1234567890', cache: true, force: false })); + expectType>>(guildBanManager.fetch()); + expectType>>(guildBanManager.fetch({})); + expectType>>(guildBanManager.fetch({ limit: 100, before: '1234567890' })); + // @ts-expect-error + guildBanManager.fetch({ cache: true, force: false }); + // @ts-expect-error + guildBanManager.fetch({ user: '1234567890', after: '1234567890', cache: true, force: false }); +} + declare const typing: Typing; expectType(typing.user); if (typing.user.partial) expectType(typing.user.username);