distube 4.1.1 → 4.2.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.d.ts CHANGED
@@ -6,147 +6,192 @@ import ytpl from '@distube/ytpl';
6
6
  import { Video, Playlist as Playlist$1 } from '@distube/ytsr';
7
7
  import { TypedEmitter } from 'tiny-typed-emitter';
8
8
  import { AudioPlayer, VoiceConnection, AudioResource, StreamType as StreamType$1 } from '@discordjs/voice';
9
- import { FFmpeg } from 'prism-media';
10
- import * as _discordjs_collection from '@discordjs/collection';
9
+ import { PassThrough } from 'node:stream';
10
+ import { ChildProcess } from 'child_process';
11
11
 
12
12
  type Awaitable<T = any> = T | PromiseLike<T>;
13
- type DisTubeVoiceEvents = {
14
- disconnect: (error?: Error) => Awaitable;
15
- error: (error: Error) => Awaitable;
16
- finish: () => Awaitable;
17
- };
18
13
  type DisTubeEvents = {
19
- error: [channel: GuildTextBasedChannel | undefined, error: Error];
20
14
  addList: [queue: Queue, playlist: Playlist];
21
15
  addSong: [queue: Queue, song: Song];
22
- playSong: [queue: Queue, song: Song];
23
- finishSong: [queue: Queue, song: Song];
16
+ deleteQueue: [queue: Queue];
17
+ disconnect: [queue: Queue];
24
18
  empty: [queue: Queue];
19
+ error: [channel: GuildTextBasedChannel | undefined, error: Error];
20
+ ffmpegDebug: [debug: string];
25
21
  finish: [queue: Queue];
22
+ finishSong: [queue: Queue, song: Song];
26
23
  initQueue: [queue: Queue];
27
24
  noRelated: [queue: Queue];
28
- disconnect: [queue: Queue];
29
- deleteQueue: [queue: Queue];
25
+ playSong: [queue: Queue, song: Song];
30
26
  searchCancel: [message: Message<true>, query: string];
31
- searchNoResult: [message: Message<true>, query: string];
32
27
  searchDone: [message: Message<true>, answer: Message<true>, query: string];
33
28
  searchInvalidAnswer: [message: Message<true>, answer: Message<true>, query: string];
29
+ searchNoResult: [message: Message<true>, query: string];
34
30
  searchResult: [message: Message<true>, results: SearchResult[], query: string];
35
31
  };
36
32
  type TypedDisTubeEvents = {
37
33
  [K in keyof DisTubeEvents]: (...args: DisTubeEvents[K]) => Awaitable;
38
34
  };
35
+ type DisTubeVoiceEvents = {
36
+ disconnect: (error?: Error) => Awaitable;
37
+ error: (error: Error) => Awaitable;
38
+ finish: () => Awaitable;
39
+ };
39
40
  /**
40
41
  * An FFmpeg audio filter object
41
- * ```
42
+ *
43
+ * ```ts
42
44
  * {
43
45
  * name: "bassboost",
44
46
  * value: "bass=g=10"
45
47
  * }
46
- * ```
47
- * @typedef {Object} Filter
48
- * @prop {string} name Name of the filter
49
- * @prop {string} value FFmpeg audio filter(s)
48
+ * ```ts
50
49
  */
51
50
  interface Filter {
51
+ /**
52
+ * Name of the filter
53
+ */
52
54
  name: string;
55
+ /**
56
+ * FFmpeg audio filter argument
57
+ */
53
58
  value: string;
54
59
  }
55
60
  /**
56
61
  * Data that resolves to give an FFmpeg audio filter. This can be:
62
+ *
57
63
  * - A name of a default filters or custom filters (`string`)
58
64
  * - A {@link Filter} object
59
- * @typedef {string|Filter} FilterResolvable
65
+ *
60
66
  * @see {@link defaultFilters}
61
67
  * @see {@link DisTubeOptions|DisTubeOptions.customFilters}
62
68
  */
63
69
  type FilterResolvable = string | Filter;
64
70
  /**
65
71
  * FFmpeg Filters
66
- * ```
72
+ *
73
+ * ```ts
67
74
  * {
68
75
  * "Filter Name": "Filter Value",
69
76
  * "bassboost": "bass=g=10"
70
77
  * }
71
- * ```
72
- * @typedef {Object.<string, string>} Filters
78
+ * ```ts
79
+ *
73
80
  * @see {@link defaultFilters}
74
81
  */
75
82
  type Filters = Record<string, string>;
76
83
  /**
77
- * DisTube options.
78
- * @typedef {Object} DisTubeOptions
79
- * @prop {Array<CustomPlugin|ExtractorPlugin>} [plugins] DisTube plugins.
80
- * @prop {boolean} [emitNewSongOnly=false] Whether or not emitting {@link DisTube#event:playSong} event
81
- * when looping a song or next song is the same as the previous one
82
- * @prop {boolean} [leaveOnEmpty=true] Whether or not leaving voice channel
83
- * if the voice channel is empty after {@link DisTubeOptions}.emptyCooldown seconds.
84
- * @prop {boolean} [leaveOnFinish=false] Whether or not leaving voice channel when the queue ends.
85
- * @prop {boolean} [leaveOnStop=true] Whether or not leaving voice channel after using {@link DisTube#stop} function.
86
- * @prop {boolean} [savePreviousSongs=true] Whether or not saving the previous songs of the queue
87
- * and enable {@link DisTube#previous} method
88
- * @prop {number} [searchSongs=0] Limit of search results emits in {@link DisTube#event:searchResult} event
89
- * when {@link DisTube#play} method executed. If `searchSongs <= 1`, play the first result
90
- * @prop {Cookie[]|string} [youtubeCookie] YouTube cookies. Guide: {@link https://distube.js.org/#/docs/DisTube/main/general/cookie YouTube Cookies}
91
- * @prop {Filters} [customFilters] Override {@link defaultFilters} or add more ffmpeg filters.
92
- * @prop {ytdl.getInfoOptions} [ytdlOptions] `ytdl-core` get info options
93
- * @prop {number} [searchCooldown=60] Built-in search cooldown in seconds (When searchSongs is bigger than 0)
94
- * @prop {number} [emptyCooldown=60] Built-in leave on empty cooldown in seconds (When leaveOnEmpty is true)
95
- * @prop {boolean} [nsfw=false] Whether or not playing age-restricted content
96
- * and disabling safe search in non-NSFW channel.
97
- * @prop {boolean} [emitAddListWhenCreatingQueue=true] Whether or not emitting `addList` event when creating a new Queue
98
- * @prop {boolean} [emitAddSongWhenCreatingQueue=true] Whether or not emitting `addSong` event when creating a new Queue
99
- * @prop {boolean} [joinNewVoiceChannel=true] Whether or not joining the new voice channel
100
- * when using {@link DisTube#play} method
101
- * @prop {StreamType} [streamType=StreamType.OPUS] Decide the {@link DisTubeStream#type} will be used
102
- * (Not the same as {@link DisTubeStream#type})
103
- * @prop {boolean} [directLink=true] Whether or not playing a song with direct link
84
+ * DisTube options
104
85
  */
105
86
  type DisTubeOptions = {
87
+ /**
88
+ * DisTube plugins
89
+ */
106
90
  plugins?: (CustomPlugin | ExtractorPlugin)[];
91
+ /**
92
+ * Whether or not emitting {@link DisTube#playSong} event when looping a song
93
+ * or next song is the same as the previous one
94
+ */
107
95
  emitNewSongOnly?: boolean;
96
+ /**
97
+ * Whether or not leaving voice channel if the voice channel is empty after {@link
98
+ * DisTubeOptions}.emptyCooldown seconds
99
+ */
100
+ leaveOnEmpty?: boolean;
101
+ /**
102
+ * Whether or not leaving voice channel when the queue ends
103
+ */
108
104
  leaveOnFinish?: boolean;
105
+ /**
106
+ * Whether or not leaving voice channel after using {@link DisTube#stop} function
107
+ */
109
108
  leaveOnStop?: boolean;
110
- leaveOnEmpty?: boolean;
109
+ /**
110
+ * Built-in leave on empty cooldown in seconds (When leaveOnEmpty is true)
111
+ */
111
112
  emptyCooldown?: number;
113
+ /**
114
+ * Whether or not saving the previous songs of the queue and enable {@link
115
+ * DisTube#previous} method
116
+ */
112
117
  savePreviousSongs?: boolean;
118
+ /**
119
+ * Limit of search results emits in {@link DisTube#searchResult} event when
120
+ * {@link DisTube#play} method executed. If `searchSongs <= 1`, play the first
121
+ * result
122
+ */
113
123
  searchSongs?: number;
124
+ /**
125
+ * Built-in search cooldown in seconds (When searchSongs is bigger than 0)
126
+ */
114
127
  searchCooldown?: number;
128
+ /**
129
+ * YouTube cookies. Guide: {@link
130
+ * https://distube.js.org/#/docs/DisTube/main/general/cookie | YouTube Cookies}
131
+ */
115
132
  youtubeCookie?: Cookie[] | string;
133
+ /**
134
+ * Override {@link defaultFilters} or add more ffmpeg filters
135
+ */
116
136
  customFilters?: Filters;
137
+ /**
138
+ * `ytdl-core` get info options
139
+ */
117
140
  ytdlOptions?: ytdl__default.downloadOptions;
141
+ /**
142
+ * Whether or not playing age-restricted content and disabling safe search in
143
+ * non-NSFW channel
144
+ */
118
145
  nsfw?: boolean;
146
+ /**
147
+ * Whether or not emitting `addSong` event when creating a new Queue
148
+ */
119
149
  emitAddSongWhenCreatingQueue?: boolean;
150
+ /**
151
+ * Whether or not emitting `addList` event when creating a new Queue
152
+ */
120
153
  emitAddListWhenCreatingQueue?: boolean;
154
+ /**
155
+ * Whether or not joining the new voice channel when using {@link DisTube#play}
156
+ * method
157
+ */
121
158
  joinNewVoiceChannel?: boolean;
159
+ /**
160
+ * Decide the {@link DisTubeStream#type} will be used (Not the same as {@link
161
+ * DisTubeStream#type})
162
+ */
122
163
  streamType?: StreamType;
164
+ /**
165
+ * Whether or not playing a song with direct link
166
+ */
123
167
  directLink?: boolean;
168
+ /**
169
+ * FFmpeg path
170
+ */
171
+ ffmpegPath?: string;
172
+ /**
173
+ * FFmpeg default arguments
174
+ */
175
+ ffmpegDefaultArgs?: FFmpegOptions;
124
176
  };
125
177
  /**
126
178
  * Data that can be resolved to give a guild id string. This can be:
179
+ *
127
180
  * - A guild id string | a guild {@link https://discord.js.org/#/docs/main/stable/class/Snowflake|Snowflake}
128
- * - A {@link https://discord.js.org/#/docs/main/stable/class/Guild|Guild}
129
- * - A {@link https://discord.js.org/#/docs/main/stable/class/Message|Message}
130
- * - A {@link https://discord.js.org/#/docs/main/stable/class/BaseGuildVoiceChannel|BaseGuildVoiceChannel}
131
- * - A {@link https://discord.js.org/#/docs/main/stable/class/BaseGuildTextChannel|BaseGuildTextChannel}
132
- * - A {@link https://discord.js.org/#/docs/main/stable/class/VoiceState|VoiceState}
133
- * - A {@link https://discord.js.org/#/docs/main/stable/class/GuildMember|GuildMember}
134
- * - A {@link https://discord.js.org/#/docs/main/stable/class/Interaction|Interaction}
181
+ * - A {@link https://discord.js.org/#/docs/main/stable/class/Guild | Guild}
182
+ * - A {@link https://discord.js.org/#/docs/main/stable/class/Message | Message}
183
+ * - A {@link https://discord.js.org/#/docs/main/stable/class/BaseGuildVoiceChannel
184
+ * | BaseGuildVoiceChannel}
185
+ * - A {@link https://discord.js.org/#/docs/main/stable/class/BaseGuildTextChannel
186
+ * | BaseGuildTextChannel}
187
+ * - A {@link https://discord.js.org/#/docs/main/stable/class/VoiceState |
188
+ * VoiceState}
189
+ * - A {@link https://discord.js.org/#/docs/main/stable/class/GuildMember |
190
+ * GuildMember}
191
+ * - A {@link https://discord.js.org/#/docs/main/stable/class/Interaction |
192
+ * Interaction}
135
193
  * - A {@link DisTubeVoice}
136
194
  * - A {@link Queue}
137
- * @typedef {
138
- * Discord.Snowflake|
139
- * Discord.Guild|
140
- * Discord.Message|
141
- * Discord.BaseGuildVoiceChannel|
142
- * Discord.BaseGuildTextChannel|
143
- * Discord.VoiceState|
144
- * Discord.GuildMember|
145
- * Discord.Interaction|
146
- * DisTubeVoice|
147
- * Queue|
148
- * string
149
- * } GuildIdResolvable
150
195
  */
