hoshimi 0.3.3 → 0.3.5
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.mts +2079 -1957
- package/dist/index.d.ts +2079 -1957
- package/dist/index.js +256 -111
- package/dist/index.mjs +256 -111
- package/package.json +9 -1
package/dist/index.mjs
CHANGED
|
@@ -98,6 +98,7 @@ var Events = /* @__PURE__ */ ((Events2) => {
|
|
|
98
98
|
Events2["PlayerCreate"] = "playerCreate";
|
|
99
99
|
Events2["PlayerUpdate"] = "playerUpdate";
|
|
100
100
|
Events2["PlayerDestroy"] = "playerDestroy";
|
|
101
|
+
Events2["PlayerError"] = "playerError";
|
|
101
102
|
Events2["TrackStart"] = "trackStart";
|
|
102
103
|
Events2["TrackEnd"] = "trackEnd";
|
|
103
104
|
Events2["TrackStuck"] = "trackStuck";
|
|
@@ -117,6 +118,8 @@ var DestroyReasons = /* @__PURE__ */ ((DestroyReasons2) => {
|
|
|
117
118
|
DestroyReasons2["NodeDisconnected"] = "Player-NodeDisconnected";
|
|
118
119
|
DestroyReasons2["NodeDestroy"] = "Player-NodeDestroy";
|
|
119
120
|
DestroyReasons2["VoiceChannelDeleted"] = "Player-VoiceChannelDeleted";
|
|
121
|
+
DestroyReasons2["VoiceChannelLeft"] = "Player-VoiceChannelLeft";
|
|
122
|
+
DestroyReasons2["ReconnectFailed"] = "Player-ReconnectFailed";
|
|
120
123
|
return DestroyReasons2;
|
|
121
124
|
})(DestroyReasons || {});
|
|
122
125
|
|
|
@@ -304,7 +307,7 @@ var Track = class {
|
|
|
304
307
|
pluginInfo;
|
|
305
308
|
/**
|
|
306
309
|
* The track user data.
|
|
307
|
-
* @type {
|
|
310
|
+
* @type {TrackUserData}
|
|
308
311
|
*/
|
|
309
312
|
userData;
|
|
310
313
|
/**
|
|
@@ -374,7 +377,7 @@ var UnresolvedTrack = class {
|
|
|
374
377
|
pluginInfo;
|
|
375
378
|
/**
|
|
376
379
|
* The track user data.
|
|
377
|
-
* @type {
|
|
380
|
+
* @type {TrackUserData | undefined}
|
|
378
381
|
*/
|
|
379
382
|
userData;
|
|
380
383
|
/**
|
|
@@ -402,7 +405,7 @@ var UnresolvedTrack = class {
|
|
|
402
405
|
constructor(track, requester) {
|
|
403
406
|
this.info = track.info;
|
|
404
407
|
this.encoded = track.encoded;
|
|
405
|
-
this.requester = requester;
|
|
408
|
+
this.requester = requester ?? {};
|
|
406
409
|
this.pluginInfo = track.pluginInfo;
|
|
407
410
|
this.userData = track.userData ?? {};
|
|
408
411
|
}
|
|
@@ -464,12 +467,20 @@ var UnresolvedTrack = class {
|
|
|
464
467
|
// package.json
|
|
465
468
|
var package_default = {
|
|
466
469
|
name: "hoshimi",
|
|
467
|
-
version: "0.3.
|
|
470
|
+
version: "0.3.5",
|
|
468
471
|
description: "A lavalink@v4 client easy to use, up-to-date and all ears.",
|
|
469
472
|
main: "./dist/index.js",
|
|
470
473
|
module: "./dist/index.mjs",
|
|
471
474
|
types: "./dist/index.d.ts",
|
|
472
|
-
packageManager: "pnpm@10.
|
|
475
|
+
packageManager: "pnpm@10.27.0+sha512.72d699da16b1179c14ba9e64dc71c9a40988cbdc65c264cb0e489db7de917f20dcf4d64d8723625f2969ba52d4b7e2a1170682d9ac2a5dcaeaab732b7e16f04a",
|
|
476
|
+
exports: {
|
|
477
|
+
".": {
|
|
478
|
+
types: "./dist/index.d.ts",
|
|
479
|
+
require: "./dist/index.js",
|
|
480
|
+
import: "./dist/index.mjs",
|
|
481
|
+
default: "./dist/index.js"
|
|
482
|
+
}
|
|
483
|
+
},
|
|
473
484
|
files: [
|
|
474
485
|
"dist"
|
|
475
486
|
],
|
|
@@ -505,8 +516,8 @@ var package_default = {
|
|
|
505
516
|
author: "Ganyu Studios",
|
|
506
517
|
license: "MIT",
|
|
507
518
|
devDependencies: {
|
|
508
|
-
"@biomejs/biome": "^2.3.
|
|
509
|
-
"@types/node": "^25.0.
|
|
519
|
+
"@biomejs/biome": "^2.3.11",
|
|
520
|
+
"@types/node": "^25.0.3",
|
|
510
521
|
"@types/ws": "^8.18.1",
|
|
511
522
|
husky: "^9.1.7",
|
|
512
523
|
"lint-staged": "^16.2.7",
|
|
@@ -694,7 +705,7 @@ function validateManagerOptions(options) {
|
|
|
694
705
|
throw new OptionError("The manager option 'options.nodes' must be a valid array of nodes and atleast one valid node.");
|
|
695
706
|
if (typeof options.sendPayload !== "function")
|
|
696
707
|
throw new OptionError("The manager option 'options.sendPayload' must be a vaid function.");
|
|
697
|
-
if (typeof options.queueOptions !== "undefined" && typeof options.queueOptions.
|
|
708
|
+
if (typeof options.queueOptions !== "undefined" && typeof options.queueOptions.maxHistory !== "number")
|
|
698
709
|
throw new OptionError("The manager option 'options.queueOptions.maxPreviousTracks' must be a number.");
|
|
699
710
|
if (typeof options.queueOptions !== "undefined" && typeof options.queueOptions.autoplayFn !== "function")
|
|
700
711
|
throw new OptionError("The manager option 'options.queueOptions.autoplayFn' must be a function.");
|
|
@@ -755,6 +766,11 @@ function validatePlayerData(data) {
|
|
|
755
766
|
player.lastPosition = data.playerOptions.position;
|
|
756
767
|
player.lastPositionUpdate = Date.now();
|
|
757
768
|
}
|
|
769
|
+
if (typeof data.playerOptions.filters === "object") {
|
|
770
|
+
const timescale = Object.freeze({ ...player.filterManager.data.timescale });
|
|
771
|
+
Object.assign(player.filterManager.data, data.playerOptions.filters);
|
|
772
|
+
player.filterManager.check(timescale);
|
|
773
|
+
}
|
|
758
774
|
}
|
|
759
775
|
}
|
|
760
776
|
function validateNodePlugins(node, plugins) {
|
|
@@ -779,9 +795,11 @@ function validateEngine(type) {
|
|
|
779
795
|
}
|
|
780
796
|
function validateTrack(player, track) {
|
|
781
797
|
if (!track) return Promise.resolve(null);
|
|
782
|
-
|
|
798
|
+
const requesterFn2 = player.manager.options.playerOptions.requesterFn;
|
|
799
|
+
if (isTrack(track)) return Promise.resolve(new Track(track, requesterFn2(track.requester)));
|
|
783
800
|
if (!isUnresolvedTrack(track)) throw new ResolveError("The track is not a valid unresolved track.");
|
|
784
|
-
if (!track.resolve || typeof track.resolve !== "function")
|
|
801
|
+
if (!track.resolve || typeof track.resolve !== "function")
|
|
802
|
+
return new UnresolvedTrack(track, requesterFn2(track.requester)).resolve(player);
|
|
785
803
|
return track.resolve(player);
|
|
786
804
|
}
|
|
787
805
|
var isTrack = (track) => {
|
|
@@ -813,6 +831,9 @@ function stringify(value, space) {
|
|
|
813
831
|
space
|
|
814
832
|
);
|
|
815
833
|
}
|
|
834
|
+
function requesterFn(requester) {
|
|
835
|
+
return requester;
|
|
836
|
+
}
|
|
816
837
|
function isNode(options) {
|
|
817
838
|
return typeof options.host === "string" && typeof options.port === "number" && typeof options.password === "string" && (typeof options.id === "string" || typeof options.id === "undefined") && (typeof options.secure === "boolean" || typeof options.secure === "undefined") && (typeof options.sessionId === "string" || typeof options.sessionId === "undefined") && (typeof options.retryAmount === "number" || typeof options.retryAmount === "undefined") && (typeof options.retryDelay === "number" || typeof options.retryDelay === "undefined");
|
|
818
839
|
}
|
|
@@ -1311,8 +1332,8 @@ async function onEnd() {
|
|
|
1311
1332
|
(x) => x.info.identifier === this.queue.current.info.identifier && x.info.title === this.queue.current.info.title
|
|
1312
1333
|
)) {
|
|
1313
1334
|
this.queue.history.unshift(this.queue.current);
|
|
1314
|
-
if (this.queue.history.length > this.manager.options.queueOptions.
|
|
1315
|
-
this.queue.history.splice(this.manager.options.queueOptions.
|
|
1335
|
+
if (this.queue.history.length > this.manager.options.queueOptions.maxHistory)
|
|
1336
|
+
this.queue.history.splice(this.manager.options.queueOptions.maxHistory, this.queue.history.length);
|
|
1316
1337
|
await this.queue.utils.save();
|
|
1317
1338
|
this.manager.emit(
|
|
1318
1339
|
"debug" /* Debug */,
|
|
@@ -1322,7 +1343,7 @@ async function onEnd() {
|
|
|
1322
1343
|
}
|
|
1323
1344
|
if (this.loop === 1 /* Track */ && this.queue.current) this.queue.unshift(this.queue.current);
|
|
1324
1345
|
if (this.loop === 2 /* Queue */ && this.queue.current) this.queue.add(this.queue.current);
|
|
1325
|
-
if (!this.queue.current) this.queue.current = await validateTrack(this, this.queue.shift());
|
|
1346
|
+
if (!this.queue.current) this.queue.current = await validateTrack(this, await this.queue.shift());
|
|
1326
1347
|
await this.queue.utils.save();
|
|
1327
1348
|
return;
|
|
1328
1349
|
}
|
|
@@ -1469,6 +1490,43 @@ async function socketClosed(payload) {
|
|
|
1469
1490
|
`[Player] -> [Socket] The socket has closed: ${this.guildId} | Payload: ${stringify(payload)}`
|
|
1470
1491
|
);
|
|
1471
1492
|
}
|
|
1493
|
+
async function resumeByLibrary(players) {
|
|
1494
|
+
this.nodeManager.manager.emit("debug" /* Debug */, 2 /* Node */, `[Socket] -> [${this.id}]: Resuming session by library...`);
|
|
1495
|
+
for (const player of players) {
|
|
1496
|
+
try {
|
|
1497
|
+
if (!player.playing && !player.paused && !player.queue.totalSize) {
|
|
1498
|
+
this.nodeManager.manager.emit(
|
|
1499
|
+
"debug" /* Debug */,
|
|
1500
|
+
2 /* Node */,
|
|
1501
|
+
`[Player] -> [Resume] Destroyed player for guild ${player.guildId} due to empty queue.`
|
|
1502
|
+
);
|
|
1503
|
+
await player.destroy();
|
|
1504
|
+
return;
|
|
1505
|
+
}
|
|
1506
|
+
const track = player.queue.current;
|
|
1507
|
+
await player.node.updatePlayer({
|
|
1508
|
+
guildId: player.guildId,
|
|
1509
|
+
playerOptions: { voice: player.voice }
|
|
1510
|
+
});
|
|
1511
|
+
await player.connect();
|
|
1512
|
+
await player.queue.utils.sync(false, true);
|
|
1513
|
+
if (track)
|
|
1514
|
+
await player.play({
|
|
1515
|
+
track,
|
|
1516
|
+
noReplace: false,
|
|
1517
|
+
position: player.lastPosition,
|
|
1518
|
+
paused: player.paused
|
|
1519
|
+
});
|
|
1520
|
+
} catch (error) {
|
|
1521
|
+
this.nodeManager.manager.emit("nodeError" /* NodeError */, this, error);
|
|
1522
|
+
}
|
|
1523
|
+
this.nodeManager.manager.emit(
|
|
1524
|
+
"debug" /* Debug */,
|
|
1525
|
+
2 /* Node */,
|
|
1526
|
+
`[Player] -> [Resume] Resumed player for guild ${player.guildId} using the library.`
|
|
1527
|
+
);
|
|
1528
|
+
}
|
|
1529
|
+
}
|
|
1472
1530
|
|
|
1473
1531
|
// src/util/events/websocket.ts
|
|
1474
1532
|
function onOpen(res) {
|
|
@@ -1541,34 +1599,37 @@ async function onMessage(message) {
|
|
|
1541
1599
|
this.sessionId = payload.sessionId;
|
|
1542
1600
|
this.session.resuming = payload.resumed;
|
|
1543
1601
|
if (payload.resumed) {
|
|
1544
|
-
const
|
|
1602
|
+
const players2 = await this.rest.request({
|
|
1545
1603
|
endpoint: `/sessions/${payload.sessionId}/players`
|
|
1546
1604
|
}) ?? [];
|
|
1547
1605
|
const timeout = this.nodeManager.manager.options.nodeOptions.resumeTimeout;
|
|
1548
|
-
this.nodeManager.manager.emit("nodeResumed" /* NodeResumed */, this,
|
|
1606
|
+
this.nodeManager.manager.emit("nodeResumed" /* NodeResumed */, this, players2, payload);
|
|
1549
1607
|
this.nodeManager.manager.emit(
|
|
1550
1608
|
"debug" /* Debug */,
|
|
1551
1609
|
2 /* Node */,
|
|
1552
|
-
`[Socket] <- [${this.id}]: Resumed session. | Session id: ${payload.sessionId} | Players: ${
|
|
1610
|
+
`[Socket] <- [${this.id}]: Resumed session. | Session id: ${payload.sessionId} | Players: ${players2.length} | Resumed: ${payload.resumed} | Timeout: ${timeout}ms`
|
|
1553
1611
|
);
|
|
1554
1612
|
}
|
|
1613
|
+
const players = this.nodeManager.manager.players.filter((p) => p.node.id === this.id);
|
|
1614
|
+
const isLibrary = this.nodeManager.manager.options.nodeOptions.resumeByLibrary;
|
|
1615
|
+
if (!payload.resumed && isLibrary && players.length) await resumeByLibrary.call(this, players);
|
|
1555
1616
|
this.info = await this.rest.request({ endpoint: "/info" });
|
|
1556
|
-
this.nodeManager.manager.emit(
|
|
1557
|
-
"debug" /* Debug */,
|
|
1558
|
-
2 /* Node */,
|
|
1559
|
-
`[Socket] <- [${this.id}]: Received ready event. | Session id: ${payload.sessionId} | Resumed: ${payload.resumed}`
|
|
1560
|
-
);
|
|
1561
|
-
this.nodeManager.manager.emit("nodeReady" /* NodeReady */, this, this.retryAmount, payload);
|
|
1562
1617
|
const isResumable = this.nodeManager.manager.options.nodeOptions.resumable;
|
|
1563
1618
|
if (isResumable) {
|
|
1564
1619
|
const timeout = this.nodeManager.manager.options.nodeOptions.resumeTimeout;
|
|
1565
1620
|
this.nodeManager.manager.emit(
|
|
1566
1621
|
"debug" /* Debug */,
|
|
1567
1622
|
2 /* Node */,
|
|
1568
|
-
`[Socket] -> [${this.id}]:
|
|
1623
|
+
`[Socket] -> [${this.id}]: Setting timeout to resume session. | Timeout: ${timeout}ms`
|
|
1569
1624
|
);
|
|
1570
1625
|
await this.updateSession(isResumable, timeout);
|
|
1571
1626
|
}
|
|
1627
|
+
this.nodeManager.manager.emit(
|
|
1628
|
+
"debug" /* Debug */,
|
|
1629
|
+
2 /* Node */,
|
|
1630
|
+
`[Socket] <- [${this.id}]: Received ready event. | Session id: ${payload.sessionId} | Resumed: ${payload.resumed}`
|
|
1631
|
+
);
|
|
1632
|
+
this.nodeManager.manager.emit("nodeReady" /* NodeReady */, this, this.retryAmount, payload);
|
|
1572
1633
|
}
|
|
1573
1634
|
break;
|
|
1574
1635
|
case "event" /* Event */: {
|
|
@@ -3295,15 +3356,7 @@ var Player = class {
|
|
|
3295
3356
|
*/
|
|
3296
3357
|
async disconnect() {
|
|
3297
3358
|
if (!this.voiceId) return this;
|
|
3298
|
-
await this.
|
|
3299
|
-
op: 4,
|
|
3300
|
-
d: {
|
|
3301
|
-
guild_id: this.guildId,
|
|
3302
|
-
channel_id: null,
|
|
3303
|
-
self_deaf: this.selfDeaf,
|
|
3304
|
-
self_mute: this.selfMute
|
|
3305
|
-
}
|
|
3306
|
-
});
|
|
3359
|
+
await this.setVoice({ voiceId: null });
|
|
3307
3360
|
this.manager.emit("debug" /* Debug */, 3 /* Player */, `[Player] -> [Disconnect] Player disconnected for guild: ${this.guildId}`);
|
|
3308
3361
|
this.connected = false;
|
|
3309
3362
|
return this;
|
|
@@ -3349,7 +3402,7 @@ var Player = class {
|
|
|
3349
3402
|
async play(options = {}) {
|
|
3350
3403
|
if (typeof options !== "object") throw new PlayerError("The play options must be an object.");
|
|
3351
3404
|
if (options.track) this.queue.current = await validateTrack(this, options.track);
|
|
3352
|
-
else if (!this.queue.current) this.queue.current = await validateTrack(this, this.queue.shift());
|
|
3405
|
+
else if (!this.queue.current) this.queue.current = await validateTrack(this, await this.queue.shift());
|
|
3353
3406
|
if (!this.queue.current) throw new PlayerError("No track to play.");
|
|
3354
3407
|
if (!isTrack(this.queue.current) && !isUnresolvedTrack(this.queue.current))
|
|
3355
3408
|
throw new PlayerError("The track must be a valid Track or UnresolvedTrack instance.");
|
|
@@ -3382,15 +3435,7 @@ var Player = class {
|
|
|
3382
3435
|
*/
|
|
3383
3436
|
async connect() {
|
|
3384
3437
|
if (!this.voiceId) return this;
|
|
3385
|
-
await this.
|
|
3386
|
-
op: 4,
|
|
3387
|
-
d: {
|
|
3388
|
-
guild_id: this.guildId,
|
|
3389
|
-
channel_id: this.voiceId,
|
|
3390
|
-
self_deaf: this.selfDeaf,
|
|
3391
|
-
self_mute: this.selfMute
|
|
3392
|
-
}
|
|
3393
|
-
});
|
|
3438
|
+
await this.setVoice();
|
|
3394
3439
|
this.manager.emit("debug" /* Debug */, 3 /* Player */, `[Player] -> [Connect] Player connected for guild: ${this.guildId}`);
|
|
3395
3440
|
this.connected = true;
|
|
3396
3441
|
return this;
|
|
@@ -3489,7 +3534,7 @@ var Player = class {
|
|
|
3489
3534
|
}
|
|
3490
3535
|
/**
|
|
3491
3536
|
* Set the voice of the player.
|
|
3492
|
-
* @param {
|
|
3537
|
+
* @param {NullableVoiceChannelUpdate} options The voice state to set.
|
|
3493
3538
|
* @returns {Promise<void>}
|
|
3494
3539
|
* @example
|
|
3495
3540
|
* ```ts
|
|
@@ -3497,27 +3542,17 @@ var Player = class {
|
|
|
3497
3542
|
* player.setVoice({ voiceId: "newVoiceId" });
|
|
3498
3543
|
* ```
|
|
3499
3544
|
*/
|
|
3500
|
-
async setVoice(
|
|
3501
|
-
|
|
3502
|
-
|
|
3503
|
-
|
|
3504
|
-
this.options.voiceId = voice.voiceId;
|
|
3505
|
-
}
|
|
3506
|
-
if (voice.selfDeaf) {
|
|
3507
|
-
this.selfDeaf = voice.selfDeaf;
|
|
3508
|
-
this.options.selfDeaf = voice.selfDeaf;
|
|
3509
|
-
}
|
|
3510
|
-
if (voice.selfMute) {
|
|
3511
|
-
this.selfMute = voice.selfMute;
|
|
3512
|
-
this.options.selfMute = voice.selfMute;
|
|
3513
|
-
}
|
|
3545
|
+
async setVoice(options = {}) {
|
|
3546
|
+
options.voiceId ??= this.voiceId;
|
|
3547
|
+
options.selfDeaf ??= this.selfDeaf;
|
|
3548
|
+
options.selfMute ??= this.selfMute;
|
|
3514
3549
|
await this.manager.options.sendPayload(this.guildId, {
|
|
3515
3550
|
op: 4,
|
|
3516
3551
|
d: {
|
|
3517
3552
|
guild_id: this.guildId,
|
|
3518
|
-
self_deaf:
|
|
3519
|
-
self_mute:
|
|
3520
|
-
channel_id:
|
|
3553
|
+
self_deaf: options.selfDeaf,
|
|
3554
|
+
self_mute: options.selfMute,
|
|
3555
|
+
channel_id: options.voiceId ?? null
|
|
3521
3556
|
}
|
|
3522
3557
|
});
|
|
3523
3558
|
this.manager.emit(
|
|
@@ -3734,16 +3769,15 @@ var QueueUtils = class {
|
|
|
3734
3769
|
* ```
|
|
3735
3770
|
*/
|
|
3736
3771
|
save() {
|
|
3737
|
-
const max = this.options.
|
|
3772
|
+
const max = this.options.maxHistory;
|
|
3738
3773
|
const length = this.queue.tracks.length;
|
|
3739
|
-
const json = this.queue.toJSON();
|
|
3740
3774
|
if (length > max) this.queue.history.splice(0, length - max);
|
|
3741
3775
|
this.queue.player.manager.emit(
|
|
3742
3776
|
"debug" /* Debug */,
|
|
3743
3777
|
5 /* Queue */,
|
|
3744
|
-
`[Queue] -> [Adapter] Saving queue for ${this.queue.player.guildId} | Object: ${stringify(
|
|
3778
|
+
`[Queue] -> [Adapter] Saving queue for ${this.queue.player.guildId} | Object: ${stringify(this.queue.toJSON())}`
|
|
3745
3779
|
);
|
|
3746
|
-
return this.store.set(this.queue.player.guildId,
|
|
3780
|
+
return this.store.set(this.queue.player.guildId, this.queue.toJSON());
|
|
3747
3781
|
}
|
|
3748
3782
|
/**
|
|
3749
3783
|
*
|
|
@@ -3909,25 +3943,50 @@ var Queue = class {
|
|
|
3909
3943
|
isEmpty() {
|
|
3910
3944
|
return this.size === 0;
|
|
3911
3945
|
}
|
|
3946
|
+
/**
|
|
3947
|
+
*
|
|
3948
|
+
* Build a track from a Lavalink track or unresolved Lavalink track.
|
|
3949
|
+
* @param {LavalinkTrack | UnresolvedLavalinkTrack} track The track to build.
|
|
3950
|
+
* @param {TrackRequester} requester The requester of the track.
|
|
3951
|
+
* @returns {Promise<Track>} The built track.
|
|
3952
|
+
* @example
|
|
3953
|
+
* ```ts
|
|
3954
|
+
* const queue = player.queue;
|
|
3955
|
+
* const lavalinkTrack = {...} // some lavalink track
|
|
3956
|
+
* const track = await queue.build(lavalinkTrack, author);
|
|
3957
|
+
*
|
|
3958
|
+
* console.log(track.info.title); // The title of the track
|
|
3959
|
+
* ```
|
|
3960
|
+
*/
|
|
3961
|
+
async build(track, requester) {
|
|
3962
|
+
const requesterFn2 = this.player.manager.options.playerOptions.requesterFn;
|
|
3963
|
+
if (isUnresolvedTrack(track)) return new UnresolvedTrack(track, requesterFn2(requester)).resolve(this.player);
|
|
3964
|
+
if (isTrack(track)) return new Track(track, requesterFn2(requester));
|
|
3965
|
+
return track;
|
|
3966
|
+
}
|
|
3912
3967
|
/**
|
|
3913
3968
|
*
|
|
3914
3969
|
* Get the previous track of the queue.
|
|
3915
3970
|
* @param {boolean} [remove=false] Whether to remove the track from the previous queue.
|
|
3916
|
-
* @returns {Track | null} The previous track of the queue.
|
|
3971
|
+
* @returns {Promise<Track | null>} The previous track of the queue.
|
|
3917
3972
|
* @example
|
|
3918
3973
|
* ```ts
|
|
3919
3974
|
* const queue = player.queue;
|
|
3920
3975
|
*
|
|
3921
|
-
* console.log(queue.previous()); // null
|
|
3976
|
+
* console.log(await queue.previous()); // null
|
|
3922
3977
|
* queue.add(track);
|
|
3923
3978
|
* queue.add(track2);
|
|
3924
3979
|
*
|
|
3925
|
-
* console.log(queue.previous()); // track
|
|
3926
|
-
* console.log(queue.previous(true)); // track and remove it from the previous tracks
|
|
3980
|
+
* console.log(await queue.previous()); // track
|
|
3981
|
+
* console.log(await queue.previous(true)); // track and remove it from the previous tracks
|
|
3927
3982
|
* ```
|
|
3928
3983
|
*/
|
|
3929
|
-
previous(remove = false) {
|
|
3930
|
-
if (remove)
|
|
3984
|
+
async previous(remove = false) {
|
|
3985
|
+
if (remove) {
|
|
3986
|
+
const track = this.history.shift() ?? null;
|
|
3987
|
+
if (track) await this.utils.save();
|
|
3988
|
+
return track;
|
|
3989
|
+
}
|
|
3931
3990
|
return this.history[0] ?? null;
|
|
3932
3991
|
}
|
|
3933
3992
|
/**
|
|
@@ -3935,94 +3994,98 @@ var Queue = class {
|
|
|
3935
3994
|
* Add a track or tracks to the queue.
|
|
3936
3995
|
* @param {Track | Track[]} track The track or tracks to add.
|
|
3937
3996
|
* @param {number} [position] The position to add the track or tracks.
|
|
3938
|
-
* @returns {this} The queue instance.
|
|
3997
|
+
* @returns {Promise<this>} The queue instance.
|
|
3939
3998
|
* @example
|
|
3940
3999
|
* ```ts
|
|
3941
4000
|
* const queue = player.queue;
|
|
3942
4001
|
*
|
|
3943
4002
|
* console.log(queue.size); // 0
|
|
3944
4003
|
*
|
|
3945
|
-
* queue.add(track);
|
|
4004
|
+
* await queue.add(track);
|
|
3946
4005
|
* console.log(queue.size); // 1
|
|
3947
4006
|
*
|
|
3948
|
-
* queue.add([track1, track2]);
|
|
4007
|
+
* await queue.add([track1, track2]);
|
|
3949
4008
|
* console.log(queue.size); // 3
|
|
3950
4009
|
*
|
|
3951
|
-
* queue.add(track3, 1);
|
|
4010
|
+
* await queue.add(track3, 1);
|
|
3952
4011
|
* console.log(queue.size); // 4
|
|
3953
4012
|
* console.log(queue.tracks); // [track1, track3, track2, track]
|
|
3954
4013
|
* ```
|
|
3955
4014
|
*/
|
|
3956
|
-
add(track, position) {
|
|
4015
|
+
async add(track, position) {
|
|
3957
4016
|
const tracks = Array.isArray(track) ? track : [track];
|
|
3958
4017
|
if (typeof position === "number" && position >= 0 && position < this.tracks.length) return this.splice(position, 0, ...tracks);
|
|
3959
4018
|
this.tracks.push(...tracks);
|
|
3960
4019
|
this.player.manager.emit("queueUpdate" /* QueueUpdate */, this.player, this);
|
|
3961
4020
|
this.player.manager.emit("debug" /* Debug */, 5 /* Queue */, `[Queue] -> [Add] Added ${this.tracks.length} tracks to the queue.`);
|
|
4021
|
+
await this.utils.save();
|
|
3962
4022
|
return this;
|
|
3963
4023
|
}
|
|
3964
4024
|
/**
|
|
3965
4025
|
*
|
|
3966
4026
|
* Get the first track of the queue.
|
|
3967
|
-
* @returns {HoshimiTrack | null} The first track of the queue.
|
|
4027
|
+
* @returns {Promise<HoshimiTrack | null>} The first track of the queue.
|
|
3968
4028
|
* @example
|
|
3969
4029
|
* ```ts
|
|
3970
4030
|
* const queue = player.queue;
|
|
3971
4031
|
*
|
|
3972
|
-
* console.log(queue.shift()); // null
|
|
3973
|
-
* queue.add(track);
|
|
4032
|
+
* console.log(await queue.shift()); // null
|
|
4033
|
+
* await queue.add(track);
|
|
3974
4034
|
*
|
|
3975
|
-
* console.log(queue.shift()); // track
|
|
3976
|
-
* queue.add(track2);
|
|
4035
|
+
* console.log(await queue.shift()); // track
|
|
4036
|
+
* await queue.add(track2);
|
|
3977
4037
|
* ```
|
|
3978
4038
|
*/
|
|
3979
|
-
shift() {
|
|
3980
|
-
|
|
4039
|
+
async shift() {
|
|
4040
|
+
const track = this.tracks.shift() ?? null;
|
|
4041
|
+
if (track) await this.utils.save();
|
|
4042
|
+
return track;
|
|
3981
4043
|
}
|
|
3982
4044
|
/**
|
|
3983
4045
|
*
|
|
3984
4046
|
* Add tracks to the beginning of the queue.
|
|
3985
4047
|
* @param {Track[]} tracks The tracks to add.
|
|
3986
|
-
* @returns {this} The queue instance.
|
|
4048
|
+
* @returns {Promise<this>} The queue instance.
|
|
3987
4049
|
* @example
|
|
3988
4050
|
* ```ts
|
|
3989
4051
|
* const queue = player.queue;
|
|
3990
4052
|
*
|
|
3991
4053
|
* console.log(queue.size); // 0
|
|
3992
|
-
* queue.unshift(track);
|
|
4054
|
+
* await queue.unshift(track);
|
|
3993
4055
|
*
|
|
3994
4056
|
* console.log(queue.size); // 1
|
|
3995
|
-
* queue.unshift(
|
|
4057
|
+
* await queue.unshift(track1, track2);
|
|
3996
4058
|
*
|
|
3997
4059
|
* console.log(queue.size); // 3
|
|
3998
4060
|
* console.log(queue.tracks); // [track1, track2, track]
|
|
3999
4061
|
* ```
|
|
4000
4062
|
*/
|
|
4001
|
-
unshift(...tracks) {
|
|
4063
|
+
async unshift(...tracks) {
|
|
4002
4064
|
this.tracks.unshift(...tracks);
|
|
4003
4065
|
this.player.manager.emit("debug" /* Debug */, 5 /* Queue */, `[Queue] -> [Unshift] Added ${this.tracks.length} tracks to the queue.`);
|
|
4066
|
+
await this.utils.save();
|
|
4004
4067
|
return this;
|
|
4005
4068
|
}
|
|
4006
4069
|
/**
|
|
4007
4070
|
*
|
|
4008
4071
|
* Shuffle the queue.
|
|
4009
|
-
* @returns {this} The queue instance.
|
|
4072
|
+
* @returns {Promise<this>} The queue instance.
|
|
4010
4073
|
* @example
|
|
4011
4074
|
* ```ts
|
|
4012
4075
|
* const queue = player.queue;
|
|
4013
4076
|
*
|
|
4014
4077
|
* console.log(queue.size); // 0
|
|
4015
|
-
* queue.add(track);
|
|
4016
|
-
* queue.add(
|
|
4078
|
+
* await queue.add(track);
|
|
4079
|
+
* await queue.add(track1, track2);
|
|
4017
4080
|
*
|
|
4018
4081
|
* console.log(queue.size); // 3
|
|
4019
4082
|
* console.log(queue.tracks); // [track, track1, track2]
|
|
4020
4083
|
*
|
|
4021
|
-
* queue.shuffle();
|
|
4084
|
+
* await queue.shuffle();
|
|
4022
4085
|
* console.log(queue.tracks); // [track2, track, track1]
|
|
4023
4086
|
* ```
|
|
4024
4087
|
*/
|
|
4025
|
-
shuffle() {
|
|
4088
|
+
async shuffle() {
|
|
4026
4089
|
if (this.size <= 1) return this;
|
|
4027
4090
|
if (this.size === 2) [this.tracks[0], this.tracks[1]] = [this.tracks[1], this.tracks[0]];
|
|
4028
4091
|
else {
|
|
@@ -4033,31 +4096,33 @@ var Queue = class {
|
|
|
4033
4096
|
}
|
|
4034
4097
|
this.player.manager.emit("queueUpdate" /* QueueUpdate */, this.player, this);
|
|
4035
4098
|
this.player.manager.emit("debug" /* Debug */, 5 /* Queue */, "[Queue] -> [Shuffle] Shuffled the queue.");
|
|
4099
|
+
await this.utils.save();
|
|
4036
4100
|
return this;
|
|
4037
4101
|
}
|
|
4038
4102
|
/**
|
|
4039
4103
|
*
|
|
4040
4104
|
* Clear the queue.
|
|
4041
|
-
* @returns {this} The queue instance.
|
|
4105
|
+
* @returns {Promise<this>} The queue instance.
|
|
4042
4106
|
* @example
|
|
4043
4107
|
* ```ts
|
|
4044
4108
|
* const queue = player.queue;
|
|
4045
4109
|
*
|
|
4046
4110
|
* console.log(queue.size); // 0
|
|
4047
|
-
* queue.add(track);
|
|
4048
|
-
* queue.add(
|
|
4111
|
+
* await queue.add(track);
|
|
4112
|
+
* await queue.add(track1, track2);
|
|
4049
4113
|
*
|
|
4050
4114
|
* console.log(queue.size); // 3
|
|
4051
|
-
* queue.clear();
|
|
4115
|
+
* await queue.clear();
|
|
4052
4116
|
* console.log(queue.size); // 0
|
|
4053
4117
|
* ```
|
|
4054
4118
|
*/
|
|
4055
|
-
clear() {
|
|
4119
|
+
async clear() {
|
|
4056
4120
|
this.tracks = [];
|
|
4057
4121
|
this.history = [];
|
|
4058
4122
|
this.current = null;
|
|
4059
4123
|
this.player.manager.emit("queueUpdate" /* QueueUpdate */, this.player, this);
|
|
4060
4124
|
this.player.manager.emit("debug" /* Debug */, 5 /* Queue */, "[Queue] -> [Clear] Cleared the queue.");
|
|
4125
|
+
await this.utils.save();
|
|
4061
4126
|
return this;
|
|
4062
4127
|
}
|
|
4063
4128
|
/**
|
|
@@ -4065,15 +4130,16 @@ var Queue = class {
|
|
|
4065
4130
|
* Move a track to a specific position in the queue.
|
|
4066
4131
|
* @param {Track} track The track to move.
|
|
4067
4132
|
* @param {number} to The position to move.
|
|
4068
|
-
* @returns {this} The queue instance.
|
|
4133
|
+
* @returns {Promise<this>} The queue instance.
|
|
4069
4134
|
*/
|
|
4070
|
-
move(track, to) {
|
|
4135
|
+
async move(track, to) {
|
|
4071
4136
|
const index = this.tracks.indexOf(track);
|
|
4072
4137
|
if (index === -1) return this;
|
|
4073
|
-
this.splice(index, 1);
|
|
4074
|
-
this.add(track, to - 1);
|
|
4138
|
+
await this.splice(index, 1);
|
|
4139
|
+
await this.add(track, to - 1);
|
|
4075
4140
|
this.player.manager.emit("queueUpdate" /* QueueUpdate */, this.player, this);
|
|
4076
4141
|
this.player.manager.emit("debug" /* Debug */, 5 /* Queue */, `[Queue] -> [Move] Moved track ${track.info.title} to position ${to}.`);
|
|
4142
|
+
await this.utils.save();
|
|
4077
4143
|
return this;
|
|
4078
4144
|
}
|
|
4079
4145
|
/**
|
|
@@ -4082,14 +4148,15 @@ var Queue = class {
|
|
|
4082
4148
|
* @param {number} start The start index.
|
|
4083
4149
|
* @param {number} deleteCount The number of tracks to delete.
|
|
4084
4150
|
* @param {Track | Track[]} [tracks] The tracks to add.
|
|
4085
|
-
* @returns {this} The queue instance.
|
|
4151
|
+
* @returns {Promise<this>} The queue instance.
|
|
4086
4152
|
*/
|
|
4087
|
-
splice(start, deleteCount, tracks) {
|
|
4088
|
-
if (!this.size && tracks) this.add(tracks);
|
|
4153
|
+
async splice(start, deleteCount, tracks) {
|
|
4154
|
+
if (!this.size && tracks) await this.add(tracks);
|
|
4089
4155
|
if (tracks) this.tracks.splice(start, deleteCount, ...Array.isArray(tracks) ? tracks : [tracks]);
|
|
4090
4156
|
else this.tracks.splice(start, deleteCount);
|
|
4091
4157
|
this.player.manager.emit("queueUpdate" /* QueueUpdate */, this.player, this);
|
|
4092
4158
|
this.player.manager.emit("debug" /* Debug */, 5 /* Queue */, `[Queue] -> [Splice] Removed ${deleteCount} tracks from the queue.`);
|
|
4159
|
+
await this.utils.save();
|
|
4093
4160
|
return this;
|
|
4094
4161
|
}
|
|
4095
4162
|
/**
|
|
@@ -4098,7 +4165,7 @@ var Queue = class {
|
|
|
4098
4165
|
* @returns {QueueJson} The queue JSON object.
|
|
4099
4166
|
*/
|
|
4100
4167
|
toJSON() {
|
|
4101
|
-
const max = this.player.manager.options.queueOptions.
|
|
4168
|
+
const max = this.player.manager.options.queueOptions.maxHistory;
|
|
4102
4169
|
if (this.history.length > max) this.history.splice(max, this.history.length);
|
|
4103
4170
|
return {
|
|
4104
4171
|
tracks: this.tracks,
|
|
@@ -4264,10 +4331,24 @@ var Hoshimi = class extends EventEmitter {
|
|
|
4264
4331
|
* resumeByLibrary: false,
|
|
4265
4332
|
* },
|
|
4266
4333
|
* queueOptions: {
|
|
4267
|
-
*
|
|
4268
|
-
*
|
|
4269
|
-
*
|
|
4334
|
+
* maxHistory: 25,
|
|
4335
|
+
* autoplayFn: autoplayFn,
|
|
4336
|
+
* autoPlay: false,
|
|
4337
|
+
* storage: new MemoryAdapter(),
|
|
4338
|
+
* requesterFn: defaultRequesterFn,
|
|
4270
4339
|
* },
|
|
4340
|
+
* playerOptions: {
|
|
4341
|
+
* onDisconnect: {
|
|
4342
|
+
* autoDestroy: false,
|
|
4343
|
+
* autoReconnect: false,
|
|
4344
|
+
* autoQueue: false,
|
|
4345
|
+
* },
|
|
4346
|
+
* onError: {
|
|
4347
|
+
* autoDestroy: false,
|
|
4348
|
+
* autoSkip: false,
|
|
4349
|
+
* autoStop: false,
|
|
4350
|
+
* },
|
|
4351
|
+
* },
|
|
4271
4352
|
* });
|
|
4272
4353
|
*
|
|
4273
4354
|
* console.log(manager); // The manager instance
|
|
@@ -4289,11 +4370,24 @@ var Hoshimi = class extends EventEmitter {
|
|
|
4289
4370
|
resumeTimeout: options.nodeOptions?.resumeTimeout ?? 1e4
|
|
4290
4371
|
},
|
|
4291
4372
|
queueOptions: {
|
|
4292
|
-
|
|
4373
|
+
maxHistory: options.queueOptions?.maxHistory ?? 25,
|
|
4293
4374
|
autoplayFn: options.queueOptions?.autoplayFn ?? autoplayFn,
|
|
4294
4375
|
autoPlay: options.queueOptions?.autoPlay ?? false,
|
|
4295
4376
|
storage: options.queueOptions?.storage ?? new MemoryAdapter()
|
|
4296
4377
|
},
|
|
4378
|
+
playerOptions: {
|
|
4379
|
+
requesterFn: options.playerOptions?.requesterFn ?? requesterFn,
|
|
4380
|
+
onDisconnect: {
|
|
4381
|
+
autoDestroy: options.playerOptions?.onDisconnect?.autoDestroy ?? false,
|
|
4382
|
+
autoReconnect: options.playerOptions?.onDisconnect?.autoReconnect ?? true,
|
|
4383
|
+
autoQueue: options.playerOptions?.onDisconnect?.autoQueue ?? false
|
|
4384
|
+
},
|
|
4385
|
+
onError: {
|
|
4386
|
+
autoDestroy: options.playerOptions?.onError?.autoDestroy ?? false,
|
|
4387
|
+
autoSkip: options.playerOptions?.onError?.autoSkip ?? false,
|
|
4388
|
+
autoStop: options.playerOptions?.onError?.autoStop ?? false
|
|
4389
|
+
}
|
|
4390
|
+
},
|
|
4297
4391
|
client: {
|
|
4298
4392
|
id: options.client?.id ?? "",
|
|
4299
4393
|
username: options.client?.username ?? "hoshimi-client"
|
|
@@ -4430,6 +4524,56 @@ var Hoshimi = class extends EventEmitter {
|
|
|
4430
4524
|
);
|
|
4431
4525
|
return;
|
|
4432
4526
|
}
|
|
4527
|
+
if ("channel_id" in data && typeof data.channel_id === "string") {
|
|
4528
|
+
if (data.channel_id !== player.voiceId) {
|
|
4529
|
+
this.emit(
|
|
4530
|
+
"debug" /* Debug */,
|
|
4531
|
+
3 /* Player */,
|
|
4532
|
+
`[Player] -> [Voice] Updating the voice channel for: ${data.guild_id} | Old: ${player.voiceId} | New: ${data.channel_id}`
|
|
4533
|
+
);
|
|
4534
|
+
player.voice.sessionId = data.session_id ?? player.voice.sessionId;
|
|
4535
|
+
player.voiceId = data.channel_id;
|
|
4536
|
+
player.options.voiceId = data.channel_id;
|
|
4537
|
+
if (!player.connected) await player.connect();
|
|
4538
|
+
return;
|
|
4539
|
+
}
|
|
4540
|
+
} else {
|
|
4541
|
+
this.emit("debug" /* Debug */, 3 /* Player */, `[Player] -> [Voice] The channel id is missing for: ${data.guild_id}`);
|
|
4542
|
+
const { autoDestroy, autoReconnect, autoQueue } = this.options.playerOptions.onDisconnect;
|
|
4543
|
+
if (autoDestroy) {
|
|
4544
|
+
await player.destroy("Player-VoiceChannelLeft" /* VoiceChannelLeft */);
|
|
4545
|
+
return;
|
|
4546
|
+
}
|
|
4547
|
+
if (autoReconnect) {
|
|
4548
|
+
try {
|
|
4549
|
+
const position = player.position;
|
|
4550
|
+
const paused = player.paused;
|
|
4551
|
+
this.emit(
|
|
4552
|
+
"debug" /* Debug */,
|
|
4553
|
+
3 /* Player */,
|
|
4554
|
+
`[Player] -> [Voice] Attempting to reconnect the player for: ${data.guild_id}`
|
|
4555
|
+
);
|
|
4556
|
+
if (autoQueue && player.queue.current && !player.queue.isEmpty()) await player.connect();
|
|
4557
|
+
if (player.queue.current) return player.play({ track: player.queue.current, paused, position });
|
|
4558
|
+
if (!player.queue.isEmpty()) return player.play({ paused });
|
|
4559
|
+
this.emit(
|
|
4560
|
+
"debug" /* Debug */,
|
|
4561
|
+
3 /* Player */,
|
|
4562
|
+
`[Player] -> [Voice] No tracks to play after reconnect for: ${data.guild_id}`
|
|
4563
|
+
);
|
|
4564
|
+
} catch (error) {
|
|
4565
|
+
this.emit("playerError" /* PlayerError */, player, error);
|
|
4566
|
+
await player.destroy("Player-ReconnectFailed" /* ReconnectFailed */);
|
|
4567
|
+
}
|
|
4568
|
+
}
|
|
4569
|
+
player.voiceId = void 0;
|
|
4570
|
+
player.voice = {
|
|
4571
|
+
endpoint: null,
|
|
4572
|
+
sessionId: null,
|
|
4573
|
+
token: null
|
|
4574
|
+
};
|
|
4575
|
+
return;
|
|
4576
|
+
}
|
|
4433
4577
|
this.emit("debug" /* Debug */, 3 /* Player */, `[Player] -> [Voice] The player voice is missing for: ${data.guild_id}`);
|
|
4434
4578
|
}
|
|
4435
4579
|
break;
|
|
@@ -4539,6 +4683,7 @@ var Hoshimi = class extends EventEmitter {
|
|
|
4539
4683
|
1 /* Manager */,
|
|
4540
4684
|
`[Manager] -> [Search] Searching for: ${options.query} (${options.engine ?? "unknown"}) | Result: ${stringify(res)}`
|
|
4541
4685
|
);
|
|
4686
|
+
const requesterFn2 = this.options.playerOptions.requesterFn;
|
|
4542
4687
|
switch (res.loadType) {
|
|
4543
4688
|
case "empty" /* Empty */: {
|
|
4544
4689
|
return {
|
|
@@ -4564,7 +4709,7 @@ var Hoshimi = class extends EventEmitter {
|
|
|
4564
4709
|
exception: null,
|
|
4565
4710
|
playlist: res.data,
|
|
4566
4711
|
pluginInfo: res.data.pluginInfo,
|
|
4567
|
-
tracks: res.data.tracks.map((t) => new Track(t, options.requester))
|
|
4712
|
+
tracks: res.data.tracks.map((t) => new Track(t, requesterFn2(options.requester)))
|
|
4568
4713
|
};
|
|
4569
4714
|
}
|
|
4570
4715
|
case "search" /* Search */: {
|
|
@@ -4573,7 +4718,7 @@ var Hoshimi = class extends EventEmitter {
|
|
|
4573
4718
|
exception: null,
|
|
4574
4719
|
playlist: null,
|
|
4575
4720
|
pluginInfo: null,
|
|
4576
|
-
tracks: res.data.map((t) => new Track(t, options.requester))
|
|
4721
|
+
tracks: res.data.map((t) => new Track(t, requesterFn2(options.requester)))
|
|
4577
4722
|
};
|
|
4578
4723
|
}
|
|
4579
4724
|
case "track" /* Track */: {
|
|
@@ -4582,7 +4727,7 @@ var Hoshimi = class extends EventEmitter {
|
|
|
4582
4727
|
exception: null,
|
|
4583
4728
|
playlist: null,
|
|
4584
4729
|
pluginInfo: res.data.pluginInfo,
|
|
4585
|
-
tracks: [new Track(res.data, options.requester)]
|
|
4730
|
+
tracks: [new Track(res.data, requesterFn2(options.requester))]
|
|
4586
4731
|
};
|
|
4587
4732
|
}
|
|
4588
4733
|
}
|