Skip to content
This repository has been archived by the owner on Nov 13, 2022. It is now read-only.

v3: fix create generics #118

Open
wants to merge 2 commits into
base: v3
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
97 changes: 48 additions & 49 deletions packages/erela.js-api/src/api/Manager.ts
Original file line number Diff line number Diff line change
@@ -1,69 +1,68 @@
import Collection from "@discordjs/collection";
import EventEmitter from "events";
import type { Player, PlayerOptions } from "./Player";
import type { Player } from "./Player";

/**
* The base options to provide for a audio provider.
* The base options to provide for a audio provider.
*/
export interface ManagerOptions {
/**
* A list of plugins to use with the audio provider, these may be specific for an audio provider.
*/
readonly plugins?: Plugin[]
/**
* A list of plugins to use with the audio provider, these may be specific for an audio provider.
*/
readonly plugins?: Plugin[]
}

/**
* The base Manager
*/
export interface Manager<
MO extends ManagerOptions = ManagerOptions,
PO extends PlayerOptions = PlayerOptions,
P extends Player<PO> = Player<PO>
> extends EventEmitter {
/**
* The options provided to this manager.
*/
readonly options: MO;
export interface Manager<O extends ManagerOptions, P extends Player<any, any>> extends EventEmitter {
/**
* The options provided to this manager.
*/
readonly options: O;

/**
* All the players that were created by this manager.
*/
readonly players: Collection<string, P>;
/**
* All the players that were created by this manager.
*/
readonly players: Collection<string, P>;

/**
* Adds a plugin
* @param plugin Plugin
*/
use(plugin: Plugin): void;
/**
* Adds a plugin
* @param plugin Plugin
*/
use(plugin: Plugin): void;

/**
* Adds an array of plugins
* @param plugin Plugin
*/
use(plugins: Plugin[]): void;
/**
* Adds an array of plugins
* @param plugins The plugins to use in this manager
*/
use(plugins: Plugin[]): void;

/**
* Creates a Player with the provided Guild ID, `textChannel` and `voiceChannel` must be bound later.
*/
create(guild: string): P;
/**
* Creates a Player with the provided Guild ID, `textChannel` and `voiceChannel` must be bound later.
*/
create(guild: string): P;

// /**
// * Creates a Player with the provided Guild and Voice channel ID, `textChannel` must be bound later.
// */
// create(guild: string, channel: string): P;
// /**
// * Creates a Player with the provided Guild and Voice channel ID, `textChannel` must be bound later.
// */
// create(guild: string, channel: string): P;

/**
* Creates a Player with the provided player options.
*/
create(options: PlayerOptions): P;
/**
* Creates a Player with the provided player options.
*/
create(options: ExtractPlayerOptions<P>): P;

/**
* Destroys a Player using the Guild ID.
*/
destroy(guild: string): void;
/**
* Destroys a Player using the Guild ID.
*/
destroy(guild: string): void;

/**
* Destroys a Player using the Player instance.
*/
destroy(player: P): void;
/**
* Destroys a Player using the Player instance.
*/
destroy(player: P): void;
}

type ExtractPlayerOptions<P> = P extends Player<Manager<any, any>, infer O> ? O : never;

29 changes: 13 additions & 16 deletions packages/erela.js-api/src/api/Player.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import { State } from "../impl/State";
import { Manager, ManagerOptions } from "./Manager";
import { Manager } from "./Manager";

/**
* The base PlayerOptions.
Expand All @@ -9,7 +9,7 @@ export interface PlayerOptions {
* The guild the Player belongs to.
*/
readonly guild: string;

/**
* The text channel the Player belongs to.
*/
Expand Down Expand Up @@ -39,55 +39,52 @@ export interface PlayerOptions {
/**
* The base Player.
*/
export interface Player<
PO extends PlayerOptions = PlayerOptions,
MO extends ManagerOptions = ManagerOptions
> {
export interface Player<M extends Manager<unknown, any>, O extends PlayerOptions> {
/**
* The options for this Player.
*/
readonly options: PO;
readonly options: O;

/**
* The manager
*/
readonly manager: Manager<MO>
readonly manager: M;

/**
* The guild this Player is bound to.
*/
readonly guild: string;

/**
* The guild text channel this Player is bound to.
* The guild text channel this Player is bound to.
*/
textChannel?: string | null;

/**
* The guild voice channel this Player is bound to and will join.
* The guild voice channel this Player is bound to and will join.
*/
voiceChannel?: string | null;

/**
* The time position in the track the player is currently at.
*/
position?: number | null;

/**
* Whether is the player is currently playing a track.
*/
playing?: boolean | null;

/**
* Whether is the player is currently paused.
*/
paused?: boolean | null;

/**
* The volume the player is playing at.
*/
volume?: number | null;

/**
* The state the player is in.
*/
Expand All @@ -98,7 +95,7 @@ export interface Player<
* @param channel string
*/
connect(channel?: string): Promise<void>;

/**
* Disconnects from the voice channel, this will keep the player alive for use later.
*/
Expand All @@ -108,4 +105,4 @@ export interface Player<
* Destroys the player and disconnects it from the voice channel.
*/
destroy(): Promise<void>;
}
}
41 changes: 18 additions & 23 deletions packages/erela.js-api/src/erela.ts
Original file line number Diff line number Diff line change
@@ -1,34 +1,27 @@
import type { Player, PlayerOptions } from "./api/Player";
import type { Manager, ManagerOptions } from "./api/Manager";
import type { Player } from "./api/Player";
import type { Manager } from "./api/Manager";
import { Detector } from "./impl/detection/Detector";

export namespace Erela {
const plugins: Plugin[] = [];

/**
* Adds a plugin that will be used when a Manager is created.
* @param plugin Plugin
*/
* Adds a plugin that will be used when a Manager is created.
* @param plugin Plugin
*/
export function use(plugin: Plugin): void {
plugins.push(plugin);
}

/**
* Creates a new player manager with the supplied options.
*
* @param options The options to supply the player manager.
* @param klass The provider class to instantiate.
*/
export async function create<
M extends Manager<ManagerOptions, PlayerOptions, Player>
>(options: ExtractOptions<M>, klass?: Class<M>): Promise<M>

export async function create<
M extends Manager<O, PO, P>,
O extends ManagerOptions = ManagerOptions,
PO extends PlayerOptions = PlayerOptions,
P extends Player<PO> = Player<PO>
>(options?: O, klass?: Class<M>): Promise<M> {
* Creates a new player manager with the supplied options.
*
* @param options The options to supply the player manager.
* @param klass The provider class to instantiate.
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I would suggest target is better word here than klass

*/
export function create<M extends Manager<any, any>>(options: ExtractOptions<M>, klass?: Class<M>): M
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

same as above klass => target


export function create<M extends Manager<any, any>>(options?: ExtractOptions<M>, klass?: Class<M>): M {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

same as above klass => target

if (!klass) {
const providers = Detector.findProviders();
if (!providers.length) {
Expand All @@ -46,14 +39,16 @@ export namespace Erela {
}

const manager = new klass!!(options);
if (plugins.length) manager.use(plugins);
if (plugins.length) {
manager.use(plugins);
}

return manager;
}

type ExtractOptions<P> = P extends Manager<infer O, Player> ? O : never;
type ExtractOptions<P> = P extends Manager<infer O, Player<any, any>> ? O : never;

type Class<T> = {
new(...args: any): T;
}
}
}
8 changes: 4 additions & 4 deletions packages/erela.js-api/src/index.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
export * from "./api/Manager"
export * from "./api/Player"
export * from "./api/Manager";
export * from "./api/Player";

export * from "./impl/State"
export * from "./impl/State";

export * from "./erela"
export * from "./erela";