151
196
  type GuildIdResolvable = Queue | DisTubeVoice | Snowflake | Message | GuildTextBasedChannel | VoiceBasedChannel | VoiceState | Guild | GuildMember | Interaction | string;
152
197
  interface OtherSongInfo {
@@ -190,76 +235,80 @@ interface PlaylistInfo {
190
235
  name?: string;
191
236
  url?: string;
192
237
  thumbnail?: string;
193
- /** @deprecated */
238
+ /**
239
+ * @deprecated Use {@link PlaylistInfo#name}
240
+ */
194
241
  title?: string;
195
- /** @deprecated */
242
+ /**
243
+ * @deprecated Use {@link PlaylistInfo#url}
244
+ */
196
245
  webpage_url?: string;
197
246
  }
198
247
  type RelatedSong = Omit<Song, "related">;
199
- /**
200
- * @typedef {Object} PlayHandlerOptions
201
- * @prop {Discord.BaseGuildTextChannel} [options.textChannel] The default text channel of the queue
202
- * @prop {boolean} [options.skip=false] Skip the playing song (if exists) and play the added playlist instantly
203
- * @prop {number} [options.position=0] Position of the song/playlist to add to the queue,
204
- * <= 0 to add to the end of the queue.
205
- */
206
248
  type PlayHandlerOptions = {
249
+ /**
250
+ * [Default: false] Skip the playing song (if exists) and play the added playlist
251
+ * instantly
252
+ */
207
253
  skip?: boolean;
254
+ /**
255
+ * [Default: 0] Position of the song/playlist to add to the queue, \<= 0 to add to
256
+ * the end of the queue
257
+ */
208
258
  position?: number;
259
+ /**
260
+ * The default text channel of the queue
261
+ */
209
262
  textChannel?: GuildTextBasedChannel;
210
263
  };
211
- /**
212
- * @typedef {Object} PlayOptions
213
- * @prop {Discord.GuildMember} [member] Requested user (default is your bot)
214
- * @prop {Discord.BaseGuildTextChannel} [textChannel] Default {@link Queue#textChannel}
215
- * @prop {boolean} [skip=false]
216
- * Skip the playing song (if exists) and play the added song/playlist if `position` is 1.
217
- * If `position` is defined and not equal to 1, it will skip to the next song instead of the added song
218
- * @prop {number} [position=0] Position of the song/playlist to add to the queue,
219
- * <= 0 to add to the end of the queue.
220
- * @prop {Discord.Message} [message] Called message (For built-in search events. If this is a {@link https://developer.mozilla.org/en-US/docs/Glossary/Falsy|falsy value}, it will play the first result instead)
221
- * @prop {*} [metadata] Optional metadata that can be attached to the song/playlist will be played,
222
- * This is useful for identification purposes when the song/playlist is passed around in events.
223
- * See {@link Song#metadata} or {@link Playlist#metadata}
224
- */
225
264
  interface PlayOptions extends PlayHandlerOptions, ResolveOptions<any> {
265
+ /**
266
+ * Called message (For built-in search events. If this is a {@link
267
+ * https://developer.mozilla.org/en-US/docs/Glossary/Falsy | falsy value}, it will
268
+ * play the first result instead)
269
+ */
226
270
  message?: Message;
227
271
  }
228
- /**
229
- * @typedef {Object} ResolveOptions
230
- * @prop {Discord.GuildMember} [member] Requested user
231
- * @prop {*} [metadata] Metadata
232
- */
233
272
  interface ResolveOptions<T = unknown> {
273
+ /**
274
+ * Requested user
275
+ */
234
276
  member?: GuildMember;
277
+ /**
278
+ * Metadata
279
+ */
235
280
  metadata?: T;
236
281
  }
237
- /**
238
- * @typedef {ResolveOptions} ResolvePlaylistOptions
239
- * @prop {string} [source] Source of the playlist
240
- */
241
282
  interface ResolvePlaylistOptions<T = unknown> extends ResolveOptions<T> {
283
+ /**
284
+ * Source of the playlist
285
+ */
242
286
  source?: string;
243
287
  }
244
- /**
245
- * @typedef {Object} CustomPlaylistOptions
246
- * @prop {Discord.GuildMember} [member] A guild member creating the playlist
247
- * @prop {Object} [properties] Additional properties such as `name`
248
- * @prop {boolean} [parallel=true] Whether or not fetch the songs in parallel
249
- * @prop {*} [metadata] Metadata
250
- */
251
288
  interface CustomPlaylistOptions {
289
+ /**
290
+ * A guild member creating the playlist
291
+ */
252
292
  member?: GuildMember;
293
+ /**
294
+ * Additional properties such as `name`
295
+ */
253
296
  properties?: Record<string, any>;
297
+ /**
298
+ * Whether or not fetch the songs in parallel
299
+ */
254
300
  parallel?: boolean;
301
+ /**
302
+ * Metadata
303
+ */
255
304
  metadata?: any;
256
305
  }
257
306
  /**
258
307
  * The repeat mode of a {@link Queue}
259
- * * `DISABLED` = 0
260
- * * `SONG` = 1
261
- * * `QUEUE` = 2
262
- * @typedef {number} RepeatMode
308
+ *
309
+ * - `DISABLED` = 0
310
+ * - `SONG` = 1
311
+ * - `QUEUE` = 2
263
312
  */
264
313
  declare enum RepeatMode {
265
314
  DISABLED = 0,
@@ -268,9 +317,9 @@ declare enum RepeatMode {
268
317
  }
269
318
  /**
270
319
  * All available plugin types:
271
- * * `CUSTOM` = `"custom"`: {@link CustomPlugin}
272
- * * `EXTRACTOR` = `"extractor"`: {@link ExtractorPlugin}
273
- * @typedef {"custom"|"extractor"} PluginType
320
+ *
321
+ * - `CUSTOM` = `"custom"`: {@link CustomPlugin}
322
+ * - `EXTRACTOR` = `"extractor"`: {@link ExtractorPlugin}
274
323
  */
275
324
  declare enum PluginType {
276
325
  CUSTOM = "custom",
@@ -278,9 +327,9 @@ declare enum PluginType {
278
327
  }
279
328
  /**
280
329
  * Search result types:
281
- * * `VIDEO` = `"video"`
282
- * * `PLAYLIST` = `"playlist"`
283
- * @typedef {"video"|"playlist"} SearchResultType
330
+ *
331
+ * - `VIDEO` = `"video"`
332
+ * - `PLAYLIST` = `"playlist"`
284
333
  */
285
334
  declare enum SearchResultType {
286
335
  VIDEO = "video",
@@ -288,34 +337,14 @@ declare enum SearchResultType {
288
337
  }
289
338
  /**
290
339
  * Stream types:
291
- * * `OPUS` = `0` (Better quality, use more resources - **Recommended**)
292
- * * `RAW` = `1` (Better performance, use less resources)
293
- * @typedef {number} StreamType
294
- * @type {StreamType}
340
+ *
341
+ * - `OPUS` = `0` (Better quality, use more resources - **Recommended**)
342
+ * - `RAW` = `1` (Better performance, use less resources)
295
343
  */
296
344
  declare enum StreamType {
297
345
  OPUS = 0,
298
346
  RAW = 1
299
347
  }
300
- /**
301
- * @typedef {Object} Events
302
- * @prop {string} ERROR error
303
- * @prop {string} ADD_LIST addList
304
- * @prop {string} ADD_SONG addSong
305
- * @prop {string} PLAY_SONG playSong
306
- * @prop {string} FINISH_SONG finishSong
307
- * @prop {string} EMPTY empty
308
- * @prop {string} FINISH finish
309
- * @prop {string} INIT_QUEUE initQueue
310
- * @prop {string} NO_RELATED noRelated
311
- * @prop {string} DISCONNECT disconnect
312
- * @prop {string} DELETE_QUEUE deleteQueue
313
- * @prop {string} SEARCH_CANCEL searchCancel
314
- * @prop {string} SEARCH_NO_RESULT searchNoResult
315
- * @prop {string} SEARCH_DONE searchDone
316
- * @prop {string} SEARCH_INVALID_ANSWER searchInvalidAnswer
317
- * @prop {string} SEARCH_RESULT searchResult
318
- */
319
348
  declare enum Events {
320
349
  ERROR = "error",
321
350
  ADD_LIST = "addList",
@@ -332,46 +361,37 @@ declare enum Events {
332
361
  SEARCH_NO_RESULT = "searchNoResult",
333
362
  SEARCH_DONE = "searchDone",
334
363
  SEARCH_INVALID_ANSWER = "searchInvalidAnswer",
335
- SEARCH_RESULT = "searchResult"
364
+ SEARCH_RESULT = "searchResult",
365
+ FFMPEG_DEBUG = "ffmpegDebug"
336
366
  }
367
+ type FFmpegOptions = Record<string, string | number | boolean | Array<string | null | undefined> | null | undefined>;
337
368
 
338
369
  /**
339
370
  * Default DisTube audio filters.
340
- * @typedef {Object} defaultFilters
341
- * @prop {string} 3d 3d
342
- * @prop {string} bassboost bassboost
343
- * @prop {string} echo echo
344
- * @prop {string} karaoke karaoke
345
- * @prop {string} nightcore nightcore
346
- * @prop {string} vaporwave vaporwave
347
- * @prop {string} flanger flanger
348
- * @prop {string} gate gate
349
- * @prop {string} haas haas
350
- * @prop {string} reverse reverse
351
- * @prop {string} surround surround
352
- * @prop {string} mcompand mcompand
353
- * @prop {string} phaser phaser
354
- * @prop {string} tremolo tremolo
355
- * @prop {string} earwax earwax
356
371
  */
357
372
  declare const defaultFilters: Filters;
358
373
  declare const defaultOptions: {
359
374
  plugins: never[];
360
- emitNewSongOnly: boolean;
361
- leaveOnEmpty: boolean;
362
- leaveOnFinish: boolean;
363
- leaveOnStop: boolean;
364
- savePreviousSongs: boolean;
375
+ emitNewSongOnly: false;
376
+ leaveOnEmpty: true;
377
+ leaveOnFinish: false;
378
+ leaveOnStop: true;
379
+ savePreviousSongs: true;
365
380
  searchSongs: number;
366
381
  ytdlOptions: {};
367
382
  searchCooldown: number;
368
383
  emptyCooldown: number;
369
- nsfw: boolean;
370
- emitAddSongWhenCreatingQueue: boolean;
371
- emitAddListWhenCreatingQueue: boolean;
372
- joinNewVoiceChannel: boolean;
373
- streamType: StreamType;
374
- directLink: boolean;
384
+ nsfw: false;
385
+ emitAddSongWhenCreatingQueue: true;
386
+ emitAddListWhenCreatingQueue: true;
387
+ joinNewVoiceChannel: true;
388
+ streamType: StreamType.OPUS;
389
+ directLink: true;
390
+ ffmpegPath: string;
391
+ ffmpegDefaultArgs: {
392
+ analyzeduration: number;
393
+ hide_banner: true;
394
+ };
375
395
  };
376
396
 
377
397
  declare const ERROR_MESSAGES: {
@@ -431,14 +451,13 @@ declare class DisTubeError<T extends string> extends Error {
431
451
 
432
452
  /**
433
453
  * Task queuing system
434
- * @private
435
454
  */
436
455
  declare class TaskQueue {
437
456
  #private;
438
457
  /**
439
458
  * Waits for last task finished and queues a new task
440
- * @param {boolean} [resolveInfo=false] Whether the task is a resolving info task
441
- * @returns {Promise<void>}
459
+ *
460
+ * @param resolveInfo - Whether the task is a resolving info task
442
461
  */
443
462
  queuing(resolveInfo?: boolean): Promise<void>;
444
463
  /**
@@ -447,20 +466,16 @@ declare class TaskQueue {
447
466
  resolve(): void;
448
467
  /**
449
468
  * The remaining number of tasks
450
- * @type {number}
451
469
  */
452
470
  get remaining(): number;
453
471
  /**
454
472
  * Whether or not having a resolving info task
455
- * @type {boolean}
456
473
  */
457
474
  get hasResolveTask(): boolean;
458
475
  }
459
476
 
460
477
  /**
461
478
  * Class representing a playlist.
462
- * @prop {string} source Playlist source
463
- * @template T - The type for the metadata (if any) of the playlist
464
479
  */
465
480
  declare class Playlist<T = unknown> implements PlaylistInfo {
466
481
  #private;
@@ -472,11 +487,9 @@ declare class Playlist<T = unknown> implements PlaylistInfo {
472
487
  [x: string]: any;
473
488
  /**
474
489
  * Create a playlist
475
- * @param {Song[]|PlaylistInfo} playlist Playlist
476
- * @param {Object} [options] Optional options
477
- * @param {Discord.GuildMember} [options.member] Requested user
478
- * @param {Object} [options.properties] Custom properties
479
- * @param {T} [options.metadata] Playlist metadata
490
+ *
491
+ * @param playlist - Playlist
492
+ * @param options - Optional options
480
493
  */
481
494
  constructor(playlist: Song[] | PlaylistInfo, options?: {
482
495
  member?: GuildMember;
@@ -485,23 +498,19 @@ declare class Playlist<T = unknown> implements PlaylistInfo {
485
498
  });
486
499
  /**
487
500
  * Playlist duration in second.
488
- * @type {number}
489
501
  */
490
502
  get duration(): number;
491
503
  /**
492
504
  * Formatted duration string `hh:mm:ss`.
493
- * @type {string}
494
505
  */
495
506
  get formattedDuration(): string;
496
507
  /**
497
508
  * User requested.
498
- * @type {Discord.GuildMember?}
499
509
  */
500
510
  get member(): GuildMember | undefined;
501
511
  set member(member: GuildMember | undefined);
502
512
  /**
503
513
  * User requested.
504
- * @type {Discord.User?}
505
514
  */
506
515
  get user(): discord_js.User | undefined;
507
516
  get metadata(): T;
@@ -510,8 +519,8 @@ declare class Playlist<T = unknown> implements PlaylistInfo {
510
519
 
511
520
  /**
512
521
  * A abstract class representing a search result.
513
- * @abstract
514
- * @private
522
+ *
523
+ * @virtual
515
524
  */
516
525
  declare abstract class ISearchResult {
517
526
  source: "youtube";
@@ -525,13 +534,13 @@ declare abstract class ISearchResult {
525
534
  };
526
535
  /**
527
536
  * Create a search result
528
- * @param {Object} info ytsr result
537
+ *
538
+ * @param info - ytsr result
529
539
  */
530
540
  constructor(info: Video | Playlist$1);
531
541
  }
532
542
  /**
533
543
  * A class representing a video search result.
534
- * @extends ISearchResult
535
544
  */
536
545
  declare class SearchResultVideo extends ISearchResult {
537
546
  type: SearchResultType.VIDEO;
@@ -544,12 +553,10 @@ declare class SearchResultVideo extends ISearchResult {
544
553
  }
545
554
  /**
546
555
  * A video or playlist search result
547
- * @typedef {SearchResultVideo|SearchResultPlaylist} SearchResult
548
556
  */
549
557
  type SearchResult = SearchResultVideo | SearchResultPlaylist;
550
558
  /**
551
559
  * A class representing a playlist search result.
552
- * @extends ISearchResult
553
560
  */
554
561
  declare class SearchResultPlaylist extends ISearchResult {
555
562
  type: SearchResultType.PLAYLIST;
@@ -560,12 +567,12 @@ declare class SearchResultPlaylist extends ISearchResult {
560
567
  /**
561
568
  * Class representing a song.
562
569
  *
563
- * <info>If {@link Song} is added from a YouTube {@link SearchResult} or {@link Playlist},
564
- * some info will be missing to save your resources. It will be filled when emitting {@link DisTube#playSong} event.
570
+ * <info>If {@link Song} is added from a YouTube {@link SearchResult} or {@link
571
+ * Playlist}, some info will be missing to save your resources. It will be filled
572
+ * when emitting {@link DisTube#playSong} event.
565
573
  *
566
574
  * Missing info: {@link Song#likes}, {@link Song#dislikes}, {@link Song#streamURL},
567
575
  * {@link Song#related}, {@link Song#chapters}, {@link Song#age_restricted}</info>
568
- * @template T - The type for the metadata (if any) of the song
569
576
  */
570
577
  declare class Song<T = unknown> {
571
578
  #private;
@@ -592,11 +599,9 @@ declare class Song<T = unknown> {
592
599
  reposts: number;
593
600
  /**
594
601
  * Create a Song
595
- * @param {ytdl.videoInfo|SearchResult|OtherSongInfo} info Raw info
596
- * @param {Object} [options] Optional options
597
- * @param {Discord.GuildMember} [options.member] Requested user
598
- * @param {string} [options.source="youtube"] Song source
599
- * @param {T} [options.metadata] Song metadata
602
+ *
603
+ * @param info - Raw info
604
+ * @param options - Optional options
600
605
  */
601
606
  constructor(info: ytdl__default.videoInfo | SearchResult | OtherSongInfo | ytdl__default.relatedVideo | RelatedSong | ytpl.result["items"][number], options?: {
602
607
  member?: GuildMember;
@@ -606,25 +611,22 @@ declare class Song<T = unknown> {
606
611
  _patchYouTube(i: ytdl__default.videoInfo | SearchResult): void;
607
612
  /**
608
613
  * Patch data from other source
609
- * @param {OtherSongInfo} info Video info
610
- * @private
614
+ *
615
+ * @param info - Video info
611
616
  */
612
617
  _patchOther(info: OtherSongInfo): void;
613
618
  /**
614
619
  * The playlist added this song
615
- * @type {Playlist?}
616
620
  */
617
621
  get playlist(): Playlist | undefined;
618
622
  set playlist(playlist: Playlist | undefined);
619
623
  /**
620
624
  * User requested.
621
- * @type {Discord.GuildMember?}
622
625
  */
623
626
  get member(): GuildMember | undefined;
624
627
  set member(member: GuildMember | undefined);
625
628
  /**
626
629
  * User requested.
627
- * @type {Discord.User?}
628
630
  */
629
631
  get user(): discord_js.User | undefined;
630
632
  get metadata(): T;
@@ -632,53 +634,43 @@ declare class Song<T = unknown> {
632
634
  }
633
635
 
634
636
  /**
635
- * @private
636
- * @abstract
637
+ * @virtual
637
638
  */
638
639
  declare abstract class DisTubeBase {
639
640
  distube: DisTube;
640
641
  constructor(distube: DisTube);
641
642
  /**
642
643
  * Emit the {@link DisTube} of this base
643
- * @param {string} eventName Event name
644
- * @param {...any} args arguments
645
- * @returns {boolean}
644
+ *
645
+ * @param eventName - Event name
646
+ * @param args - arguments
646
647
  */
647
648
  emit(eventName: keyof DisTubeEvents, ...args: any): boolean;
648
649
  /**
649
650
  * Emit error event
650
- * @param {Error} error error
651
- * @param {Discord.BaseGuildTextChannel} [channel] Text channel where the error is encountered.
651
+ *
652
+ * @param error - error
653
+ * @param channel - Text channel where the error is encountered.
652
654
  */
653
655
  emitError(error: Error, channel?: GuildTextBasedChannel): void;
654
656
  /**
655
657
  * The queue manager
656
- * @type {QueueManager}
657
- * @readonly
658
658
  */
659
659
  get queues(): QueueManager;
660
660
  /**
661
661
  * The voice manager
662
- * @type {DisTubeVoiceManager}
663
- * @readonly
664
662
  */
665
663
  get voices(): DisTubeVoiceManager;
666
664
  /**
667
665
  * Discord.js client
668
- * @type {Discord.Client}
669
- * @readonly
670
666
  */
671
667
  get client(): Client;
672
668
  /**
673
669
  * DisTube options
674
- * @type {DisTubeOptions}
675
- * @readonly
676
670
  */
677
671
  get options(): Options;
678
672
  /**
679
673
  * DisTube handler
680
- * @type {DisTubeHandler}
681
- * @readonly
682
674
  */
683
675
  get handler(): DisTubeHandler;
684
676
  }
@@ -695,119 +687,124 @@ declare class DisTubeVoice extends TypedEmitter<DisTubeVoiceEvents> {
695
687
  audioResource?: AudioResource;
696
688
  emittedError: boolean;
697
689
  isDisconnected: boolean;
690
+ stream?: DisTubeStream;
698
691
  constructor(voiceManager: DisTubeVoiceManager, channel: VoiceBasedChannel);
699
692
  /**
700
693
  * The voice channel id the bot is in
701
- * @type {Snowflake?}
702
694
  */
703
695
  get channelId(): string | undefined;
704
696
  get channel(): VoiceBasedChannel;
705
697
  set channel(channel: VoiceBasedChannel);
706
698
  /**
707
699
  * Join a voice channel with this connection
708
- * @param {Discord.BaseGuildVoiceChannel} [channel] A voice channel
709
- * @returns {Promise<DisTubeVoice>}
700
+ *
701
+ * @param channel - A voice channel
710
702
  */
711
703
  join(channel?: VoiceBasedChannel): Promise<DisTubeVoice>;
712
704
  /**
713
705
  * Leave the voice channel of this connection
714
- * @param {Error} [error] Optional, an error to emit with 'error' event.
706
+ *
707
+ * @param error - Optional, an error to emit with 'error' event.
715
708
  */
716
709
  leave(error?: Error): void;
717
710
  /**
718
711
  * Stop the playing stream
719
- * @param {boolean} [force=false] If true, will force the {@link DisTubeVoice#audioPlayer} to enter the Idle state
720
- * even if the {@link DisTubeVoice#audioResource} has silence padding frames.
721
- * @private
712
+ *
713
+ * @param force - If true, will force the {@link DisTubeVoice#audioPlayer} to enter the Idle state even
714
+ * if the {@link DisTubeVoice#audioResource} has silence padding frames.
722
715
  */
723
716
  stop(force?: boolean): void;
724
717
  /**
725
- * Play a readable stream
726
- * @private
727
- * @param {DisTubeStream} stream Readable stream
718
+ * Play a {@link DisTubeStream}
719
+ *
720
+ * @param dtStream - DisTubeStream
728
721
  */
729
- play(stream: DisTubeStream): void;
722
+ play(dtStream: DisTubeStream): void;
730
723
  set volume(volume: number);
731
724
  get volume(): number;
732
725
  /**
733
726
  * Playback duration of the audio resource in seconds
734
- * @type {number}
735
727
  */
736
728
  get playbackDuration(): number;
737
729
  pause(): void;
738
730
  unpause(): void;
739
731
  /**
740
732
  * Whether the bot is self-deafened
741
- * @type {boolean}
742
733
  */
743
734
  get selfDeaf(): boolean;
744
735
  /**
745
736
  * Whether the bot is self-muted
746
- * @type {boolean}
747
737
  */
748
738
  get selfMute(): boolean;
749
739
  /**
750
740
  * Self-deafens/undeafens the bot.
751
- * @param {boolean} selfDeaf Whether or not the bot should be self-deafened
752
- * @returns {boolean} true if the voice state was successfully updated, otherwise false
741
+ *
742
+ * @param selfDeaf - Whether or not the bot should be self-deafened
743
+ *
744
+ * @returns true if the voice state was successfully updated, otherwise false
753
745
  */
754
746
  setSelfDeaf(selfDeaf: boolean): boolean;
755
747
  /**
756
748
  * Self-mutes/unmutes the bot.
757
- * @param {boolean} selfMute Whether or not the bot should be self-muted
758
- * @returns {boolean} true if the voice state was successfully updated, otherwise false
749
+ *
750
+ * @param selfMute - Whether or not the bot should be self-muted
751
+ *
752
+ * @returns true if the voice state was successfully updated, otherwise false
759
753
  */
760
754
  setSelfMute(selfMute: boolean): boolean;
761
755
  /**
762
756
  * The voice state of this connection
763
- * @type {Discord.VoiceState?}
764
757
  */
765
758
  get voiceState(): VoiceState | undefined;
766
759
  }
767
760
 
768
761
  interface StreamOptions {
762
+ ffmpeg: {
763
+ path: string;
764
+ args: FFmpegOptions;
765
+ };
769
766
  seek?: number;
770
- ffmpegArgs?: string[];
771
767
  type?: StreamType;
772
768
  }
773
769
  declare const chooseBestVideoFormat: ({ duration, formats, isLive }: Song) => ytdl.videoFormat | undefined;
774
770
  /**
775
771
  * Create a stream to play with {@link DisTubeVoice}
776
- * @private
777
772
  */
778
- declare class DisTubeStream {
773
+ declare class DisTubeStream extends TypedEmitter<{
774
+ debug: (debug: string) => Awaitable;
775
+ }> {
776
+ private killed;
777
+ process: ChildProcess;
778
+ stream: PassThrough;
779
+ type: StreamType$1;
780
+ url: string;
779
781
  /**
780
- * Create a stream from ytdl video formats
781
- * @param {Song} song A YouTube Song
782
- * @param {StreamOptions} options options
783
- * @returns {DisTubeStream}
784
- * @private
782
+ * Create a DisTubeStream to play with {@link DisTubeVoice}
783
+ *
784
+ * @param url - Stream URL
785
+ * @param options - Stream options
785
786
  */
786
- static YouTube(song: Song, options?: StreamOptions): DisTubeStream;
787
+ constructor(url: string, { ffmpeg, seek, type }: StreamOptions);
788
+ private debug;
789
+ kill(): void;
787
790
  /**
788
- * Create a stream from a stream url
789
- * @param {string} url stream url
790
- * @param {StreamOptions} options options
791
- * @returns {DisTubeStream}
792
- * @private
791
+ * Create a stream from a YouTube {@link Song}
792
+ *
793
+ * @param song - A YouTube Song
794
+ * @param options - options
793
795
  */
794
- static DirectLink(url: string, options?: StreamOptions): DisTubeStream;
795
- type: StreamType$1;
796
- stream: FFmpeg;
797
- url: string;
796
+ static YouTube(song: Song, options: StreamOptions): DisTubeStream;
798
797
  /**
799
- * Create a DisTubeStream to play with {@link DisTubeVoice}
800
- * @param {string} url Stream URL
801
- * @param {StreamOptions} options Stream options
802
- * @private
798
+ * Create a stream from a stream url
799
+ *
800
+ * @param url - stream url
801
+ * @param options - options
803
802
  */
804
- constructor(url: string, options: StreamOptions);
803
+ static DirectLink(url: string, options: StreamOptions): DisTubeStream;
805
804
  }
806
805
 
807
806
  /**
808
807
  * DisTube's Handler
809
- * @extends DisTubeBase
810
- * @private
811
808
  */
812
809
  declare class DisTubeHandler extends DisTubeBase {
813
810
  #private;
@@ -815,9 +812,8 @@ declare class DisTubeHandler extends DisTubeBase {
815
812
  get ytdlOptions(): ytdl__default.getInfoOptions;
816
813
  get ytCookie(): string;
817
814
  /**
818
- * @param {string} url url
819
- * @param {boolean} [basic=false] getBasicInfo?
820
- * @returns {Promise<ytdl.videoInfo>}
815
+ * @param url - url
816
+ * @param basic - getBasicInfo?
821
817
  */
822
818
  getYouTubeInfo(url: string, basic?: boolean): Promise<ytdl__default.videoInfo>;
823
819
  resolve<T = unknown>(song: Song<T>, options?: Omit<ResolveOptions, "metadata">): Promise<Song<T>>;
@@ -830,46 +826,55 @@ declare class DisTubeHandler extends DisTubeBase {
830
826
  resolvePlaylist<T = undefined>(playlist: Playlist | Song[] | string, options: ResolvePlaylistOptions<T>): Promise<Playlist<T>>;
831
827
  resolvePlaylist(playlist: Playlist | Song[] | string, options?: ResolvePlaylistOptions): Promise<Playlist>;
832
828
  /**
833
- * Search for a song, fire {@link DisTube#event:error} if not found.
834
- * @param {Discord.Message} message The original message from an user
835
- * @param {string} query The query string
836
- * @returns {Promise<SearchResult?>} Song info
837
- * @throws {DisTubeError}
829
+ * Search for a song, fire {@link DisTube#error} if not found.
830
+ *
831
+ * @throws {@link DisTubeError}
832
+ *
833
+ * @param message - The original message from an user
834
+ * @param query - The query string
835
+ *
836
+ * @returns Song info
838
837
  */
839
838
  searchSong(message: Message<true>, query: string): Promise<SearchResult | null>;
840
839
  /**
841
840
  * Create a message collector for selecting search results.
842
841
  *
843
- * Needed events: {@link DisTube#event:searchResult}, {@link DisTube#event:searchCancel},
844
- * {@link DisTube#event:searchInvalidAnswer}, {@link DisTube#event:searchDone}.
845
- * @param {Discord.Message} message The original message from an user
846
- * @param {Array<SearchResult|Song|Playlist>} results The search results
847
- * @param {string?} [query] The query string
848
- * @returns {Promise<SearchResult|Song|Playlist|null>} Selected result
849
- * @throws {DisTubeError}
842
+ * Needed events: {@link DisTube#searchResult}, {@link DisTube#searchCancel},
843
+ * {@link DisTube#searchInvalidAnswer}, {@link DisTube#searchDone}.
844
+ *
845
+ * @throws {@link DisTubeError}
846
+ *
847
+ * @param message - The original message from an user
848
+ * @param results - The search results
849
+ * @param query - The query string
850
+ *
851
+ * @returns Selected result
850
852
  */
851
853
  createSearchMessageCollector<R extends SearchResult | Song | Playlist>(message: Message<true>, results: Array<R>, query?: string): Promise<R | null>;
852
854
  /**
853
855
  * Play or add a {@link Playlist} to the queue.
854
- * @param {Discord.BaseGuildVoiceChannel} voiceChannel A voice channel
855
- * @param {Playlist|string} playlist A YouTube playlist url | a Playlist
856
- * @param {PlayHandlerOptions} [options] Optional options
857
- * @returns {Promise<void>}
858
- * @throws {DisTubeError}
856
+ *
857
+ * @throws {@link DisTubeError}
858
+ *
859
+ * @param voiceChannel - A voice channel
860
+ * @param playlist - A YouTube playlist url | a Playlist
861
+ * @param options - Optional options
859
862
  */
860
863
  playPlaylist(voiceChannel: VoiceBasedChannel, playlist: Playlist, options?: PlayHandlerOptions): Promise<void>;
861
864
  /**
862
865
  * Play or add a {@link Song} to the queue.
863
- * @param {Discord.BaseGuildVoiceChannel} voiceChannel A voice channel
864
- * @param {Song} song A YouTube playlist url | a Playlist
865
- * @param {PlayHandlerOptions} [options] Optional options
866
- * @returns {Promise<void>}
867
- * @throws {DisTubeError}
866
+ *
867
+ * @throws {@link DisTubeError}
868
+ *
869
+ * @param voiceChannel - A voice channel
870
+ * @param song - A YouTube playlist url | a Playlist
871
+ * @param options - Optional options
868
872
  */
869
873
  playSong(voiceChannel: VoiceBasedChannel, song: Song, options?: PlayHandlerOptions): Promise<void>;
870
874
  /**
871
875
  * Get {@link Song}'s stream info and attach it to the song.
872
- * @param {Song} song A Song
876
+ *
877
+ * @param song - A Song
873
878
  */
874
879
  attachStreamInfo(song: Song): Promise<void>;
875
880
  }
@@ -894,37 +899,34 @@ declare class Options {
894
899
  joinNewVoiceChannel: boolean;
895
900
  streamType: StreamType;
896
901
  directLink: boolean;
902
+ ffmpegPath: string;
903
+ ffmpegDefaultArgs: FFmpegOptions;
897
904
  constructor(options: DisTubeOptions);
898
905
  }
899
906
 
900
907
  /**
901
908
  * Manages the collection of a data model.
902
- * @abstract
903
- * @private
904
- * @extends DisTubeBase
909
+ *
910
+ * @virtual
905
911
  */
906
912
  declare abstract class BaseManager<V> extends DisTubeBase {
907
913
  /**
908
914
  * The collection of items for this manager.
909
- * @type {Collection}
910
- * @name BaseManager#collection
911
915
  */
912
916
  collection: Collection<string, V>;
913
917
  /**
914
918
  * The size of the collection.
915
- * @type {number}
916
919
  */
917
920
  get size(): number;
918
921
  }
919
922
 
920
923
  /**
921
924
  * Manages the collection of a data model paired with a guild id.
922
- * @abstract
923
- * @private
924
- * @extends BaseManager
925
+ *
926
+ * @virtual
925
927
  */
926
928
  declare abstract class GuildIdManager<V> extends BaseManager<V> {
927
- add(idOrInstance: GuildIdResolvable, data: V): this | _discordjs_collection.Collection<string, V>;
929
+ add(idOrInstance: GuildIdResolvable, data: V): this;
928
930
  get(idOrInstance: GuildIdResolvable): V | undefined;
929
931
  remove(idOrInstance: GuildIdResolvable): boolean;
930
932
  has(idOrInstance: GuildIdResolvable): boolean;
@@ -932,138 +934,123 @@ declare abstract class GuildIdManager<V> extends BaseManager<V> {
932
934
 
933
935
  /**
934
936
  * Manages voice connections for {@link DisTube}
935
- * @extends BaseManager
936
937
  */
937
938
  declare class DisTubeVoiceManager extends GuildIdManager<DisTubeVoice> {
938
939
  /**
939
940
  * Get a {@link DisTubeVoice}.
940
- * @method get
941
- * @memberof DisTubeVoiceManager#
942
- * @param {GuildIdResolvable} guild The queue resolvable to resolve
943
- * @returns {DisTubeVoice?}
941
+ *
942
+ * @param guild - The queue resolvable to resolve
944
943
  */
945
944
  /**
946
945
  * Collection of {@link DisTubeVoice}.
947
- * @name DisTubeVoiceManager#collection
948
- * @type {Discord.Collection<string, DisTubeVoice>}
949
946
  */
950
947
  /**
951
948
  * Create a {@link DisTubeVoice}
952
- * @param {Discord.BaseGuildVoiceChannel} channel A voice channel to join
953
- * @returns {DisTubeVoice}
954
- * @private
949
+ *
950
+ * @param channel - A voice channel to join
955
951
  */
956
952
  create(channel: VoiceBasedChannel): DisTubeVoice;
957
953
  /**
958
954
  * Join a voice channel
959
- * @param {Discord.BaseGuildVoiceChannel} channel A voice channel to join
960
- * @returns {Promise<DisTubeVoice>}
955
+ *
956
+ * @param channel - A voice channel to join
961
957
  */
962
958
  join(channel: VoiceBasedChannel): Promise<DisTubeVoice>;
963
959
  /**
964
960
  * Leave the connected voice channel in a guild
965
- * @param {GuildIdResolvable} guild Queue Resolvable
961
+ *
962
+ * @param guild - Queue Resolvable
966
963
  */
967
964
  leave(guild: GuildIdResolvable): void;
968
965
  }
969
966
 
970
967
  /**
971
968
  * Manage filters of a playing {@link Queue}
972
- * @extends {BaseManager}
973
969
  */
974
970
  declare class FilterManager extends BaseManager<Filter> {
975
971
  #private;
976
972
  /**
977
973
  * Collection of {@link Filter}.
978
- * @name FilterManager#collection
979
- * @type {Discord.Collection<string, DisTubeVoice>}
980
974
  */
981
975
  queue: Queue;
982
976
  constructor(queue: Queue);
983
977
  /**
984
978
  * Enable a filter or multiple filters to the manager
985
- * @param {FilterResolvable|FilterResolvable[]} filterOrFilters The filter or filters to enable
986
- * @param {boolean} [override=false] Wether or not override the applied filter with new filter value
987
- * @returns {FilterManager}
979
+ *
980
+ * @param filterOrFilters - The filter or filters to enable
981
+ * @param override - Wether or not override the applied filter with new filter value
988
982
  */
989
983
  add(filterOrFilters: FilterResolvable | FilterResolvable[], override?: boolean): this;
990
984
  /**
991
985
  * Clear enabled filters of the manager
992
- * @returns {FilterManager}
993
986
  */
994
987
  clear(): this;
995
988
  /**
996
989
  * Set the filters applied to the manager
997
- * @param {FilterResolvable[]} filters The filters to apply
998
- * @returns {FilterManager}
990
+ *
991
+ * @param filters - The filters to apply
999
992
  */
1000
993
  set(filters: FilterResolvable[]): this;
1001
994
  /**
1002
995
  * Disable a filter or multiple filters
1003
- * @param {FilterResolvable|FilterResolvable[]} filterOrFilters The filter or filters to disable
1004
- * @returns {FilterManager}
996
+ *
997
+ * @param filterOrFilters - The filter or filters to disable
1005
998
  */
1006
999
  remove(filterOrFilters: FilterResolvable | FilterResolvable[]): this;
1007
1000
  /**
1008
1001
  * Check whether a filter enabled or not
1009
- * @param {FilterResolvable} filter The filter to check
1010
- * @returns {boolean}
1002
+ *
1003
+ * @param filter - The filter to check
1011
1004
  */
1012
1005
  has(filter: FilterResolvable): boolean;
1013
1006
  /**
1014
1007
  * Array of enabled filter names
1015
- * @type {Array<string>}
1016
- * @readonly
1017
1008
  */
1018
1009
  get names(): string[];
1019
1010
  /**
1020
1011
  * Array of enabled filters
1021
- * @type {Array<Filter>}
1022
- * @readonly
1023
1012
  */
1024
1013
  get values(): Filter[];
1025
- get ffmpegArgs(): string[];
1014
+ get ffmpegArgs(): FFmpegOptions;
1026
1015
  toString(): string;
1027
1016
  }
1028
1017
 
1029
1018
  /**
1030
1019
  * Queue manager
1031
- * @extends GuildIdManager
1032
1020
  */
1033
1021
  declare class QueueManager extends GuildIdManager<Queue> {
1034
1022
  #private;
1035
1023
  /**
1036
1024
  * Collection of {@link Queue}.
1037
- * @name QueueManager#collection
1038
- * @type {Discord.Collection<string, Queue>}
1039
1025
  */
1040
1026
  /**
1041
1027
  * Create a {@link Queue}
1042
- * @private
1043
- * @param {Discord.BaseGuildVoiceChannel} channel A voice channel
1044
- * @param {Song|Song[]} song First song
1045
- * @param {Discord.BaseGuildTextChannel} textChannel Default text channel
1046
- * @returns {Promise<Queue|true>} Returns `true` if encounter an error
1028
+ *
1029
+ * @param channel - A voice channel
1030
+ * @param song - First song
1031
+ * @param textChannel - Default text channel
1032
+ *
1033
+ * @returns Returns `true` if encounter an error
1047
1034
  */
1048
1035
  create(channel: VoiceBasedChannel, song: Song[] | Song, textChannel?: GuildTextBasedChannel): Promise<Queue | true>;
1049
1036
  /**
1050
1037
  * Create a ytdl stream
1051
- * @param {Queue} queue Queue
1052
- * @returns {DisTubeStream}
1038
+ *
1039
+ * @param queue - Queue
1053
1040
  */
1054
1041
  createStream(queue: Queue): DisTubeStream;
1055
1042
  /**
1056
1043
  * Play a song on voice connection
1057
- * @private
1058
- * @param {Queue} queue The guild queue
1059
- * @returns {Promise<boolean>} error?
1044
+ *
1045
+ * @param queue - The guild queue
1046
+ *
1047
+ * @returns error?
1060
1048
  */
1061
1049
  playSong(queue: Queue): Promise<boolean>;
1062
1050
  }
1063
1051
 
1064
1052
  /**
1065
1053
  * Represents a queue.
1066
- * @extends DisTubeBase
1067
1054
  */
1068
1055
  declare class Queue extends DisTubeBase {
1069
1056
  #private;
@@ -1085,125 +1072,123 @@ declare class Queue extends DisTubeBase {
1085
1072
  _listeners?: DisTubeVoiceEvents;
1086
1073
  /**
1087
1074
  * Create a queue for the guild
1088
- * @param {DisTube} distube DisTube
1089
- * @param {DisTubeVoice} voice Voice connection
1090
- * @param {Song|Song[]} song First song(s)
1091
- * @param {Discord.BaseGuildTextChannel?} textChannel Default text channel
1075
+ *
1076
+ * @param distube - DisTube
1077
+ * @param voice - Voice connection
1078
+ * @param song - First song(s)
1079
+ * @param textChannel - Default text channel
1092
1080
  */
1093
1081
  constructor(distube: DisTube, voice: DisTubeVoice, song: Song | Song[], textChannel?: GuildTextBasedChannel);
1094
1082
  /**
1095
1083
  * The client user as a `GuildMember` of this queue's guild
1096
- * @type {Discord.GuildMember?}
1097
1084
  */
1098
1085
  get clientMember(): discord_js.GuildMember | undefined;
1099
1086
  /**
1100
1087
  * The filter manager of the queue
1101
- * @type {FilterManager}
1102
- * @readonly
1103
1088
  */
1104
1089
  get filters(): FilterManager;
1105
1090
  /**
1106
1091
  * Formatted duration string.
1107
- * @type {string}
1108
- * @readonly
1109
1092
  */
1110
1093
  get formattedDuration(): string;
1111
1094
  /**
1112
1095
  * Queue's duration.
1113
- * @type {number}
1114
- * @readonly
1115
1096
  */
1116
1097
  get duration(): number;
1117
1098
  /**
1118
1099
  * What time in the song is playing (in seconds).
1119
- * @type {number}
1120
- * @readonly
1121
1100
  */
1122
1101
  get currentTime(): number;
1123
1102
  /**
1124
1103
  * Formatted {@link Queue#currentTime} string.
1125
- * @type {string}
1126
- * @readonly
1127
1104
  */
1128
1105
  get formattedCurrentTime(): string;
1129
1106
  /**
1130
1107
  * The voice channel playing in.
1131
- * @type {Discord.VoiceChannel|Discord.StageChannel|null}
1132
- * @readonly
1133
1108
  */
1134
1109
  get voiceChannel(): discord_js.VoiceBasedChannel | null;
1135
1110
  get volume(): number;
1136
1111
  set volume(value: number);
1137
1112
  /**
1138
- * @private
1139
- * Add a Song or an array of Song to the queue
1140
- * @param {Song|Song[]} song Song to add
1141
- * @param {number} [position=0] Position to add, <= 0 to add to the end of the queue
1142
- * @throws {Error}
1143
- * @returns {Queue} The guild queue
1113
+ * @throws {DisTubeError}
1114
+ *
1115
+ * @param song - Song to add
1116
+ * @param position - Position to add, \<= 0 to add to the end of the queue
1117
+ *
1118
+ * @returns The guild queue
1144
1119
  */
1145
1120
  addToQueue(song: Song | Song[], position?: number): Queue;
1146
1121
  /**
1147
1122
  * Pause the guild stream
1148
- * @returns {Queue} The guild queue
1123
+ *
1124
+ * @returns The guild queue
1149
1125
  */
1150
1126
  pause(): Queue;
1151
1127
  /**
1152
1128
  * Resume the guild stream
1153
- * @returns {Queue} The guild queue
1129
+ *
1130
+ * @returns The guild queue
1154
1131
  */
1155
1132
  resume(): Queue;
1156
1133
  /**
1157
1134
  * Set the guild stream's volume
1158
- * @param {number} percent The percentage of volume you want to set
1159
- * @returns {Queue} The guild queue
1135
+ *
1136
+ * @param percent - The percentage of volume you want to set
1137
+ *
1138
+ * @returns The guild queue
1160
1139
  */
1161
1140
  setVolume(percent: number): Queue;
1162
1141
  /**
1163
- * Skip the playing song if there is a next song in the queue.
1164
- * <info>If {@link Queue#autoplay} is `true` and there is no up next song,
1165
- * DisTube will add and play a related song.</info>
1166
- * @returns {Promise<Song>} The song will skip to
1167
- * @throws {Error}
1142
+ * Skip the playing song if there is a next song in the queue. <info>If {@link
1143
+ * Queue#autoplay} is `true` and there is no up next song, DisTube will add and
1144
+ * play a related song.</info>
1145
+ *
1146
+ * @returns The song will skip to
1168
1147
  */
1169
1148
  skip(): Promise<Song>;
1170
1149
  /**
1171
1150
  * Play the previous song if exists
1172
- * @returns {Promise<Song>} The guild queue
1173
- * @throws {Error}
1151
+ *
1152
+ * @returns The guild queue
1174
1153
  */
1175
1154
  previous(): Promise<Song>;
1176
1155
  /**
1177
1156
  * Shuffle the queue's songs
1178
- * @returns {Promise<Queue>} The guild queue
1157
+ *
1158
+ * @returns The guild queue
1179
1159
  */
1180
1160
  shuffle(): Promise<Queue>;
1181
1161
  /**
1182
- * Jump to the song position in the queue.
1183
- * The next one is 1, 2,...
1184
- * The previous one is -1, -2,...
1185
- * @param {number} position The song position to play
1186
- * @returns {Promise<Song>} The new Song will be played
1187
- * @throws {Error} if `num` is invalid number
1162
+ * Jump to the song position in the queue. The next one is 1, 2,... The previous
1163
+ * one is -1, -2,...
1164
+ * if `num` is invalid number
1165
+ *
1166
+ * @param position - The song position to play
1167
+ *
1168
+ * @returns The new Song will be played
1188
1169
  */
1189
1170
  jump(position: number): Promise<Song>;
1190
1171
  /**
1191
- * Set the repeat mode of the guild queue.\
1172
+ * Set the repeat mode of the guild queue.
1192
1173
  * Toggle mode `(Disabled -> Song -> Queue -> Disabled ->...)` if `mode` is `undefined`
1193
- * @param {RepeatMode?} [mode] The repeat modes (toggle if `undefined`)
1194
- * @returns {RepeatMode} The new repeat mode
1174
+ *
1175
+ * @param mode - The repeat modes (toggle if `undefined`)
1176
+ *
1177
+ * @returns The new repeat mode
1195
1178
  */
1196
1179
  setRepeatMode(mode?: RepeatMode): RepeatMode;
1197
1180
  /**
1198
1181
  * Set the playing time to another position
1199
- * @param {number} time Time in seconds
1200
- * @returns {Queue} The guild queue
1182
+ *
1183
+ * @param time - Time in seconds
1184
+ *
1185
+ * @returns The guild queue
1201
1186
  */
1202
1187
  seek(time: number): Queue;
1203
1188
  /**
1204
1189
  * Add a related song of the playing song to the queue
1205
- * @returns {Promise<Song>} The added song
1206
- * @throws {Error}
1190
+ *
1191
+ * @returns The added song
1207
1192
  */
1208
1193
  addRelatedSong(): Promise<Song>;
1209
1194
  /**
@@ -1211,22 +1196,22 @@ declare class Queue extends DisTubeBase {
1211
1196
  */
1212
1197
  stop(): Promise<void>;
1213
1198
  /**
1214
- * Remove the queue from the manager
1215
- * (This does not leave the voice channel even if {@link DisTubeOptions|DisTubeOptions.leaveOnStop} is enabled)
1216
- * @private
1199
+ * Remove the queue from the manager (This does not leave the voice channel even if
1200
+ * {@link DisTubeOptions | DisTubeOptions.leaveOnStop} is enabled)
1217
1201
  */
1218
1202
  remove(): void;
1219
1203
  /**
1220
1204
  * Toggle autoplay mode
1221
- * @returns {boolean} Autoplay mode state
1205
+ *
1206
+ * @returns Autoplay mode state
1222
1207
  */
1223
1208
  toggleAutoplay(): boolean;
1224
1209
  }
1225
1210
 
1226
1211
  /**
1227
1212
  * DisTube Plugin
1228
- * @abstract
1229
- * @private
1213
+ *
1214
+ * @virtual
1230
1215
  */
1231
1216
  declare abstract class Plugin {
1232
1217
  abstract type: PluginType;
@@ -1234,78 +1219,68 @@ declare abstract class Plugin {
1234
1219
  init(distube: DisTube): void;
1235
1220
  /**
1236
1221
  * Type of the plugin
1237
- * @name Plugin#type
1238
- * @type {PluginType}
1239
1222
  */
1240
1223
  /**
1241
1224
  * Emit an event to the {@link DisTube} class
1242
- * @param {string} eventName Event name
1243
- * @param {...any} args arguments
1244
- * @returns {boolean}
1225
+ *
1226
+ * @param eventName - Event name
1227
+ * @param args - arguments
1245
1228
  */
1246
1229
  emit(eventName: keyof DisTubeEvents, ...args: any): boolean;
1247
1230
  /**
1248
1231
  * Emit error event to the {@link DisTube} class
1249
- * @param {Error} error error
1250
- * @param {Discord.BaseGuildTextChannel} [channel] Text channel where the error is encountered.
1232
+ *
1233
+ * @param error - error
1234
+ * @param channel - Text channel where the error is encountered.
1251
1235
  */
1252
1236
  emitError(error: Error, channel?: GuildTextBasedChannel): void;
1253
1237
  /**
1254
1238
  * The queue manager
1255
- * @type {QueueManager}
1256
- * @readonly
1257
1239
  */
1258
1240
  get queues(): QueueManager;
1259
1241
  /**
1260
1242
  * The voice manager
1261
- * @type {DisTubeVoiceManager}
1262
- * @readonly
1263
1243
  */
1264
1244
  get voices(): DisTubeVoiceManager;
1265
1245
  /**
1266
1246
  * Discord.js client
1267
- * @type {Discord.Client}
1268
- * @readonly
1269
1247
  */
1270
1248
  get client(): Client;
1271
1249
  /**
1272
1250
  * DisTube options
1273
- * @type {DisTubeOptions}
1274
- * @readonly
1275
1251
  */
1276
1252
  get options(): Options;
1277
1253
  /**
1278
1254
  * DisTube handler
1279
- * @type {DisTubeHandler}
1280
- * @readonly
1281
1255
  */
1282
1256
  get handler(): DisTubeHandler;
1283
1257
  /**
1284
1258
  * Check if the string is working with this plugin
1285
- * @param {string} _string Input string
1286
- * @returns {boolean|Promise<boolean>}
1259
+ *
1260
+ * @param _string - Input string
1287
1261
  */
1288
1262
  validate(_string: string): Awaitable<boolean>;
1289
1263
  /**
1290
1264
  * Get the stream url from {@link Song#url}. Returns {@link Song#url} by default.
1291
1265
  * Not needed if the plugin plays song from YouTube.
1292
- * @param {string} url Input url
1293
- * @returns {string|Promise<string>}
1266
+ *
1267
+ * @param url - Input url
1294
1268
  */
1295
1269
  getStreamURL(url: string): Awaitable<string>;
1296
1270
  /**
1297
- * Get related songs from a supported url. {@link Song#member} should be `undefined`.
1298
- * Not needed to add {@link Song#related} because it will be added with this function later.
1299
- * @param {string} _url Input url
1300
- * @returns {Song[]|Promise<Song[]>}
1271
+ * Get related songs from a supported url. {@link Song#member} should be
1272
+ * `undefined`. Not needed to add {@link Song#related} because it will be added
1273
+ * with this function later.
1274
+ *
1275
+ * @param _url - Input url
1301
1276
  */
1302
1277
  getRelatedSongs(_url: string): Awaitable<RelatedSong[]>;
1303
1278
  }
1304
1279
 
1305
1280
  /**
1306
1281
  * Custom Plugin
1307
- * @extends Plugin
1308
- * @abstract
1282
+ *
1283
+ * @virtual
1309
1284
  */
1310
1285
  declare abstract class CustomPlugin extends Plugin {
1311
1286
  readonly type = PluginType.CUSTOM;
@@ -1314,8 +1289,8 @@ declare abstract class CustomPlugin extends Plugin {
1314
1289
 
1315
1290
  /**
1316
1291
  * Extractor Plugin
1317
- * @extends Plugin
1318
- * @abstract
1292
+ *
1293
+ * @virtual
1319
1294
  */
1320
1295
  declare abstract class ExtractorPlugin extends Plugin {
1321
1296
  readonly type = PluginType.EXTRACTOR;
@@ -1327,38 +1302,39 @@ declare abstract class ExtractorPlugin extends Plugin {
1327
1302
 
1328
1303
  /**
1329
1304
  * Format duration to string
1330
- * @param {number} sec Duration in seconds
1331
- * @returns {string}
1305
+ *
1306
+ * @param sec - Duration in seconds
1332
1307
  */
1333
1308
  declare function formatDuration(sec: number): string;
1334
1309
  /**
1335
1310
  * Convert formatted duration to seconds
1336
- * @param {*} input Formatted duration string
1337
- * @returns {number}
1311
+ *
1312
+ * @param input - Formatted duration string
1338
1313
  */
1339
1314
  declare function toSecond(input: any): number;
1340
1315
  /**
1341
1316
  * Parse number from input
1342
- * @param {*} input Any
1343
- * @returns {number}
1317
+ *
1318
+ * @param input - Any
1344
1319
  */
1345
1320
  declare function parseNumber(input: any): number;
1346
1321
  declare const SUPPORTED_PROTOCOL: readonly ["https:", "http:", "file:"];
1347
1322
  /**
1348
1323
  * Check if the string is an URL
1349
- * @param {string} input input
1350
- * @returns {boolean}
1324
+ *
1325
+ * @param input - input
1351
1326
  */
1352
1327
  declare function isURL(input: any): input is `${(typeof SUPPORTED_PROTOCOL)[number]}//${string}`;
1353
1328
  /**
1354
1329
  * Check if the Client has enough intents to using DisTube
1355
- * @param {ClientOptions} options options
1330
+ *
1331
+ * @param options - options
1356
1332
  */
1357
1333
  declare function checkIntents(options: ClientOptions): void;
1358
1334
  /**
1359
1335
  * Check if the voice channel is empty
1360
- * @param {Discord.VoiceState} voiceState voiceState
1361
- * @returns {boolean}
1336
+ *
1337
+ * @param voiceState - voiceState
1362
1338
  */
1363
1339
  declare function isVoiceChannelEmpty(voiceState: VoiceState): boolean;
1364
1340
  declare function isSnowflake(id: any): id is Snowflake;
@@ -1387,9 +1363,246 @@ declare class DirectLinkPlugin extends ExtractorPlugin {
1387
1363
  }
1388
1364
 
1389
1365
  declare const version: string;
1366
+ interface DisTube extends TypedEmitter<TypedDisTubeEvents> {
1367
+ /**
1368
+ * @event
1369
+ * Emitted after DisTube add a new playlist to the playing {@link Queue}.
1370
+ *
1371
+ * @example
1372
+ * ```ts
1373
+ * distube.on("addList", (queue, playlist) => queue.textChannel.send(
1374
+ * `Added \`${playlist.name}\` playlist (${playlist.songs.length} songs) to the queue!`
1375
+ * ));
1376
+ * ```
1377
+ *
1378
+ * @param queue - The guild queue
1379
+ * @param playlist - Playlist info
1380
+ */
1381
+ [Events.ADD_LIST]: (queue: Queue, playlist: Playlist) => Awaitable;
1382
+ /**
1383
+ * @event
1384
+ * Emitted after DisTube add a new song to the playing {@link Queue}.
1385
+ *
1386
+ * @example
1387
+ * ```ts
1388
+ * distube.on("addSong", (queue, song) => queue.textChannel.send(
1389
+ * `Added ${song.name} - \`${song.formattedDuration}\` to the queue by ${song.user}.`
1390
+ * ));
1391
+ * ```
1392
+ *
1393
+ * @param queue - The guild queue
1394
+ * @param song - Added song
1395
+ */
1396
+ [Events.ADD_SONG]: (queue: Queue, song: Song) => Awaitable;
1397
+ /**
1398
+ * @event
1399
+ * Emitted when a {@link Queue} is deleted with any reasons.
1400
+ *
1401
+ * @param queue - The guild queue
1402
+ */
1403
+ [Events.DELETE_QUEUE]: (queue: Queue) => Awaitable;
1404
+ /**
1405
+ * @event
1406
+ * Emitted when the bot is disconnected to a voice channel.
1407
+ *
1408
+ * @param queue - The guild queue
1409
+ */
1410
+ [Events.DISCONNECT]: (queue: Queue) => Awaitable;
1411
+ /**
1412
+ * @event
1413
+ * Emitted when there is no user in the voice channel, {@link DisTubeOptions}.leaveOnEmpty
1414
+ * is `true` and there is a playing queue.
1415
+ *
1416
+ * If there is no playing queue (stopped and {@link DisTubeOptions}.leaveOnStop is
1417
+ * `false`), it will leave the channel without emitting this event.
1418
+ *
1419
+ * @example
1420
+ * ```ts
1421
+ * distube.on("empty", queue => queue.textChannel.send("Channel is empty. Leaving the channel"))
1422
+ * ```
1423
+ *
1424
+ * @param queue - The guild queue
1425
+ */
1426
+ [Events.EMPTY]: (queue: Queue) => Awaitable;
1427
+ /**
1428
+ * @event
1429
+ * Emitted when DisTube encounters an error while playing songs.
1430
+ *
1431
+ * @example
1432
+ * ```ts
1433
+ * distube.on('error', (channel, e) => {
1434
+ * if (channel) channel.send(`An error encountered: ${e}`)
1435
+ * else console.error(e)
1436
+ * })
1437
+ * ```
1438
+ *
1439
+ * @param channel - Text channel where the error is encountered.
1440
+ * @param error - The error encountered
1441
+ */
1442
+ [Events.ERROR]: (channel: GuildTextBasedChannel | undefined, error: Error) => Awaitable;
1443
+ /**
1444
+ * @event
1445
+ * Emitted for FFmpeg debugging information.
1446
+ *
1447
+ * @param debug - The debug information
1448
+ */
1449
+ [Events.FFMPEG_DEBUG]: (debug: string) => Awaitable;
1450
+ /**
1451
+ * @event
1452
+ * Emitted when there is no more song in the queue and {@link Queue#autoplay} is
1453
+ * `false`. DisTube will leave voice channel if {@link
1454
+ * DisTubeOptions}.leaveOnFinish is `true`.
1455
+ *
1456
+ * @example
1457
+ * ```ts
1458
+ * distube.on("finish", queue => queue.textChannel.send("No more song in queue"));
1459
+ * ```
1460
+ *
1461
+ * @param queue - The guild queue
1462
+ */
1463
+ [Events.FINISH]: (queue: Queue) => Awaitable;
1464
+ /**
1465
+ * @event
1466
+ * Emitted when DisTube finished a song.
1467
+ *
1468
+ * @example
1469
+ * ```ts
1470
+ * distube.on("finishSong", (queue, song) => queue.textChannel.send(`${song.name} has finished!`));
1471
+ * ```
1472
+ *
1473
+ * @param queue - The guild queue
1474
+ * @param song - Finished song
1475
+ */
1476
+ [Events.FINISH_SONG]: (queue: Queue, song: Song) => Awaitable;
1477
+ /**
1478
+ * @event
1479
+ * Emitted when DisTube initialize a queue to change queue default properties.
1480
+ *
1481
+ * @example
1482
+ * ```ts
1483
+ * distube.on("initQueue", queue => {
1484
+ * queue.autoplay = false;
1485
+ * queue.volume = 100;
1486
+ * });
1487
+ * ```ts
1488
+ *
1489
+ * @param queue - The guild queue
1490
+ */
1491
+ [Events.INIT_QUEUE]: (queue: Queue) => Awaitable;
1492
+ /**
1493
+ * @event
1494
+ * Emitted when {@link Queue#autoplay} is `true`, {@link Queue#songs} is empty, and
1495
+ * DisTube cannot find related songs to play.
1496
+ *
1497
+ * @example
1498
+ * ```ts
1499
+ * distube.on("noRelated", queue => queue.textChannel.send("Can't find related video to play."));
1500
+ * ```ts
1501
+ *
1502
+ * @param queue - The guild queue
1503
+ */
1504
+ [Events.NO_RELATED]: (queue: Queue) => Awaitable;
1505
+ /**
1506
+ * @event
1507
+ * Emitted when DisTube play a song.
1508
+ *
1509
+ * If {@link DisTubeOptions}.emitNewSongOnly is `true`, this event is not emitted
1510
+ * when looping a song or next song is the previous one.
1511
+ *
1512
+ * @example
1513
+ * ```ts
1514
+ * distube.on("playSong", (queue, song) => queue.textChannel.send(
1515
+ * `Playing \`${song.name}\` - \`${song.formattedDuration}\`\nRequested by: ${song.user}`
1516
+ * ));
1517
+ * ```ts
1518
+ *
1519
+ * @param queue - The guild queue
1520
+ * @param song - Playing song
1521
+ */
1522
+ [Events.PLAY_SONG]: (queue: Queue, song: Song) => Awaitable;
1523
+ /**
1524
+ * @event
1525
+ * Emitted when {@link DisTubeOptions | DisTubeOptions.searchSongs} bigger than 0,
1526
+ * and the search canceled due to {@link DisTubeOptions |
1527
+ * DisTubeOptions.searchTimeout}.
1528
+ *
1529
+ * @example
1530
+ * ```ts
1531
+ * // DisTubeOptions.searchSongs > 0
1532
+ * distube.on("searchCancel", (message) => message.channel.send(`Searching canceled`));
1533
+ * ```ts
1534
+ *
1535
+ * @param message - The user message called play method
1536
+ * @param query - The search query
1537
+ */
1538
+ [Events.SEARCH_CANCEL]: (message: Message, query: string) => Awaitable;
1539
+ /**
1540
+ * @event
1541
+ * Emitted when {@link DisTubeOptions | DisTubeOptions.searchSongs} bigger than 0,
1542
+ * and after the user chose a search result to play.
1543
+ *
1544
+ * @param message - The user message called play method
1545
+ * @param answer - The answered message of user
1546
+ * @param query - The search query
1547
+ */
1548
+ [Events.SEARCH_DONE]: (message: Message, answer: string, query: string) => Awaitable;
1549
+ /**
1550
+ * @event
1551
+ * Emitted when {@link DisTubeOptions | DisTubeOptions.searchSongs} bigger than 0,
1552
+ * and the search canceled due to user's next message is not a number or out of
1553
+ * results range.
1554
+ *
1555
+ * @example
1556
+ * ```ts
1557
+ * // DisTubeOptions.searchSongs > 0
1558
+ * distube.on("searchInvalidAnswer", (message) => message.channel.send(`You answered an invalid number!`));
1559
+ * ```ts
1560
+ *
1561
+ * @param message - The user message called play method
1562
+ * @param answer - The answered message of user
1563
+ * @param query - The search query
1564
+ */
1565
+ [Events.SEARCH_INVALID_ANSWER]: (message: Message, answer: string, query: string) => Awaitable;
1566
+ /**
1567
+ * @event
1568
+ * Emitted when DisTube cannot find any results for the query.
1569
+ *
1570
+ * @example
1571
+ * ```ts
1572
+ * distube.on("searchNoResult", (message, query) => message.channel.send(`No result found for ${query}!`));
1573
+ * ```ts
1574
+ *
1575
+ * @param message - The user message called play method
1576
+ * @param query - The search query
1577
+ */
1578
+ [Events.SEARCH_NO_RESULT]: (message: Message, query: string) => Awaitable;
1579
+ /**
1580
+ * @event
1581
+ * Emitted when {@link DisTubeOptions | DisTubeOptions.searchSongs} bigger than 0,
1582
+ * and song param of {@link DisTube#play} is invalid url. DisTube will wait for
1583
+ * user's next message to choose a song manually. <info>{@link
1584
+ * https://support.google.com/youtube/answer/7354993 | Safe search} is enabled if
1585
+ * {@link DisTubeOptions}.nsfw is disabled and the message's channel is not a nsfw
1586
+ * channel.</info>
1587
+ *
1588
+ * @example
1589
+ * ```ts
1590
+ * // DisTubeOptions.searchSongs > 0
1591
+ * distube.on("searchResult", (message, results) => {
1592
+ * message.channel.send(`**Choose an option from below**\n${
1593
+ * results.map((song, i) => `**${i + 1}**. ${song.name} - \`${song.formattedDuration}\``).join("\n")
1594
+ * }\n*Enter anything else or wait 60 seconds to cancel*`);
1595
+ * });
1596
+ * ```ts
1597
+ *
1598
+ * @param message - The user message called play method
1599
+ * @param results - Searched results
1600
+ * @param query - The search query
1601
+ */
1602
+ [Events.SEARCH_RESULT]: (message: Message, results: SearchResult[], query: string) => Awaitable;
1603
+ }
1390
1604
  /**
1391
1605
  * DisTube class
1392
- * @extends EventEmitter
1393
1606
  */
1394
1607
  declare class DisTube extends TypedEmitter<TypedDisTubeEvents> {
1395
1608
  #private;
@@ -1402,17 +1615,17 @@ declare class DisTube extends TypedEmitter<TypedDisTubeEvents> {
1402
1615
  readonly customPlugins: CustomPlugin[];
1403
1616
  readonly filters: Filters;
1404
1617
  /**
1405
- * @deprecated Use `youtubeCookie: Cookie[]` instead. Guide: {@link https://distube.js.org/#/docs/DisTube/main/general/cookie YouTube Cookies}
1618
+ * @deprecated Use `youtubeCookie: Cookie[]` instead. Guide: {@link
1619
+ * https://distube.js.org/#/docs/DisTube/main/general/cookie | YouTube Cookies}
1406
1620
  */
1407
1621
  constructor(client: Client, otp: DisTubeOptions & {
1408
1622
  youtubeCookie: string;
1409
1623
  });
1410
1624
  /**
1411
1625
  * Create a new DisTube class.
1412
- * @param {Discord.Client} client Discord.JS client
1413
- * @param {DisTubeOptions} [otp] Custom DisTube options
1414
- * @throws {DisTubeError}
1626
+ *
1415
1627
  * @example
1628
+ * ```ts
1416
1629
  * const Discord = require('discord.js'),
1417
1630
  * DisTube = require('distube'),
1418
1631
  * client = new Discord.Client();
@@ -1420,24 +1633,25 @@ declare class DisTube extends TypedEmitter<TypedDisTubeEvents> {
1420
1633
  * const distube = new DisTube.default(client, { searchSongs: 10 });
1421
1634
  * // client.DisTube = distube // make it access easily
1422
1635
  * client.login("Your Discord Bot Token")
1636
+ * ```ts
1637
+ *
1638
+ * @throws {@link DisTubeError}
1639
+ *
1640
+ * @param client - Discord.JS client
1641
+ * @param otp - Custom DisTube options
1423
1642
  */
1424
1643
  constructor(client: Client, otp?: DisTubeOptions);
1425
1644
  static get version(): string;
1426
1645
  /**
1427
1646
  * DisTube version
1428
- * @type {string}
1429
1647
  */
1430
1648
  get version(): string;
1431
1649
  /**
1432
- * Play / add a song or playlist from url. Search and play a song if it is not a valid url.
1650
+ * Play / add a song or playlist from url. Search and play a song if it is not a
1651
+ * valid url.
1433
1652
  *
1434
- * @param {Discord.BaseGuildVoiceChannel} voiceChannel The channel will be joined if the bot isn't in any channels,
1435
- * the bot will be moved to this channel if {@link DisTubeOptions}.joinNewVoiceChannel is `true`
1436
- * @param {string|Song|SearchResult|Playlist} song URL | Search string |
1437
- * {@link Song} | {@link SearchResult} | {@link Playlist}
1438
- * @param {PlayOptions} [options] Optional options
1439
- * @throws {DisTubeError}
1440
1653
  * @example
1654
+ * ```ts
1441
1655
  * client.on('message', (message) => {
1442
1656
  * if (!message.content.startsWith(config.prefix)) return;
1443
1657
  * const args = message.content.slice(config.prefix.length).trim().split(/ +/g);
@@ -1449,15 +1663,21 @@ declare class DisTube extends TypedEmitter<TypedDisTubeEvents> {
1449
1663
  * message
1450
1664
  * });
1451
1665
  * });
1452
- * @returns {Promise<void>}
1666
+ * ```ts
1667
+ *
1668
+ * @throws {@link DisTubeError}
1669
+ *
1670
+ * @param voiceChannel - The channel will be joined if the bot isn't in any channels, the bot will be
1671
+ * moved to this channel if {@link DisTubeOptions}.joinNewVoiceChannel is `true`
1672
+ * @param song - URL | Search string | {@link Song} | {@link SearchResult} | {@link Playlist}
1673
+ * @param options - Optional options
1453
1674
  */
1454
1675
  play(voiceChannel: VoiceBasedChannel, song: string | Song | SearchResult | Playlist, options?: PlayOptions): Promise<void>;
1455
1676
  /**
1456
1677
  * Create a custom playlist
1457
- * @returns {Promise<Playlist>}
1458
- * @param {Array<string|Song|SearchResult>} songs Array of url, Song or SearchResult
1459
- * @param {CustomPlaylistOptions} [options] Optional options
1678
+ *
1460
1679
  * @example
1680
+ * ```ts
1461
1681
  * const songs = ["https://www.youtube.com/watch?v=xxx", "https://www.youtube.com/watch?v=yyy"];
1462
1682
  * const playlist = await distube.createCustomPlaylist(songs, {
1463
1683
  * member: message.member,
@@ -1465,6 +1685,10 @@ declare class DisTube extends TypedEmitter<TypedDisTubeEvents> {
1465
1685
  * parallel: true
1466
1686
  * });
1467
1687
  * distube.play(voiceChannel, playlist, { ... });
1688
+ * ```ts
1689
+ *
1690
+ * @param songs - Array of url, Song or SearchResult
1691
+ * @param options - Optional options
1468
1692
  */
1469
1693
  createCustomPlaylist(songs: (string | Song | SearchResult)[], options?: CustomPlaylistOptions): Promise<Playlist>;
1470
1694
  search(string: string, options?: {
@@ -1487,10 +1711,9 @@ declare class DisTube extends TypedEmitter<TypedDisTubeEvents> {
1487
1711
  }): Promise<Array<SearchResult>>;
1488
1712
  /**
1489
1713
  * Get the guild queue
1490
- * @param {GuildIdResolvable} guild The type can be resolved to give a {@link Queue}
1491
- * @returns {Queue?}
1492
- * @throws {Error}
1714
+ *
1493
1715
  * @example
1716
+ * ```ts
1494
1717
  * client.on('message', (message) => {
1495
1718
  * if (!message.content.startsWith(config.prefix)) return;
1496
1719
  * const args = message.content.slice(config.prefix.length).trim().split(/ +/g);
@@ -1502,28 +1725,32 @@ declare class DisTube extends TypedEmitter<TypedDisTubeEvents> {
1502
1725
  * ).join("\n"));
1503
1726
  * }
1504
1727
  * });
1728
+ * ```ts
1729
+ *
1730
+ * @param guild - The type can be resolved to give a {@link Queue}
1505
1731
  */
1506
1732
  getQueue(guild: GuildIdResolvable): Queue | undefined;
1507
1733
  /**
1508
1734
  * Pause the guild stream
1509
- * @param {GuildIdResolvable} guild The type can be resolved to give a {@link Queue}
1510
- * @returns {Queue} The guild queue
1511
- * @throws {Error}
1735
+ *
1736
+ * @param guild - The type can be resolved to give a {@link Queue}
1737
+ *
1738
+ * @returns The guild queue
1512
1739
  */
1513
1740
  pause(guild: GuildIdResolvable): Queue;
1514
1741
  /**
1515
1742
  * Resume the guild stream
1516
- * @param {GuildIdResolvable} guild The type can be resolved to give a {@link Queue}
1517
- * @returns {Queue} The guild queue
1518
- * @throws {Error}
1743
+ *
1744
+ * @param guild - The type can be resolved to give a {@link Queue}
1745
+ *
1746
+ * @returns The guild queue
1519
1747
  */
1520
1748
  resume(guild: GuildIdResolvable): Queue;
1521
1749
  /**
1522
1750
  * Stop the guild stream
1523
- * @param {GuildIdResolvable} guild The type can be resolved to give a {@link Queue}
1524
- * @returns {Promise<void>}
1525
- * @throws {Error}
1751
+ *
1526
1752
  * @example
1753
+ * ```ts
1527
1754
  * client.on('message', (message) => {
1528
1755
  * if (!message.content.startsWith(config.prefix)) return;
1529
1756
  * const args = message.content.slice(config.prefix.length).trim().split(/ +/g);
@@ -1533,15 +1760,16 @@ declare class DisTube extends TypedEmitter<TypedDisTubeEvents> {
1533
1760
  * message.channel.send("Stopped the queue!");
1534
1761
  * }
1535
1762
  * });
1763
+ * ```ts
1764
+ *
1765
+ * @param guild - The type can be resolved to give a {@link Queue}
1536
1766
  */
1537
1767
  stop(guild: GuildIdResolvable): Promise<void>;
1538
1768
  /**
1539
1769
  * Set the guild stream's volume
1540
- * @param {GuildIdResolvable} guild The type can be resolved to give a {@link Queue}
1541
- * @param {number} percent The percentage of volume you want to set
1542
- * @returns {Queue} The guild queue
1543
- * @throws {Error}
1770
+ *
1544
1771
  * @example
1772
+ * ```ts
1545
1773
  * client.on('message', (message) => {
1546
1774
  * if (!message.content.startsWith(config.prefix)) return;
1547
1775
  * const args = message.content.slice(config.prefix.length).trim().split(/ +/g);
@@ -1549,16 +1777,21 @@ declare class DisTube extends TypedEmitter<TypedDisTubeEvents> {
1549
1777
  * if (command == "volume")
1550
1778
  * distube.setVolume(message, Number(args[0]));
1551
1779
  * });
1780
+ * ```ts
1781
+ *
1782
+ * @param guild - The type can be resolved to give a {@link Queue}
1783
+ * @param percent - The percentage of volume you want to set
1784
+ *
1785
+ * @returns The guild queue
1552
1786
  */
1553
1787
  setVolume(guild: GuildIdResolvable, percent: number): Queue;
1554
1788
  /**
1555
- * Skip the playing song if there is a next song in the queue.
1556
- * <info>If {@link Queue#autoplay} is `true` and there is no up next song,
1557
- * DisTube will add and play a related song.</info>
1558
- * @param {GuildIdResolvable} guild The type can be resolved to give a {@link Queue}
1559
- * @returns {Promise<Song>} The new Song will be played
1560
- * @throws {Error}
1789
+ * Skip the playing song if there is a next song in the queue. <info>If {@link
1790
+ * Queue#autoplay} is `true` and there is no up next song, DisTube will add and
1791
+ * play a related song.</info>
1792
+ *
1561
1793
  * @example
1794
+ * ```ts
1562
1795
  * client.on('message', (message) => {
1563
1796
  * if (!message.content.startsWith(config.prefix)) return;
1564
1797
  * const args = message.content.slice(config.prefix.length).trim().split(/ +/g);
@@ -1566,14 +1799,18 @@ declare class DisTube extends TypedEmitter<TypedDisTubeEvents> {
1566
1799
  * if (command == "skip")
1567
1800
  * distube.skip(message);
1568
1801
  * });
1802
+ * ```ts
1803
+ *
1804
+ * @param guild - The type can be resolved to give a {@link Queue}
1805
+ *
1806
+ * @returns The new Song will be played
1569
1807
  */
1570
1808
  skip(guild: GuildIdResolvable): Promise<Song>;
1571
1809
  /**
1572
1810
  * Play the previous song
1573
- * @param {GuildIdResolvable} guild The type can be resolved to give a {@link Queue}
1574
- * @returns {Promise<Song>} The new Song will be played
1575
- * @throws {Error}
1811
+ *
1576
1812
  * @example
1813
+ * ```ts
1577
1814
  * client.on('message', (message) => {
1578
1815
  * if (!message.content.startsWith(config.prefix)) return;
1579
1816
  * const args = message.content.slice(config.prefix.length).trim().split(/ +/g);
@@ -1581,13 +1818,18 @@ declare class DisTube extends TypedEmitter<TypedDisTubeEvents> {
1581
1818
  * if (command == "previous")
1582
1819
  * distube.previous(message);
1583
1820
  * });
1821
+ * ```ts
1822
+ *
1823
+ * @param guild - The type can be resolved to give a {@link Queue}
1824
+ *
1825
+ * @returns The new Song will be played
1584
1826
  */
1585
1827
  previous(guild: GuildIdResolvable): Promise<Song>;
1586
1828
  /**
1587
1829
  * Shuffle the guild queue songs
1588
- * @param {GuildIdResolvable} guild The type can be resolved to give a {@link Queue}
1589
- * @returns {Promise<Queue>} The guild queue
1830
+ *
1590
1831
  * @example
1832
+ * ```ts
1591
1833
  * client.on('message', (message) => {
1592
1834
  * if (!message.content.startsWith(config.prefix)) return;
1593
1835
  * const args = message.content.slice(config.prefix.length).trim().split(/ +/g);
@@ -1595,17 +1837,19 @@ declare class DisTube extends TypedEmitter<TypedDisTubeEvents> {
1595
1837
  * if (command == "shuffle")
1596
1838
  * distube.shuffle(message);
1597
1839
  * });
1840
+ * ```ts
1841
+ *
1842
+ * @param guild - The type can be resolved to give a {@link Queue}
1843
+ *
1844
+ * @returns The guild queue
1598
1845
  */
1599
1846
  shuffle(guild: GuildIdResolvable): Promise<Queue>;
1600
1847
  /**
1601
- * Jump to the song number in the queue.
1602
- * The next one is 1, 2,...
1603
- * The previous one is -1, -2,...
1604
- * @param {GuildIdResolvable} guild The type can be resolved to give a {@link Queue}
1605
- * @param {number} num The song number to play
1606
- * @returns {Promise<Song>} The new Song will be played
1607
- * @throws {Error} if `num` is invalid number (0 < num < {@link Queue#songs}.length)
1848
+ * Jump to the song number in the queue. The next one is 1, 2,... The previous one
1849
+ * is -1, -2,...
1850
+ *
1608
1851
  * @example
1852
+ * ```ts
1609
1853
  * client.on('message', (message) => {
1610
1854
  * if (!message.content.startsWith(config.prefix)) return;
1611
1855
  * const args = message.content.slice(config.prefix.length).trim().split(/ +/g);
@@ -1614,15 +1858,20 @@ declare class DisTube extends TypedEmitter<TypedDisTubeEvents> {
1614
1858
  * distube.jump(message, parseInt(args[0]))
1615
1859
  * .catch(err => message.channel.send("Invalid song number."));
1616
1860
  * });
1861
+ * ```ts
1862
+ *
1863
+ * @param guild - The type can be resolved to give a {@link Queue}
1864
+ * @param num - The song number to play
1865
+ *
1866
+ * @returns The new Song will be played
1617
1867
  */
1618
1868
  jump(guild: GuildIdResolvable, num: number): Promise<Song>;
1619
1869
  /**
1620
- * Set the repeat mode of the guild queue.\
1870
+ * Set the repeat mode of the guild queue.
1621
1871
  * Toggle mode `(Disabled -> Song -> Queue -> Disabled ->...)` if `mode` is `undefined`
1622
- * @param {GuildIdResolvable} guild The type can be resolved to give a {@link Queue}
1623
- * @param {RepeatMode?} [mode] The repeat modes (toggle if `undefined`)
1624
- * @returns {RepeatMode} The new repeat mode
1872
+ *
1625
1873
  * @example
1874
+ * ```ts
1626
1875
  * client.on('message', (message) => {
1627
1876
  * if (!message.content.startsWith(config.prefix)) return;
1628
1877
  * const args = message.content.slice(config.prefix.length).trim().split(/ +/g);
@@ -1633,7 +1882,9 @@ declare class DisTube extends TypedEmitter<TypedDisTubeEvents> {
1633
1882
  * message.channel.send("Set repeat mode to `" + mode + "`");
1634
1883
  * }
1635
1884
  * });
1885
+ * ```ts
1636
1886
  * @example
1887
+ * ```ts
1637
1888
  * const { RepeatMode } = require("distube");
1638
1889
  * let mode;
1639
1890
  * switch(distube.setRepeatMode(message, parseInt(args[0]))) {
@@ -1648,14 +1899,19 @@ declare class DisTube extends TypedEmitter<TypedDisTubeEvents> {
1648
1899
  * break;
1649
1900
  * }
1650
1901
  * message.channel.send("Set repeat mode to `" + mode + "`");
1902
+ * ```ts
1903
+ *
1904
+ * @param guild - The type can be resolved to give a {@link Queue}
1905
+ * @param mode - The repeat modes (toggle if `undefined`)
1906
+ *
1907
+ * @returns The new repeat mode
1651
1908
  */
1652
1909
  setRepeatMode(guild: GuildIdResolvable, mode?: number): number;
1653
1910
  /**
1654
1911
  * Toggle autoplay mode
1655
- * @param {GuildIdResolvable} guild The type can be resolved to give a {@link Queue}
1656
- * @returns {boolean} Autoplay mode state
1657
- * @throws {Error}
1912
+ *
1658
1913
  * @example
1914
+ * ```ts
1659
1915
  * client.on('message', (message) => {
1660
1916
  * if (!message.content.startsWith(config.prefix)) return;
1661
1917
  * const args = message.content.slice(config.prefix.length).trim().split(/ +/g);
@@ -1665,20 +1921,26 @@ declare class DisTube extends TypedEmitter<TypedDisTubeEvents> {
1665
1921
  * message.channel.send("Set autoplay mode to `" + (mode ? "On" : "Off") + "`");
1666
1922
  * }
1667
1923
  * });
1924
+ * ```ts
1925
+ *
1926
+ * @param guild - The type can be resolved to give a {@link Queue}
1927
+ *
1928
+ * @returns Autoplay mode state
1668
1929
  */
1669
1930
  toggleAutoplay(guild: GuildIdResolvable): boolean;
1670
1931
  /**
1671
1932
  * Add related song to the queue
1672
- * @param {GuildIdResolvable} guild The type can be resolved to give a {@link Queue}
1673
- * @returns {Promise<Song>} The guild queue
1933
+ *
1934
+ * @param guild - The type can be resolved to give a {@link Queue}
1935
+ *
1936
+ * @returns The guild queue
1674
1937
  */
1675
1938
  addRelatedSong(guild: GuildIdResolvable): Promise<Song>;
1676
1939
  /**
1677
1940
  * Set the playing time to another position
1678
- * @param {GuildIdResolvable} guild The type can be resolved to give a {@link Queue}
1679
- * @param {number} time Time in seconds
1680
- * @returns {Queue} Seeked queue
1941
+ *
1681
1942
  * @example
1943
+ * ```ts
1682
1944
  * client.on('message', message => {
1683
1945
  * if (!message.content.startsWith(config.prefix)) return;
1684
1946
  * const args = message.content.slice(config.prefix.length).trim().split(/ +/g);
@@ -1686,15 +1948,21 @@ declare class DisTube extends TypedEmitter<TypedDisTubeEvents> {
1686
1948
  * if (command = 'seek')
1687
1949
  * distube.seek(message, Number(args[0]));
1688
1950
  * });
1951
+ * ```ts
1952
+ *
1953
+ * @param guild - The type can be resolved to give a {@link Queue}
1954
+ * @param time - Time in seconds
1955
+ *
1956
+ * @returns Seeked queue
1689
1957
  */
1690
1958
  seek(guild: GuildIdResolvable, time: number): Queue;
1691
1959
  /**
1692
1960
  * Emit error event
1693
- * @param {Error} error error
1694
- * @param {Discord.BaseGuildTextChannel} [channel] Text channel where the error is encountered.
1695
- * @private
1961
+ *
1962
+ * @param error - error
1963
+ * @param channel - Text channel where the error is encountered.
1696
1964
  */
1697
1965
  emitError(error: Error, channel?: GuildTextBasedChannel): void;
1698
1966
  }
1699
1967
 
1700
- export { Awaitable, BaseManager, Chapter, CustomPlaylistOptions, CustomPlugin, DirectLinkPlugin, DisTube, DisTubeBase, DisTubeError, DisTubeEvents, DisTubeHandler, DisTubeOptions, DisTubeStream, DisTubeVoice, DisTubeVoiceEvents, DisTubeVoiceManager, Events, ExtractorPlugin, Filter, FilterManager, FilterResolvable, Filters, GuildIdManager, GuildIdResolvable, Options, OtherSongInfo, PlayHandlerOptions, PlayOptions, Playlist, PlaylistInfo, Plugin, PluginType, Queue, QueueManager, RelatedSong, RepeatMode, ResolveOptions, ResolvePlaylistOptions, SearchResult, SearchResultPlaylist, SearchResultType, SearchResultVideo, Song, StreamType, TaskQueue, TypedDisTubeEvents, checkIntents, checkInvalidKey, chooseBestVideoFormat, DisTube as default, defaultFilters, defaultOptions, formatDuration, isClientInstance, isGuildInstance, isMemberInstance, isMessageInstance, isNsfwChannel, isObject, isRecord, isSnowflake, isSupportedVoiceChannel, isTextChannelInstance, isTruthy, isURL, isVoiceChannelEmpty, objectKeys, parseNumber, resolveGuildId, toSecond, version };
1968
+ export { type Awaitable, BaseManager, type Chapter, type CustomPlaylistOptions, CustomPlugin, DirectLinkPlugin, DisTube, DisTubeBase, DisTubeError, type DisTubeEvents, DisTubeHandler, type DisTubeOptions, DisTubeStream, DisTubeVoice, type DisTubeVoiceEvents, DisTubeVoiceManager, Events, ExtractorPlugin, type FFmpegOptions, type Filter, FilterManager, type FilterResolvable, type Filters, GuildIdManager, type GuildIdResolvable, Options, type OtherSongInfo, type PlayHandlerOptions, type PlayOptions, Playlist, type PlaylistInfo, Plugin, PluginType, Queue, QueueManager, type RelatedSong, RepeatMode, type ResolveOptions, type ResolvePlaylistOptions, type SearchResult, SearchResultPlaylist, SearchResultType, SearchResultVideo, Song, StreamType, TaskQueue, type TypedDisTubeEvents, checkIntents, checkInvalidKey, chooseBestVideoFormat, DisTube as default, defaultFilters, defaultOptions, formatDuration, isClientInstance, isGuildInstance, isMemberInstance, isMessageInstance, isNsfwChannel, isObject, isRecord, isSnowflake, isSupportedVoiceChannel, isTextChannelInstance, isTruthy, isURL, isVoiceChannelEmpty, objectKeys, parseNumber, resolveGuildId, toSecond, version };