Module
Overview
This page walks through a minimal but complete Glyria module — @glyria/timers — as a reference for building your own.
index.ts
The entry point of your module. This is where you hook into the bot lifecycle and expose your public API.
// src/index.ts
import { globalBus, GlyriaBus } from "@glyria/bot"
import { Events } from "discord.js"
type TimersBusEvents = {
ready: []
}
export const bus = new GlyriaBus<TimersBusEvents>()
globalBus.on("botReady", async (client) => {
await bus.emit("ready")
client.bus.on(Events.MessageCreate, (message) => {
if (message.content === "!ping") {
message.reply("Pong! From @glyria/timers !")
}
})
})
globalBus
globalBus is the internal Glyria event bus. The botReady event fires once the Discord client is logged in and ready. This is the recommended entry point for any module initialization logic.
client.bus
client.bus is the Discord.js event bus. It maps directly to the Events enum from discord.js, but goes through Glyria's middleware layer — meaning user-defined middleware and middleware from other modules are applied. Using client.on directly bypasses all of them.
// ✅ Goes through user and module middleware
client.bus.on(Events.MessageCreate, handler)
// ⚠️ Bypasses all middleware — use only if you know what you're doing
client.on(Events.MessageCreate, handler)
Auto imports
Auto imports are a feature designed for the user's project (src/composables/, src/utils/). Inside a module, they are not available — always use explicit imports.
// ❌ Don't rely on auto imports in a module
const db = useDatabase()
// ✅ Always import explicitly
import { useDatabase } from "./composables/useDatabase.js"
const db = useDatabase()
Exposing a public API
Anything exported from index.ts is automatically available in the user's project under your module's namespace — no import needed on their end.
// src/index.ts
export const createJob = (fn: () => void, cron: string) => { ... }
export const deleteJob = (id: string) => { ... }
// In the user's project — no import required
Timers.createJob(() => {
console.log("runs every minute")
}, "* * * * *")
Exposing a Bus
If your module emits its own events, export the bus directly from index.ts. Users can then listen to it under your module's namespace.
// src/index.ts
type TimersBusEvents = {
ready: []
}
export const bus = new GlyriaBus<TimersBusEvents>()
// In the user's project — no import required
Timers.bus.on("ready", () => {
console.log("Timers module is ready!")
})
The namespace is derived from the package name in PascalCase — @glyria/timers → Timers.

