mirror of
https://github.com/discordeno/discordeno.git
synced 2026-09-17 08:47:22 +00:00
refactor(bot, gateway, rest)!: Improve the interface of the createBot() function. (#3422)
* misc: Make the token a required property on the rest manager. * refactor: Make unnecessarily required properties optional. * misc: Improve interface for `createBot()` and allow passing in `transformers`/`handlers`. * fix: Test made redundant by changes still being included. * fix: Missing non-null assertions. * fix: Benchmarks failing. * misc: Remove `cache.requestMembers.pending` as an exposed option. * style: Switch back to interface approach.
This commit is contained in:
@@ -1,7 +1,7 @@
|
||||
import { createRestManager } from '@discordeno/rest'
|
||||
import { suite } from '../benchmarkSuite.js'
|
||||
|
||||
const rest = createRestManager({ applicationId: 1n })
|
||||
const rest = createRestManager({ token: '1', applicationId: 1n })
|
||||
|
||||
suite.add(`rest.simplifyUrl`, () => {
|
||||
rest.simplifyUrl('/messages/555555555555555555', 'PUT')
|
||||
|
||||
+14
-7
@@ -27,6 +27,7 @@ import type { Sticker } from './transformers/sticker.js'
|
||||
import type { ThreadMember } from './transformers/threadMember.js'
|
||||
import type { User } from './transformers/user.js'
|
||||
import type { VoiceState } from './transformers/voiceState.js'
|
||||
import type { BotGatewayHandlerOptions } from './typings.js'
|
||||
|
||||
/**
|
||||
* Create a bot object that will maintain the rest and gateway connection.
|
||||
@@ -36,7 +37,10 @@ import type { VoiceState } from './transformers/voiceState.js'
|
||||
*/
|
||||
export function createBot(options: CreateBotOptions): Bot {
|
||||
if (!options.rest) options.rest = { token: options.token, applicationId: options.applicationId }
|
||||
if (!options.gateway) options.gateway = { token: options.token, events: {} }
|
||||
if (!options.rest.token) options.rest.token = options.token
|
||||
if (!options.gateway) options.gateway = { token: options.token }
|
||||
if (!options.gateway.token) options.gateway.token = options.token
|
||||
if (!options.gateway.events) options.gateway.events = {}
|
||||
if (!options.gateway.events.message) {
|
||||
options.gateway.events.message = async (shard, data) => {
|
||||
// TRIGGER RAW EVENT
|
||||
@@ -50,7 +54,6 @@ export function createBot(options: CreateBotOptions): Bot {
|
||||
}
|
||||
}
|
||||
|
||||
options.rest.token = options.token
|
||||
options.gateway.intents = options.intents
|
||||
options.gateway.preferSnakeCase = true
|
||||
|
||||
@@ -59,8 +62,8 @@ export function createBot(options: CreateBotOptions): Bot {
|
||||
const bot: Bot = {
|
||||
id,
|
||||
applicationId: id,
|
||||
transformers: createTransformers({}, { defaultDesiredPropertiesValue: options.defaultDesiredPropertiesValue ?? false }),
|
||||
handlers: createBotGatewayHandlers({}),
|
||||
transformers: createTransformers(options.transformers ?? {}, { defaultDesiredPropertiesValue: options.defaultDesiredPropertiesValue ?? false }),
|
||||
handlers: createBotGatewayHandlers(options.handlers ?? {}),
|
||||
rest: createRestManager(options.rest),
|
||||
gateway: createGatewayManager(options.gateway),
|
||||
events: options.events ?? {},
|
||||
@@ -101,11 +104,15 @@ export interface CreateBotOptions {
|
||||
/** The bot's intents that will be used to make a connection with discords gateway. */
|
||||
intents?: GatewayIntents
|
||||
/** Any options you wish to provide to the rest manager. */
|
||||
rest?: CreateRestManagerOptions
|
||||
rest?: CreateRestManagerOptions & Partial<Pick<CreateRestManagerOptions, 'token'>>
|
||||
/** Any options you wish to provide to the gateway manager. */
|
||||
gateway?: CreateGatewayManagerOptions
|
||||
gateway?: CreateGatewayManagerOptions & Partial<Pick<CreateGatewayManagerOptions, 'token'>>
|
||||
/** The event handlers. */
|
||||
events: Partial<EventHandlers>
|
||||
events?: Partial<EventHandlers>
|
||||
/** The functions that should transform discord objects to discordeno shaped objects. */
|
||||
transformers?: Partial<Transformers>
|
||||
/** The handler functions that should handle incoming discord payloads from gateway and call an event. */
|
||||
handlers?: Partial<BotGatewayHandlerOptions>
|
||||
/**
|
||||
* @deprecated Use with caution
|
||||
*
|
||||
|
||||
@@ -6,7 +6,7 @@ export async function handleGuildMembersChunk(bot: Bot, data: DiscordGatewayPayl
|
||||
const payload = data.d as DiscordGuildMembersChunk
|
||||
|
||||
// If it's not enabled skip checks.
|
||||
if (!bot.gateway.cache.requestMembers?.enabled) return
|
||||
if (!bot.gateway.cache.requestMembers.enabled) return
|
||||
|
||||
// If this request has no nonce, skip checks.
|
||||
if (!payload.nonce) return
|
||||
|
||||
@@ -26,7 +26,7 @@ export function createGatewayManager(options: CreateGatewayManagerOptions): Gate
|
||||
}
|
||||
|
||||
const gateway: GatewayManager = {
|
||||
events: options.events,
|
||||
events: options.events ?? {},
|
||||
compress: options.compress ?? false,
|
||||
intents: options.intents ?? 0,
|
||||
properties: {
|
||||
@@ -172,7 +172,7 @@ export function createGatewayManager(options: CreateGatewayManagerOptions): Gate
|
||||
url: this.url,
|
||||
version: this.version,
|
||||
},
|
||||
events: options.events,
|
||||
events: options.events ?? {},
|
||||
requestIdentify: async () => {
|
||||
await gateway.identify(shardId)
|
||||
},
|
||||
@@ -186,7 +186,7 @@ export function createGatewayManager(options: CreateGatewayManagerOptions): Gate
|
||||
|
||||
if (this.preferSnakeCase) {
|
||||
shard.forwardToBot = async (payload) => {
|
||||
options.events.message?.(shard!, payload)
|
||||
shard!.events.message?.(shard!, payload)
|
||||
}
|
||||
}
|
||||
|
||||
@@ -294,11 +294,11 @@ export function createGatewayManager(options: CreateGatewayManagerOptions): Gate
|
||||
}
|
||||
|
||||
const members =
|
||||
!gateway.cache.requestMembers?.enabled || !options?.nonce
|
||||
!gateway.cache.requestMembers.enabled || !options?.nonce
|
||||
? []
|
||||
: new Promise<Camelize<DiscordMemberWithUser[]>>((resolve, reject) => {
|
||||
// Should never happen.
|
||||
if (!gateway.cache.requestMembers?.enabled || !options?.nonce) {
|
||||
if (!gateway.cache.requestMembers.enabled || !options?.nonce) {
|
||||
reject(new Error("Can't request the members without the nonce or with the feature disabled."))
|
||||
return
|
||||
}
|
||||
@@ -425,7 +425,7 @@ export interface CreateGatewayManagerOptions {
|
||||
*/
|
||||
version?: number
|
||||
/** The events handlers */
|
||||
events: ShardEvents
|
||||
events?: ShardEvents
|
||||
/** This managers cache related settings. */
|
||||
cache?: {
|
||||
requestMembers?: {
|
||||
@@ -434,8 +434,6 @@ export interface CreateGatewayManagerOptions {
|
||||
* @default false
|
||||
*/
|
||||
enabled?: boolean
|
||||
/** The pending requests. */
|
||||
pending: Collection<string, RequestMemberRequest>
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -541,6 +539,18 @@ export interface GatewayManager extends Required<CreateGatewayManagerOptions> {
|
||||
* @see {@link https://discord.com/developers/docs/topics/gateway#update-voice-state}
|
||||
*/
|
||||
leaveVoiceChannel: (guildId: BigString) => Promise<void>
|
||||
/** This managers cache related settings. */
|
||||
cache: {
|
||||
requestMembers: {
|
||||
/**
|
||||
* Whether or not request member requests should be cached.
|
||||
* @default false
|
||||
*/
|
||||
enabled: boolean
|
||||
/** The pending requests. */
|
||||
pending: Collection<string, RequestMemberRequest>
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
export interface RequestMemberRequest {
|
||||
|
||||
@@ -76,12 +76,7 @@ export const RATE_LIMIT_LIMIT_HEADER = 'x-ratelimit-limit'
|
||||
export const RATE_LIMIT_SCOPE_HEADER = 'x-ratelimit-scope'
|
||||
|
||||
export function createRestManager(options: CreateRestManagerOptions): RestManager {
|
||||
const applicationId = options.applicationId ? BigInt(options.applicationId) : options.token ? getBotIdFromToken(options.token) : undefined
|
||||
if (!applicationId) {
|
||||
throw new Error(
|
||||
'`applicationId` was not provided and was not able to extract the id from the bots token. Please explicitly pass `applicationId` to the rest manager.',
|
||||
)
|
||||
}
|
||||
const applicationId = options.applicationId ? BigInt(options.applicationId) : getBotIdFromToken(options.token)
|
||||
|
||||
const baseUrl = options.proxy?.baseUrl ?? DISCORD_API_URL
|
||||
|
||||
|
||||
@@ -134,7 +134,7 @@ import type { RestRoutes } from './typings/routes.js'
|
||||
|
||||
export interface CreateRestManagerOptions {
|
||||
/** The bot token which will be used to make requests. */
|
||||
token?: string
|
||||
token: string
|
||||
/**
|
||||
* For old bots that have a different bot id and application id.
|
||||
* @default bot id from token
|
||||
@@ -170,7 +170,7 @@ export interface CreateRestManagerOptions {
|
||||
|
||||
export interface RestManager {
|
||||
/** The bot token which will be used to make requests. */
|
||||
token?: string
|
||||
token: string
|
||||
/** The application id. Normally this is not required for recent bots but old bot's application id is sometimes different from the bot id so it is required for those bots. */
|
||||
applicationId: bigint
|
||||
/** The api version to use when making requests. Only the latest supported version will be tested. */
|
||||
|
||||
@@ -38,10 +38,6 @@ describe('[rest] manager', () => {
|
||||
expect(rest.baseUrl).to.be.equal(options.proxy.baseUrl)
|
||||
})
|
||||
|
||||
it('With a falsy token', () => {
|
||||
expect(() => createRestManager({ token: '' })).throws()
|
||||
})
|
||||
|
||||
it('With an application id', () => {
|
||||
const subrest = createRestManager({ ...options, applicationId: '130136895395987456' })
|
||||
expect(subrest.applicationId).to.be.equal(130136895395987456n)
|
||||
@@ -173,7 +169,7 @@ describe('[rest] manager', () => {
|
||||
let time: sinon.SinonFakeTimers
|
||||
|
||||
beforeEach(() => {
|
||||
rest = createRestManager({ applicationId: 1n })
|
||||
rest = createRestManager({ token: '1', applicationId: 1n })
|
||||
time = sinon.useFakeTimers()
|
||||
})
|
||||
|
||||
|
||||
Reference in New Issue
Block a user