DJS Commandsv2 docs
API Reference@djs-commands/core

Plugins

PluginManifest and PluginSetupContext for cross-cutting hooks.

See Concepts → Plugins for the narrative.

PluginManifest

interface PluginManifest {
	name: string;
	commands?: AnyCommand[];
	setup?: (ctx: PluginSetupContext) => void | Promise<void>;
	teardown?: () => void | Promise<void>;
}

A plain object passed to createCommandHandler's plugins array. Convention is to expose it as a factory function so consumers can configure it.

import type { PluginManifest } from "@djs-commands/core";

export function loggingPlugin(opts: { level?: "info" | "debug" } = {}): PluginManifest {
	return {
		name: "logging",
		setup({ client }) {
			client.on("interactionCreate", (i) => {
				if (i.isChatInputCommand()) {
					console.log(`[${opts.level ?? "info"}]`, i.commandName, "by", i.user.tag);
				}
			});
		},
	};
}
FieldNotes
nameHuman-readable identifier; surfaces in error messages.
commandsCommands merged into the dispatcher at boot — same shape as the top-level commands. Duplicate names throw at boot.
setupAwaited at boot in registration order. Throwing aborts handler boot (handler.ready rejects).
teardownAwaited on handler.destroy() in reverse-registration order. Errors are logged but don't block other teardowns.

PluginSetupContext

interface PluginSetupContext {
	client: Client;
}

Intentionally minimal. Plugins that need to expose state to commands typically:

  • Attach to the client as a property: client.myState = .... Type via module augmentation.
  • Close over their own values and inject them into the commands they ship.
  • Use the Storage adapter for persistent state.

Avoid module-scoped singletons in plugin code — that breaks tests that want to construct multiple handlers in the same process.

Last updated on

On this page