mirror of
https://github.com/discordjs/discord.js.git
synced 2026-03-19 13:03:31 +01:00
test: replace jest with vitest (#10472)
* chore: vitest config * feat: vitest * fix: do not actually create ws * chore: config * chore: lockfile * chore: revert downgrade, up node * chore: package - 'git add -A' * chore: delete mock-socket * chore: delete mock-socket * fix: lockfile --------- Co-authored-by: almeidx <github@almeidx.dev> Co-authored-by: kodiakhq[bot] <49736102+kodiakhq[bot]@users.noreply.github.com>
This commit is contained in:
@@ -5,6 +5,7 @@ import { Buffer } from 'node:buffer';
|
||||
import { once } from 'node:events';
|
||||
import process from 'node:process';
|
||||
import { Readable } from 'node:stream';
|
||||
import { describe, test, expect, vitest, type Mock, beforeEach, afterEach } from 'vitest';
|
||||
import { addAudioPlayer, deleteAudioPlayer } from '../src/DataStore';
|
||||
import { VoiceConnection, VoiceConnectionStatus } from '../src/VoiceConnection';
|
||||
import type { AudioPlayer } from '../src/audio/AudioPlayer';
|
||||
@@ -13,14 +14,31 @@ import { AudioPlayerError } from '../src/audio/AudioPlayerError';
|
||||
import { AudioResource } from '../src/audio/AudioResource';
|
||||
import { NoSubscriberBehavior } from '../src/index';
|
||||
|
||||
jest.mock('../src/DataStore');
|
||||
jest.mock('../src/VoiceConnection');
|
||||
jest.mock('../src/audio/AudioPlayerError');
|
||||
vitest.mock('../src/DataStore', () => {
|
||||
return {
|
||||
addAudioPlayer: vitest.fn(),
|
||||
deleteAudioPlayer: vitest.fn(),
|
||||
};
|
||||
});
|
||||
|
||||
const addAudioPlayerMock = addAudioPlayer as unknown as jest.Mock<typeof addAudioPlayer>;
|
||||
const deleteAudioPlayerMock = deleteAudioPlayer as unknown as jest.Mock<typeof deleteAudioPlayer>;
|
||||
const AudioPlayerErrorMock = AudioPlayerError as unknown as jest.Mock<typeof AudioPlayerError>;
|
||||
const VoiceConnectionMock = VoiceConnection as unknown as jest.Mock<VoiceConnection>;
|
||||
vitest.mock('../src/VoiceConnection', async (importOriginal) => {
|
||||
// eslint-disable-next-line @typescript-eslint/consistent-type-imports
|
||||
const actual = await importOriginal<typeof import('../src/VoiceConnection')>();
|
||||
const VoiceConnection = vitest.fn();
|
||||
VoiceConnection.prototype.setSpeaking = vitest.fn();
|
||||
VoiceConnection.prototype.dispatchAudio = vitest.fn();
|
||||
VoiceConnection.prototype.prepareAudioPacket = vitest.fn();
|
||||
return {
|
||||
...actual,
|
||||
VoiceConnection,
|
||||
};
|
||||
});
|
||||
|
||||
vitest.mock('../src/audio/AudioPlayerError', () => {
|
||||
return {
|
||||
AudioPlayerError: vitest.fn(),
|
||||
};
|
||||
});
|
||||
|
||||
function* silence() {
|
||||
while (true) {
|
||||
@@ -29,15 +47,15 @@ function* silence() {
|
||||
}
|
||||
|
||||
function createVoiceConnectionMock() {
|
||||
const connection = new VoiceConnectionMock();
|
||||
const connection = new VoiceConnection({} as any, {} as any);
|
||||
connection.state = {
|
||||
status: VoiceConnectionStatus.Signalling,
|
||||
adapter: {
|
||||
sendPayload: jest.fn(),
|
||||
destroy: jest.fn(),
|
||||
sendPayload: vitest.fn(),
|
||||
destroy: vitest.fn(),
|
||||
},
|
||||
};
|
||||
connection.subscribe = jest.fn((player) => player['subscribe'](connection));
|
||||
connection.subscribe = vitest.fn((player) => player['subscribe'](connection));
|
||||
return connection;
|
||||
}
|
||||
|
||||
@@ -57,10 +75,7 @@ async function started(resource: AudioResource) {
|
||||
let player: AudioPlayer | undefined;
|
||||
|
||||
beforeEach(() => {
|
||||
AudioPlayerErrorMock.mockReset();
|
||||
VoiceConnectionMock.mockReset();
|
||||
addAudioPlayerMock.mockReset();
|
||||
deleteAudioPlayerMock.mockReset();
|
||||
vitest.resetAllMocks();
|
||||
});
|
||||
|
||||
afterEach(() => {
|
||||
@@ -71,8 +86,8 @@ describe('State transitions', () => {
|
||||
test('Starts in Idle state', () => {
|
||||
player = createAudioPlayer();
|
||||
expect(player.state.status).toEqual(AudioPlayerStatus.Idle);
|
||||
expect(addAudioPlayerMock).toBeCalledTimes(0);
|
||||
expect(deleteAudioPlayerMock).toBeCalledTimes(0);
|
||||
expect(addAudioPlayer).toBeCalledTimes(0);
|
||||
expect(deleteAudioPlayer).toBeCalledTimes(0);
|
||||
});
|
||||
|
||||
test('Playing resource with pausing and resuming', async () => {
|
||||
@@ -86,11 +101,11 @@ describe('State transitions', () => {
|
||||
expect(player.state.status).toEqual(AudioPlayerStatus.Idle);
|
||||
expect(player.unpause()).toEqual(false);
|
||||
expect(player.state.status).toEqual(AudioPlayerStatus.Idle);
|
||||
expect(addAudioPlayerMock).toBeCalledTimes(0);
|
||||
expect(addAudioPlayer).toBeCalledTimes(0);
|
||||
|
||||
player.play(resource);
|
||||
expect(player.state.status).toEqual(AudioPlayerStatus.Playing);
|
||||
expect(addAudioPlayerMock).toBeCalledTimes(1);
|
||||
expect(addAudioPlayer).toBeCalledTimes(1);
|
||||
|
||||
// Expect pause() to return true and transition to paused state
|
||||
expect(player.pause()).toEqual(true);
|
||||
@@ -109,7 +124,7 @@ describe('State transitions', () => {
|
||||
expect(player.state.status).toEqual(AudioPlayerStatus.Playing);
|
||||
|
||||
// The audio player should not have been deleted throughout these changes
|
||||
expect(deleteAudioPlayerMock).toBeCalledTimes(0);
|
||||
expect(deleteAudioPlayer).toBeCalledTimes(0);
|
||||
});
|
||||
|
||||
test('Playing to Stopping', async () => {
|
||||
@@ -122,13 +137,13 @@ describe('State transitions', () => {
|
||||
|
||||
player.play(resource);
|
||||
expect(player.state.status).toEqual(AudioPlayerStatus.Playing);
|
||||
expect(addAudioPlayerMock).toBeCalledTimes(1);
|
||||
expect(deleteAudioPlayerMock).toBeCalledTimes(0);
|
||||
expect(addAudioPlayer).toBeCalledTimes(1);
|
||||
expect(deleteAudioPlayer).toBeCalledTimes(0);
|
||||
|
||||
expect(player.stop()).toEqual(true);
|
||||
expect(player.state.status).toEqual(AudioPlayerStatus.Playing);
|
||||
expect(addAudioPlayerMock).toBeCalledTimes(1);
|
||||
expect(deleteAudioPlayerMock).toBeCalledTimes(0);
|
||||
expect(addAudioPlayer).toBeCalledTimes(1);
|
||||
expect(deleteAudioPlayer).toBeCalledTimes(0);
|
||||
expect(resource.silenceRemaining).toEqual(5);
|
||||
});
|
||||
|
||||
@@ -142,8 +157,8 @@ describe('State transitions', () => {
|
||||
await started(resource);
|
||||
|
||||
expect(player.state.status).toEqual(AudioPlayerStatus.Playing);
|
||||
expect(addAudioPlayerMock).toHaveBeenCalled();
|
||||
expect(deleteAudioPlayerMock).not.toHaveBeenCalled();
|
||||
expect(addAudioPlayer).toHaveBeenCalled();
|
||||
expect(deleteAudioPlayer).not.toHaveBeenCalled();
|
||||
});
|
||||
|
||||
describe('NoSubscriberBehavior transitions', () => {
|
||||
@@ -188,11 +203,11 @@ describe('State transitions', () => {
|
||||
player = createAudioPlayer({ behaviors: { noSubscriber: NoSubscriberBehavior.Stop } });
|
||||
|
||||
player.play(resource);
|
||||
expect(addAudioPlayerMock).toBeCalledTimes(1);
|
||||
expect(addAudioPlayer).toBeCalledTimes(1);
|
||||
expect(player.checkPlayable()).toEqual(true);
|
||||
player['_stepPrepare']();
|
||||
expect(player.state.status).toEqual(AudioPlayerStatus.Idle);
|
||||
expect(deleteAudioPlayerMock).toBeCalledTimes(1);
|
||||
expect(deleteAudioPlayer).toBeCalledTimes(1);
|
||||
});
|
||||
});
|
||||
|
||||
@@ -217,7 +232,7 @@ describe('State transitions', () => {
|
||||
|
||||
player.play(resource);
|
||||
expect(player.state.status).toEqual(AudioPlayerStatus.Playing);
|
||||
expect(addAudioPlayerMock).toBeCalledTimes(1);
|
||||
expect(addAudioPlayer).toBeCalledTimes(1);
|
||||
expect(player.checkPlayable()).toEqual(true);
|
||||
|
||||
// Run through a few packet cycles
|
||||
@@ -241,7 +256,8 @@ describe('State transitions', () => {
|
||||
expect(connection.dispatchAudio).toHaveBeenCalledTimes(6);
|
||||
await wait();
|
||||
player['_stepPrepare']();
|
||||
const prepareAudioPacket = connection.prepareAudioPacket as unknown as jest.Mock<
|
||||
const prepareAudioPacket = connection.prepareAudioPacket as unknown as Mock<
|
||||
[Buffer],
|
||||
typeof connection.prepareAudioPacket
|
||||
>;
|
||||
expect(prepareAudioPacket).toHaveBeenCalledTimes(6);
|
||||
@@ -251,7 +267,7 @@ describe('State transitions', () => {
|
||||
expect(player.state.status).toEqual(AudioPlayerStatus.Idle);
|
||||
expect(connection.setSpeaking).toBeCalledTimes(1);
|
||||
expect(connection.setSpeaking).toHaveBeenLastCalledWith(false);
|
||||
expect(deleteAudioPlayerMock).toHaveBeenCalledTimes(1);
|
||||
expect(deleteAudioPlayer).toHaveBeenCalledTimes(1);
|
||||
});
|
||||
|
||||
test('stop() causes resource to use silence padding frames', async () => {
|
||||
@@ -275,7 +291,7 @@ describe('State transitions', () => {
|
||||
|
||||
player.play(resource);
|
||||
expect(player.state.status).toEqual(AudioPlayerStatus.Playing);
|
||||
expect(addAudioPlayerMock).toBeCalledTimes(1);
|
||||
expect(addAudioPlayer).toBeCalledTimes(1);
|
||||
expect(player.checkPlayable()).toEqual(true);
|
||||
|
||||
player.stop();
|
||||
@@ -298,7 +314,8 @@ describe('State transitions', () => {
|
||||
|
||||
await wait();
|
||||
expect(player.checkPlayable()).toEqual(false);
|
||||
const prepareAudioPacket = connection.prepareAudioPacket as unknown as jest.Mock<
|
||||
const prepareAudioPacket = connection.prepareAudioPacket as unknown as Mock<
|
||||
[Buffer],
|
||||
typeof connection.prepareAudioPacket
|
||||
>;
|
||||
expect(prepareAudioPacket).toHaveBeenCalledTimes(5);
|
||||
@@ -306,7 +323,7 @@ describe('State transitions', () => {
|
||||
expect(player.state.status).toEqual(AudioPlayerStatus.Idle);
|
||||
expect(connection.setSpeaking).toBeCalledTimes(1);
|
||||
expect(connection.setSpeaking).toHaveBeenLastCalledWith(false);
|
||||
expect(deleteAudioPlayerMock).toHaveBeenCalledTimes(1);
|
||||
expect(deleteAudioPlayer).toHaveBeenCalledTimes(1);
|
||||
});
|
||||
|
||||
test('Plays silence 5 times for unreadable stream before quitting', async () => {
|
||||
@@ -328,10 +345,11 @@ describe('State transitions', () => {
|
||||
|
||||
player.play(resource);
|
||||
expect(player.state.status).toEqual(AudioPlayerStatus.Playing);
|
||||
expect(addAudioPlayerMock).toBeCalledTimes(1);
|
||||
expect(addAudioPlayer).toBeCalledTimes(1);
|
||||
expect(player.checkPlayable()).toEqual(true);
|
||||
|
||||
const prepareAudioPacket = connection.prepareAudioPacket as unknown as jest.Mock<
|
||||
const prepareAudioPacket = connection.prepareAudioPacket as unknown as Mock<
|
||||
[Buffer],
|
||||
typeof connection.prepareAudioPacket
|
||||
>;
|
||||
|
||||
@@ -351,7 +369,7 @@ describe('State transitions', () => {
|
||||
expect(player.state.status).toEqual(AudioPlayerStatus.Idle);
|
||||
expect(connection.setSpeaking).toBeCalledTimes(1);
|
||||
expect(connection.setSpeaking).toHaveBeenLastCalledWith(false);
|
||||
expect(deleteAudioPlayerMock).toHaveBeenCalledTimes(1);
|
||||
expect(deleteAudioPlayer).toHaveBeenCalledTimes(1);
|
||||
});
|
||||
|
||||
test('checkPlayable() transitions to Idle for unreadable stream', async () => {
|
||||
@@ -397,6 +415,6 @@ test('Propagates errors from streams', async () => {
|
||||
const res = await once(player, 'error');
|
||||
const playerError = res[0] as AudioPlayerError;
|
||||
expect(playerError).toBeInstanceOf(AudioPlayerError);
|
||||
expect(AudioPlayerErrorMock).toHaveBeenCalledWith(error, resource);
|
||||
expect(AudioPlayerError).toHaveBeenCalledWith(error, resource);
|
||||
expect(player.state.status).toEqual(AudioPlayerStatus.Idle);
|
||||
});
|
||||
|
||||
Reference in New Issue
Block a user